From a01a85d2d0ba719dd7251407e1d08477963904e3 Mon Sep 17 00:00:00 2001 From: lav Date: Thu, 18 Dec 2025 16:04:15 +0100 Subject: [PATCH] add logs in ui --- flows.json | 632 +++++++++++++++++++++++++++++++++++++++++++--- package-lock.json | 117 +++------ package.json | 2 +- public/index.html | 3 + public/js/main.js | 31 ++- 5 files changed, 663 insertions(+), 122 deletions(-) diff --git a/flows.json b/flows.json index ebcfc70..842d9aa 100644 --- a/flows.json +++ b/flows.json @@ -31,6 +31,14 @@ "info": "", "env": [] }, + { + "id": "21d6665eb37042e8", + "type": "tab", + "label": "MGMT", + "disabled": false, + "info": "", + "env": [] + }, { "id": "d760e52dca2de1e8", "type": "subflow", @@ -1411,7 +1419,9 @@ "x": 1110, "y": 540, "wires": [ - [] + [ + "090a84d8dfd47125" + ] ] }, { @@ -1578,35 +1588,10 @@ "wires": [ [ "9d7a8062c6f83014", - "bfb586da4d7113d1" + "3ddef8030d0b6ef5" ] ] }, - { - "id": "bfb586da4d7113d1", - "type": "change", - "z": "a0840e5d7cd65ea0", - "name": "", - "rules": [ - { - "t": "set", - "p": "payload", - "pt": "msg", - "to": "{}", - "tot": "json" - } - ], - "action": "", - "property": "", - "from": "", - "to": "", - "reg": false, - "x": 1060, - "y": 360, - "wires": [ - [] - ] - }, { "id": "3e60e0d59090800a", "type": "change", @@ -1800,6 +1785,84 @@ "y": 100, "wires": [] }, + { + "id": "3ddef8030d0b6ef5", + "type": "change", + "z": "a0840e5d7cd65ea0", + "name": "", + "rules": [ + { + "t": "set", + "p": "logs", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$now() & \" RECREATE : \" & $string($count(msg.payload)) & \"
\" & msg.logs", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 1100, + "y": 400, + "wires": [ + [] + ] + }, + { + "id": "090a84d8dfd47125", + "type": "change", + "z": "a0840e5d7cd65ea0", + "name": "", + "rules": [ + { + "t": "set", + "p": "logs", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$now() & \" RECREATE : \" & $string(msg.payload.display) & \" \" & msg.statusCode & \"
\" & msg.logs", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 1300, + "y": 540, + "wires": [ + [] + ] + }, { "id": "d9c660c69caba97c", "type": "http in", @@ -1808,7 +1871,6 @@ "url": "/restart", "method": "get", "upload": false, - "skipBodyParsing": false, "swaggerDoc": "", "x": 190, "y": 180, @@ -2190,7 +2252,9 @@ "x": 790, "y": 480, "wires": [ - [] + [ + "83a533c9ce37c823" + ] ] }, { @@ -2325,8 +2389,8 @@ "arraySpltType": "len", "stream": false, "addname": "", - "x": 1170, - "y": 400, + "x": 130, + "y": 480, "wires": [ [ "83ec24b3be755314" @@ -2363,8 +2427,9 @@ "y": 400, "wires": [ [ - "38b25596b8879610", - "96e3b644172be37e" + "96e3b644172be37e", + "6af54db44072d8c8", + "8f40c26a58d47965" ] ] }, @@ -2465,6 +2530,109 @@ "y": 120, "wires": [] }, + { + "id": "83a533c9ce37c823", + "type": "change", + "z": "47309e7eb1ed7972", + "name": "", + "rules": [ + { + "t": "set", + "p": "logs", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$now() & \" RESTART : \" & $string(msg.payload.display) & \" \" & msg.statusCode & \"
\" & msg.logs", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 1000, + "y": 480, + "wires": [ + [] + ] + }, + { + "id": "6af54db44072d8c8", + "type": "change", + "z": "47309e7eb1ed7972", + "name": "", + "rules": [ + { + "t": "set", + "p": "logs", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$now() & \" RESTART : \" & $string($count(msg.payload)) & \"
\" & msg.logs", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 1200, + "y": 360, + "wires": [ + [] + ] + }, + { + "id": "8f40c26a58d47965", + "type": "delay", + "z": "47309e7eb1ed7972", + "name": "", + "pauseType": "delay", + "timeout": "2", + "timeoutUnits": "seconds", + "rate": "1", + "nbRateUnits": "1", + "rateUnits": "second", + "randomFirst": "1", + "randomLast": "5", + "randomUnits": "seconds", + "drop": false, + "allowrate": false, + "outputs": 1, + "x": 1180, + "y": 400, + "wires": [ + [ + "38b25596b8879610" + ] + ] + }, { "id": "444d125462e30efe", "type": "http in", @@ -3165,5 +3333,403 @@ "ce466fc9782d3b86" ] ] + }, + { + "id": "7d8824d42f0b1752", + "type": "http in", + "z": "21d6665eb37042e8", + "name": "", + "url": "/test", + "method": "post", + "upload": false, + "swaggerDoc": "", + "x": 140, + "y": 100, + "wires": [ + [ + "cd6d824315922ceb" + ] + ] + }, + { + "id": "e992ee6eb7559901", + "type": "http response", + "z": "21d6665eb37042e8", + "name": "", + "statusCode": "", + "headers": {}, + "x": 930, + "y": 100, + "wires": [] + }, + { + "id": "cd6d824315922ceb", + "type": "json", + "z": "21d6665eb37042e8", + "name": "", + "property": "payload", + "action": "", + "pretty": false, + "x": 310, + "y": 100, + "wires": [ + [ + "20461edbf6653a39" + ] + ] + }, + { + "id": "82ae9ffa34434352", + "type": "http request", + "z": "21d6665eb37042e8", + "name": "", + "method": "GET", + "ret": "obj", + "paytoqs": "ignore", + "url": "", + "tls": "", + "persist": false, + "proxy": "", + "insecureHTTPParser": false, + "authType": "", + "senderr": false, + "headers": [], + "x": 730, + "y": 100, + "wires": [ + [ + "e992ee6eb7559901", + "9322fc637b3ddea0" + ] + ] + }, + { + "id": "20461edbf6653a39", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "url", + "pt": "msg", + "to": "msg.payload.netbox & \"/api/plugins/docker/hosts/?name=\" & msg.payload.hostname\t", + "tot": "jsonata" + }, + { + "t": "set", + "p": "headers", + "pt": "msg", + "to": "{\t \"Authorization\": \"Token \" & msg.payload.token,\t \"Accept\": \"application/json\"\t}", + "tot": "jsonata" + }, + { + "t": "set", + "p": "rejectUnauthorized", + "pt": "msg", + "to": "false", + "tot": "bool" + }, + { + "t": "set", + "p": "input", + "pt": "msg", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 500, + "y": 100, + "wires": [ + [ + "82ae9ffa34434352" + ] + ] + }, + { + "id": "d3055430fe5f774c", + "type": "http in", + "z": "21d6665eb37042e8", + "name": "", + "url": "/logs", + "method": "get", + "upload": false, + "swaggerDoc": "", + "x": 140, + "y": 260, + "wires": [ + [ + "443460d30d26adbc" + ] + ] + }, + { + "id": "4cb1f7781eae6e5b", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "logs", + "tot": "global" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 600, + "y": 360, + "wires": [ + [ + "2545a966a84f9381" + ] + ] + }, + { + "id": "2545a966a84f9381", + "type": "http response", + "z": "21d6665eb37042e8", + "name": "", + "statusCode": "", + "headers": {}, + "x": 1190, + "y": 280, + "wires": [] + }, + { + "id": "9322fc637b3ddea0", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "logs", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$now() & \" TEST : \" & $string(msg.input) & \" \" & msg.statusCode & \"
\" & msg.logs", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 940, + "y": 180, + "wires": [ + [] + ] + }, + { + "id": "443460d30d26adbc", + "type": "switch", + "z": "21d6665eb37042e8", + "name": "", + "property": "req.query", + "propertyType": "msg", + "rules": [ + { + "t": "hask", + "v": "last", + "vt": "str" + }, + { + "t": "else" + } + ], + "checkall": "true", + "repair": false, + "outputs": 2, + "x": 310, + "y": 260, + "wires": [ + [ + "cbfea97cbcf6167f" + ], + [ + "4cb1f7781eae6e5b" + ] + ] + }, + { + "id": "cbfea97cbcf6167f", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$split(msg.payload, /
/)[0]", + "tot": "jsonata" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 520, + "y": 240, + "wires": [ + [ + "d2b29dd41f01f36b" + ] + ] + }, + { + "id": "6b332cda48996404", + "type": "inject", + "z": "21d6665eb37042e8", + "name": "", + "props": [ + { + "p": "payload" + } + ], + "repeat": "60", + "crontab": "", + "once": false, + "onceDelay": 0.1, + "topic": "", + "payload": "", + "payloadType": "date", + "x": 170, + "y": 480, + "wires": [ + [ + "f109f382a72456d7" + ] + ] + }, + { + "id": "f109f382a72456d7", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "logs", + "tot": "global" + }, + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": "$join($filter($split($string(payload), \"
\"), function($v, $i) { $i < 500 }),\"
\") & \"
\"", + "tot": "jsonata" + }, + { + "t": "set", + "p": "logs", + "pt": "global", + "to": "payload", + "tot": "msg" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 400, + "y": 480, + "wires": [ + [] + ] + }, + { + "id": "d2b29dd41f01f36b", + "type": "switch", + "z": "21d6665eb37042e8", + "name": "", + "property": "$millis() - (msg.payload ~> $substring(0, 24) ~> $toMillis())", + "propertyType": "jsonata", + "rules": [ + { + "t": "lt", + "v": "2200", + "vt": "num" + }, + { + "t": "else" + } + ], + "checkall": "true", + "repair": false, + "outputs": 2, + "x": 710, + "y": 240, + "wires": [ + [ + "2545a966a84f9381" + ], + [ + "cb0189dbe7b882ec" + ] + ] + }, + { + "id": "cb0189dbe7b882ec", + "type": "change", + "z": "21d6665eb37042e8", + "name": "", + "rules": [ + { + "t": "set", + "p": "payload", + "pt": "msg", + "to": " 
", + "tot": "str" + } + ], + "action": "", + "property": "", + "from": "", + "to": "", + "reg": false, + "x": 740, + "y": 300, + "wires": [ + [ + "2545a966a84f9381" + ] + ] } ] \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index dd2ba5e..5b55544 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "netbox-docker-image-upgrade", - "version": "0.8.0", + "version": "0.9.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "netbox-docker-image-upgrade", - "version": "0.8.0", + "version": "0.9.0", "license": "BSD-3-Clause", "dependencies": { "node-red": "*" @@ -493,9 +493,9 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "25.0.1", - "resolved": "https://registry.npmjs.org/@types/node/-/node-25.0.1.tgz", - "integrity": "sha512-czWPzKIAXucn9PtsttxmumiQ9N0ok9FrBwgRWrwmVLlp86BrMExzvXRLFYRJ+Ex3g6yqj+KuaxfX1JTgV2lpfg==", + "version": "25.0.3", + "resolved": "https://registry.npmjs.org/@types/node/-/node-25.0.3.tgz", + "integrity": "sha512-W609buLVRVmeW693xKfzHeIV6nJGGz98uCPfeXI1ELMLXVeKYZ9m15fAMSaUPBHYLGFsVRcMmSCksQOrZV9BYA==", "license": "MIT", "dependencies": { "undici-types": "~7.16.0" @@ -3012,9 +3012,9 @@ } }, "node_modules/send": { - "version": "0.19.1", - "resolved": "https://registry.npmjs.org/send/-/send-0.19.1.tgz", - "integrity": "sha512-p4rRk4f23ynFEfcD9LA0xRYngj+IyGiEYyqqOak8kaN0TvNmuxC2dcVeBn62GpCeR2CpWqyHCNScTP91QbAVFg==", + "version": "0.19.2", + "resolved": "https://registry.npmjs.org/send/-/send-0.19.2.tgz", + "integrity": "sha512-VMbMxbDeehAxpOtWJXlcUS5E8iXh6QmN+BkRX1GARS3wRaXEEgzCcB10gTQazO42tpNIya8xIyNx8fll1OFPrg==", "license": "MIT", "dependencies": { "debug": "2.6.9", @@ -3023,61 +3023,39 @@ "encodeurl": "~2.0.0", "escape-html": "~1.0.3", "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", + "fresh": "~0.5.2", + "http-errors": "~2.0.1", "mime": "1.6.0", "ms": "2.1.3", - "on-finished": "2.4.1", + "on-finished": "~2.4.1", "range-parser": "~1.2.1", - "statuses": "2.0.1" + "statuses": "~2.0.2" }, "engines": { "node": ">= 0.8.0" } }, - "node_modules/send/node_modules/mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "license": "MIT", - "bin": { - "mime": "cli.js" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/send/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/send/node_modules/statuses": { + "node_modules/send/node_modules/http-errors": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/serve-static": { - "version": "1.16.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.16.2.tgz", - "integrity": "sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.1.tgz", + "integrity": "sha512-4FbRdAX+bSdmo4AUFuS0WNiPz8NgFt+r8ThgNWmlrjQjt1Q7ZR9+zTlce2859x4KSXrwIsaeTqDoKQmtP8pLmQ==", "license": "MIT", "dependencies": { - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.19.0" + "depd": "~2.0.0", + "inherits": "~2.0.4", + "setprototypeof": "~1.2.0", + "statuses": "~2.0.2", + "toidentifier": "~1.0.1" }, "engines": { - "node": ">= 0.8.0" + "node": ">= 0.8" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" } }, - "node_modules/serve-static/node_modules/mime": { + "node_modules/send/node_modules/mime": { "version": "1.6.0", "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", @@ -3089,54 +3067,27 @@ "node": ">=4" } }, - "node_modules/serve-static/node_modules/ms": { + "node_modules/send/node_modules/ms": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", "license": "MIT" }, - "node_modules/serve-static/node_modules/send": { - "version": "0.19.0", - "resolved": "https://registry.npmjs.org/send/-/send-0.19.0.tgz", - "integrity": "sha512-dW41u5VfLXu8SJh5bwRmyYUbAoSB3c9uQh6L8h/KtsFREPWpbX1lrljJo186Jc4nmci/sGUZ9a0a0J2zgfq2hw==", + "node_modules/serve-static": { + "version": "1.16.3", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.16.3.tgz", + "integrity": "sha512-x0RTqQel6g5SY7Lg6ZreMmsOzncHFU7nhnRWkKgWuMTu5NN0DR5oruckMqRvacAN9d5w6ARnRBXl9xhDCgfMeA==", "license": "MIT", "dependencies": { - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "encodeurl": "~1.0.2", + "encodeurl": "~2.0.0", "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "2.4.1", - "range-parser": "~1.2.1", - "statuses": "2.0.1" + "parseurl": "~1.3.3", + "send": "~0.19.1" }, "engines": { "node": ">= 0.8.0" } }, - "node_modules/serve-static/node_modules/send/node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/serve-static/node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/setprototypeof": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", diff --git a/package.json b/package.json index 034ef1b..c15a33d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "netbox-docker-image-upgrade", - "version": "0.8.0", + "version": "0.9.0", "description": "App to deploy new image to all containers", "author": "vincent@saashup.com", "homepage": "https://github.com/SaaShup/netbox-docker-image-upgrade", diff --git a/public/index.html b/public/index.html index c572b5e..814fa44 100644 --- a/public/index.html +++ b/public/index.html @@ -20,6 +20,9 @@
Welcome !
+
+  
+
diff --git a/public/js/main.js b/public/js/main.js index 6a0e0d1..261ecc4 100644 --- a/public/js/main.js +++ b/public/js/main.js @@ -167,15 +167,20 @@ function remove() { } function test() { - fetch(document.getElementById(current + "netbox").value + '/api/plugins/docker/hosts/?name=' + document.getElementById(current + "hostname").value, { - method: 'GET', + fetch('/test', { + method: 'POST', headers: { 'Accept': 'application/json', - 'Authorization': 'Token ' + document.getElementById(current + "token").value - } + }, + body: JSON.stringify({ + "netbox": document.getElementById(current + "netbox").value, + "hostname": document.getElementById(current + "hostname").value, + "token": document.getElementById(current + "token").value + }) }) .then(response => response.json()) .then(data => { + console.log(data); if ('count' in data && data.count == 1) alert("Success"); else alert('Error'); @@ -254,6 +259,19 @@ function change(notif = true) { } } +async function getLogs() { + try { + const response = await fetch("logs?last=true"); + if (!response.ok) { + throw new Error(`HTTP error! status: ${response.status}`); + } + const data = await response.text(); + document.getElementById("logs").innerHTML = data; + } catch (err) { + console.error('Error fetching logs:', err); + } +} + if (select.selectedIndex >= 0) { if (selected != "") { for (const option of select.options) { @@ -264,4 +282,7 @@ if (select.selectedIndex >= 0) { } } change(false); -} \ No newline at end of file +} + +getLogs(); +setInterval(getLogs, 1000); \ No newline at end of file