diff --git a/.dockerignore b/.dockerignore index b68a8a694..d439b2db5 100644 --- a/.dockerignore +++ b/.dockerignore @@ -3,3 +3,11 @@ /node_modules /data/kuma.db /.do +**/.dockerignore +**/.git +**/.gitignore +**/docker-compose* +**/Dockerfile* +LICENSE +README.md +.editorconfig diff --git a/dockerfile b/dockerfile index 923d8b10a..1ebf00999 100644 --- a/dockerfile +++ b/dockerfile @@ -17,11 +17,14 @@ RUN apk add --no-cache --virtual .build-deps make g++ python3 python3-dev && \ # Compilation Fail 3 => Google Search "alpine opensslv.h" => Add openssl-dev # Compilation Fail 4 => Google Search "alpine opensslv.h" again => Change to libressl-dev musl-dev # Compilation Fail 5 => Google Search "ERROR: libressl3.3-libtls-3.3.3-r0: trying to overwrite usr/lib/libtls.so.20 owned by libretls-3.3.3-r0." again => Change back to openssl-dev with musl-dev +# Runtime Error => ModuleNotFoundError: No module named 'six' => pip3 install six +# Runtime Error 2 => ModuleNotFoundError: No module named 'six' => apk add py3-six ENV CRYPTOGRAPHY_DONT_BUILD_RUST=1 -RUN apk add --no-cache python3 -RUN apk add --no-cache --virtual .build-deps libffi-dev musl-dev openssl-dev cargo py3-pip python3-dev && \ +RUN apk add --no-cache python3 py3-pip py3-six cargo +RUN apk add --no-cache --virtual .build-deps libffi-dev musl-dev openssl-dev python3-dev && \ pip3 install apprise && \ apk del .build-deps +RUN apprise --version # New things add here @@ -31,7 +34,7 @@ RUN npm run build EXPOSE 3001 VOLUME ["/app/data"] -HEALTHCHECK --interval=5s --timeout=3s --start-period=30s CMD node extra/healthcheck.js +HEALTHCHECK --interval=60s --timeout=30s --start-period=300s CMD node extra/healthcheck.js CMD ["npm", "run", "start-server"] FROM release AS nightly diff --git a/package-lock.json b/package-lock.json index e7486fc81..5b4f4d4aa 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "uptime-kuma", - "version": "1.0.4", + "version": "1.0.5", "lockfileVersion": 1, "requires": true, "dependencies": { @@ -655,6 +655,11 @@ "delayed-stream": "~1.0.0" } }, + "command-exists": { + "version": "1.2.9", + "resolved": "https://registry.npmjs.org/command-exists/-/command-exists-1.2.9.tgz", + "integrity": "sha512-LTQ/SGc+s0Xc0Fu5WaKnR0YiygZkm9eKFvyS+fRsU7/ZWFF8ykFM6Pc9aCVf1+xasOOZpO3BAVgVrKvsqKHV7w==" + }, "commander": { "version": "6.2.1", "resolved": "https://registry.npmjs.org/commander/-/commander-6.2.1.tgz", diff --git a/package.json b/package.json index 4a0cd42cc..017fe3df4 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,11 @@ { "name": "uptime-kuma", "version": "1.0.5", + "license": "MIT", + "repository": { + "type": "git", + "url": "https://github.com/louislam/uptime-kuma.git" + }, "scripts": { "dev": "vite --host", "start-server": "node server/server.js", @@ -19,6 +24,7 @@ "axios": "^0.21.1", "bcrypt": "^5.0.1", "bootstrap": "^5.0.0", + "command-exists": "^1.2.9", "dayjs": "^1.10.4", "express": "^4.17.1", "form-data": "^4.0.0", diff --git a/server/notification.js b/server/notification.js index e264f7161..ff5298e6e 100644 --- a/server/notification.js +++ b/server/notification.js @@ -2,9 +2,16 @@ const axios = require("axios"); const {R} = require("redbean-node"); const FormData = require('form-data'); const nodemailer = require("nodemailer"); +const child_process = require("child_process"); class Notification { static async send(notification, msg, monitorJSON = null, heartbeatJSON = null) { + + let res = { + ok: true, + msg: "Sent Successfully" + } + if (notification.type === "telegram") { try { await axios.get(`https://api.telegram.org/bot${notification.telegramBotToken}/sendMessage`, { @@ -185,7 +192,7 @@ class Notification { var pushoverlink = 'https://api.pushover.net/1/messages.json' try { if (heartbeatJSON == null) { - let data = {'message': "Uptime Kuma Pushover testing successful.", + let data = {'message': "Uptime Kuma Pushover testing successful.", 'user': notification.pushoveruserkey, 'token': notification.pushoverapptoken, 'sound':notification.pushoversounds, 'priority': notification.pushoverpriority, 'title':notification.pushovertitle, 'retry': "30", 'expire':"3600", 'html': 1} let res = await axios.post(pushoverlink, data) @@ -210,6 +217,10 @@ class Notification { return false; } + } else if (notification.type === "apprise") { + + return Notification.apprise(notification, msg) + } else { throw new Error("Notification type is not supported") } @@ -274,16 +285,26 @@ class Notification { return true; } - static async discord(notification, msg) { - const client = new Discord.Client(); - await client.login(notification.discordToken) + static async apprise(notification, msg) { + let s = child_process.spawnSync("apprise", [ "-vv", "-b", msg, notification.appriseURL]) + let output = s.stdout.toString(); - const channel = await client.channels.fetch(notification.discordChannelID); - await channel.send(msg); + console.log(output) - client.destroy() + if (output) { + return { + ok: ! output.includes("ERROR"), + msg: output + } + } else { + return { } + } + } - return true; + static checkApprise() { + let commandExistsSync = require('command-exists').sync; + let exists = commandExistsSync('apprise'); + return exists; } } diff --git a/server/server.js b/server/server.js index b53f32b49..ee27dc815 100644 --- a/server/server.js +++ b/server/server.js @@ -35,12 +35,15 @@ let needSetup = false; (async () => { await initDatabase(); + console.log("Adding route") app.use('/', express.static("dist")); app.get('*', function(request, response, next) { response.sendFile(process.cwd() + '/dist/index.html'); }); + + console.log("Adding socket handler") io.on('connection', async (socket) => { socket.emit("info", { @@ -437,12 +440,9 @@ let needSetup = false; try { checkLogin(socket) - await Notification.send(notification, notification.name + " Testing") + let res = await Notification.send(notification, notification.name + " Testing") - callback({ - ok: true, - msg: "Sent Successfully" - }); + callback(res); } catch (e) { callback({ @@ -451,11 +451,20 @@ let needSetup = false; }); } }); + + socket.on("checkApprise", async (callback) => { + try { + checkLogin(socket) + callback(Notification.checkApprise()); + } catch (e) { + callback(false); + } + }); }); + console.log("Init") server.listen(port, hostname, () => { console.log(`Listening on ${hostname}:${port}`); - startMonitors(); }); @@ -551,10 +560,11 @@ async function initDatabase() { } console.log("Connecting to Database") - R.setup('sqlite', { filename: path }); + console.log("Connected") + R.freeze(true) await R.autoloadModels("./server/model"); @@ -569,6 +579,7 @@ async function initDatabase() { jwtSecretBean.value = passwordHash.generate(dayjs() + "") await R.store(jwtSecretBean) + console.log("Stored JWT secret into database") } else { console.log("Load JWT secret from database.") } diff --git a/src/components/Login.vue b/src/components/Login.vue index cc5cea576..017261ccd 100644 --- a/src/components/Login.vue +++ b/src/components/Login.vue @@ -15,14 +15,14 @@ -
-