Merge branch 'default-notification' of https://github.com/Ponkhy/uptime-kuma into default-notification

This commit is contained in:
Ponkhy 2021-09-06 09:46:36 +02:00
commit bb8385d690
21 changed files with 222 additions and 52 deletions

View File

@ -4,6 +4,8 @@ const FormData = require("form-data");
const nodemailer = require("nodemailer"); const nodemailer = require("nodemailer");
const child_process = require("child_process"); const child_process = require("child_process");
const { UP, DOWN } = require("../src/util");
class Notification { class Notification {
/** /**
@ -80,7 +82,7 @@ class Notification {
} }
} else if (notification.type === "smtp") { } else if (notification.type === "smtp") {
return await Notification.smtp(notification, msg) return await Notification.smtp(notification, msg, heartbeatJSON)
} else if (notification.type === "discord") { } else if (notification.type === "discord") {
try { try {
@ -109,7 +111,7 @@ class Notification {
} }
// If heartbeatJSON is not null, we go into the normal alerting loop. // If heartbeatJSON is not null, we go into the normal alerting loop.
if (heartbeatJSON["status"] == 0) { if (heartbeatJSON["status"] == DOWN) {
let discorddowndata = { let discorddowndata = {
username: discordDisplayName, username: discordDisplayName,
embeds: [{ embeds: [{
@ -139,7 +141,7 @@ class Notification {
await axios.post(notification.discordWebhookUrl, discorddowndata) await axios.post(notification.discordWebhookUrl, discorddowndata)
return okMsg; return okMsg;
} else if (heartbeatJSON["status"] == 1) { } else if (heartbeatJSON["status"] == UP) {
let discordupdata = { let discordupdata = {
username: discordDisplayName, username: discordDisplayName,
embeds: [{ embeds: [{
@ -343,7 +345,7 @@ class Notification {
const mattermostIconEmoji = notification.mattermosticonemo; const mattermostIconEmoji = notification.mattermosticonemo;
const mattermostIconUrl = notification.mattermosticonurl; const mattermostIconUrl = notification.mattermosticonurl;
if (heartbeatJSON["status"] == 0) { if (heartbeatJSON["status"] == DOWN) {
let mattermostdowndata = { let mattermostdowndata = {
username: mattermostUserName, username: mattermostUserName,
text: "Uptime Kuma Alert", text: "Uptime Kuma Alert",
@ -387,7 +389,7 @@ class Notification {
mattermostdowndata mattermostdowndata
); );
return okMsg; return okMsg;
} else if (heartbeatJSON["status"] == 1) { } else if (heartbeatJSON["status"] == UP) {
let mattermostupdata = { let mattermostupdata = {
username: mattermostUserName, username: mattermostUserName,
text: "Uptime Kuma Alert", text: "Uptime Kuma Alert",
@ -489,19 +491,19 @@ class Notification {
return okMsg; return okMsg;
} }
if (heartbeatJSON["status"] == 0) { if (heartbeatJSON["status"] == DOWN) {
let downdata = { let downdata = {
"title": "UptimeKuma Alert:" + monitorJSON["name"], "title": "UptimeKuma Alert: " + monitorJSON["name"],
"body": "[🔴 Down]" + heartbeatJSON["msg"] + "\nTime (UTC):" + heartbeatJSON["time"], "body": "[🔴 Down] " + heartbeatJSON["msg"] + "\nTime (UTC): " + heartbeatJSON["time"],
} }
await axios.post(lunaseadevice, downdata) await axios.post(lunaseadevice, downdata)
return okMsg; return okMsg;
} }
if (heartbeatJSON["status"] == 1) { if (heartbeatJSON["status"] == UP) {
let updata = { let updata = {
"title": "UptimeKuma Alert:" + monitorJSON["name"], "title": "UptimeKuma Alert: " + monitorJSON["name"],
"body": "[✅ Up]" + heartbeatJSON["msg"] + "\nTime (UTC):" + heartbeatJSON["time"], "body": "[✅ Up] " + heartbeatJSON["msg"] + "\nTime (UTC): " + heartbeatJSON["time"],
} }
await axios.post(lunaseadevice, updata) await axios.post(lunaseadevice, updata)
return okMsg; return okMsg;
@ -527,18 +529,18 @@ class Notification {
"body": "Testing Successful.", "body": "Testing Successful.",
} }
await axios.post(pushbulletUrl, testdata, config) await axios.post(pushbulletUrl, testdata, config)
} else if (heartbeatJSON["status"] == 0) { } else if (heartbeatJSON["status"] == DOWN) {
let downdata = { let downdata = {
"type": "note", "type": "note",
"title": "UptimeKuma Alert:" + monitorJSON["name"], "title": "UptimeKuma Alert: " + monitorJSON["name"],
"body": "[🔴 Down]" + heartbeatJSON["msg"] + "\nTime (UTC):" + heartbeatJSON["time"], "body": "[🔴 Down] " + heartbeatJSON["msg"] + "\nTime (UTC): " + heartbeatJSON["time"],
} }
await axios.post(pushbulletUrl, downdata, config) await axios.post(pushbulletUrl, downdata, config)
} else if (heartbeatJSON["status"] == 1) { } else if (heartbeatJSON["status"] == UP) {
let updata = { let updata = {
"type": "note", "type": "note",
"title": "UptimeKuma Alert:" + monitorJSON["name"], "title": "UptimeKuma Alert: " + monitorJSON["name"],
"body": "[✅ Up]" + heartbeatJSON["msg"] + "\nTime (UTC):" + heartbeatJSON["time"], "body": "[✅ Up] " + heartbeatJSON["msg"] + "\nTime (UTC): " + heartbeatJSON["time"],
} }
await axios.post(pushbulletUrl, updata, config) await axios.post(pushbulletUrl, updata, config)
} }
@ -566,7 +568,7 @@ class Notification {
] ]
} }
await axios.post(lineAPIUrl, testMessage, config) await axios.post(lineAPIUrl, testMessage, config)
} else if (heartbeatJSON["status"] == 0) { } else if (heartbeatJSON["status"] == DOWN) {
let downMessage = { let downMessage = {
"to": notification.lineUserID, "to": notification.lineUserID,
"messages": [ "messages": [
@ -577,7 +579,7 @@ class Notification {
] ]
} }
await axios.post(lineAPIUrl, downMessage, config) await axios.post(lineAPIUrl, downMessage, config)
} else if (heartbeatJSON["status"] == 1) { } else if (heartbeatJSON["status"] == UP) {
let upMessage = { let upMessage = {
"to": notification.lineUserID, "to": notification.lineUserID,
"messages": [ "messages": [
@ -639,7 +641,7 @@ class Notification {
await R.trash(bean) await R.trash(bean)
} }
static async smtp(notification, msg) { static async smtp(notification, msg, heartbeatJSON = null) {
const config = { const config = {
host: notification.smtpHost, host: notification.smtpHost,
@ -657,12 +659,17 @@ class Notification {
let transporter = nodemailer.createTransport(config); let transporter = nodemailer.createTransport(config);
let bodyTextContent = msg;
if(heartbeatJSON) {
bodyTextContent = `${msg}\nTime (UTC): ${heartbeatJSON["time"]}`;
}
// send mail with defined transport object // send mail with defined transport object
await transporter.sendMail({ await transporter.sendMail({
from: `"Uptime Kuma" <${notification.smtpFrom}>`, from: `"Uptime Kuma" <${notification.smtpFrom}>`,
to: notification.smtpTo, to: notification.smtpTo,
subject: msg, subject: msg,
text: msg, text: bodyTextContent,
}); });
return "Sent Successfully."; return "Sent Successfully.";

View File

@ -31,7 +31,7 @@ export default {
beatWidth: 10, beatWidth: 10,
beatHeight: 30, beatHeight: 30,
hoverScale: 1.5, hoverScale: 1.5,
beatMargin: 3, // Odd number only, even = blurry beatMargin: 4,
move: false, move: false,
maxBeat: -1, maxBeat: -1,
} }
@ -122,11 +122,26 @@ export default {
this.$root.heartbeatList[this.monitorId] = []; this.$root.heartbeatList[this.monitorId] = [];
} }
}, },
mounted() { mounted() {
if (this.size === "small") { if (this.size === "small") {
this.beatWidth = 5.6; this.beatWidth = 5;
this.beatMargin = 2.4; this.beatHeight = 16;
this.beatHeight = 16 this.beatMargin = 2;
}
// Suddenly, have an idea how to handle it universally.
// If the pixel * ratio != Integer, then it causes render issue, round it to solve it!!
const actualWidth = this.beatWidth * window.devicePixelRatio;
const actualMargin = this.beatMargin * window.devicePixelRatio;
if (! Number.isInteger(actualWidth)) {
this.beatWidth = Math.round(actualWidth) / window.devicePixelRatio;
console.log(this.beatWidth);
}
if (! Number.isInteger(actualMargin)) {
this.beatMargin = Math.round(actualMargin) / window.devicePixelRatio;
} }
window.addEventListener("resize", this.resize); window.addEventListener("resize", this.resize);

View File

@ -108,5 +108,6 @@ export default {
"Repeat Password": "Gentag adgangskoden", "Repeat Password": "Gentag adgangskoden",
"Resource Record Type": "Resource Record Type", "Resource Record Type": "Resource Record Type",
respTime: "Resp. Time (ms)", respTime: "Resp. Time (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -112,4 +112,5 @@ export default {
"Default enabled": "Standardmäßig aktiviert", "Default enabled": "Standardmäßig aktiviert",
"Also apply to existing monitors": "Auch für alle existierenden Monitore aktivieren", "Also apply to existing monitors": "Auch für alle existierenden Monitore aktivieren",
enableDefaultNotificationDescription: "Für jeden neuen Monitor wird diese Benachrichtigung standardmäßig aktiviert. Die Benachrichtigung kann weiterhin für jeden Monitor separat deaktiviert werden.", enableDefaultNotificationDescription: "Für jeden neuen Monitor wird diese Benachrichtigung standardmäßig aktiviert. Die Benachrichtigung kann weiterhin für jeden Monitor separat deaktiviert werden.",
Create: "Erstellen",
} }

View File

@ -112,4 +112,5 @@ export default {
notAvailableShort: "N/A", notAvailableShort: "N/A",
"Default enabled": "Default enabled", "Default enabled": "Default enabled",
"Also apply to existing monitors": "Also apply to existing monitors", "Also apply to existing monitors": "Also apply to existing monitors",
Create: "Create",
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Crea tu cuenta de administrador", "Create your admin account": "Crea tu cuenta de administrador",
"Repeat Password": "Repetir contraseña", "Repeat Password": "Repetir contraseña",
respTime: "Tiempo de resp. (ms)", respTime: "Tiempo de resp. (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Créez votre compte administrateur", "Create your admin account": "Créez votre compte administrateur",
"Repeat Password": "Répéter le mot de passe", "Repeat Password": "Répéter le mot de passe",
respTime: "Temps de réponse (ms)", respTime: "Temps de réponse (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Create your admin account", "Create your admin account": "Create your admin account",
"Repeat Password": "Repeat Password", "Repeat Password": "Repeat Password",
respTime: "Resp. Time (ms)", respTime: "Resp. Time (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "관리자 계정 만들기", "Create your admin account": "관리자 계정 만들기",
"Repeat Password": "비밀번호 재입력", "Repeat Password": "비밀번호 재입력",
respTime: "응답 시간 (ms)", respTime: "응답 시간 (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Maak uw beheerdersaccount aan", "Create your admin account": "Maak uw beheerdersaccount aan",
"Repeat Password": "Herhaal wachtwoord", "Repeat Password": "Herhaal wachtwoord",
respTime: "resp. tijd (ms)", respTime: "resp. tijd (ms)",
notAvailableShort: "N.v.t." notAvailableShort: "N.v.t.",
Create: "Create"
} }

113
src/languages/pl.js Normal file
View File

@ -0,0 +1,113 @@
export default {
languageName: "Polski",
checkEverySecond: "sprawdzaj co {0} sekund.",
"Avg.": "Średnia. ",
retriesDescription: "Maksymalna liczba ponownych prób, zanim usługa zostanie oznaczona jako offline i zostanie wysłane powiadomienie.",
ignoreTLSError: "Ignoruj błąd TLS/SSL dla stron HTTPS.",
upsideDownModeDescription: "Odwróć status do góry nogami. Jeśli usługa jest osiągalna, to jest niedostępna.",
maxRedirectDescription: "Maksymalna liczba przekierowań do naśladowania. Ustaw na 0, aby wyłączyć przekierowania.",
acceptedStatusCodesDescription: "Wybierz kody stanu, które są uważane za udaną odpowiedź.",
passwordNotMatchMsg: "Powtórzone hasło nie jest takie samo.",
notificationDescription: "Dodaj powiadomienie do monitorów, aby one działały.",
keywordDescription: "Wyszukaj słowo kluczowe w html lub JSON i wielkość liter ma znaczenie.",
pauseDashboardHome: "pauza",
deleteMonitorMsg: "Czy na pewno chcesz usunąć ten monitor?",
deleteNotificationMsg: "Czy na pewno chcesz usunąć to powiadomienie ze wszystkich monitorów?",
resoverserverDescription: "Cloudflare jest domyślnym serwerem, możesz zmienić serwer resolver w dowolnym momencie.",
rrtypeDescription: "Wybierz typ RR-Type który chcesz monitorować.",
pauseMonitorMsg: "Czy na pewno chcesz wstrzymać?",
Settings: "Ustawienia",
Dashboard: "Panel",
"New Update": "Nowa aktualizacja",
Language: "Język",
Appearance: "Wygląd",
Theme: "Motyw",
General: "Ogólne",
Version: "Versja",
"Check Update On GitHub": "Sprawdź aktualizację na GitHub.",
List: "Lista",
Add: "Dodaj",
"Add New Monitor": "Dodaj Nowy Monitor",
"Quick Stats": "Szybkie statystyki",
Up: "Online",
Down: "Offline",
Pending: "Oczekujący",
Unknown: "Nieznane",
Pause: "Pauza",
Name: "Nazwa",
Status: "Status",
DateTime: "Data i godzina",
Message: "Wiadomość",
"No important events": "Brak ważnych wydarzeń.",
Resume: "Wznów",
Edit: "Edytuj",
Delete: "Usuń",
Current: "aktualny",
Uptime: "czas pracy",
"Cert Exp.": "Wygaśnięcie certyfikatu.",
days: "dni",
day: "dzień",
"-day": "-dzień",
hour: "godzina",
"-hour": "-godzina",
Response: "odpowiedź",
Ping: "Ping",
"Monitor Type": "Typ monitora",
Keyword: "słowo kluczowe",
"Friendly Name": "Przyjazne imię",
URL: "URL",
Hostname: "Hostname",
Port: "Port",
"Heartbeat Interval": "Interwał bicia serca",
Retries: "Prób",
Advanced: "Zaawansowane",
"Upside Down Mode": "Tryb do góry nogami",
"Max. Redirects": "Maks. Przekierowania",
"Accepted Status Codes": "Akceptowane kody statusu",
Save: "Zapisz",
Notifications: "Powiadomienia",
"Not available, please setup.": "Niedostępne, proszę skonfigurować.",
"Setup Notification": "Powiadomienie konfiguracji",
Light: "Jasny",
Dark: "Ciemny",
Auto: "Automatyczny",
"Theme - Heartbeat Bar": "Motyw - pasek bicia serca",
Normal: "Normalne",
Bottom: "Na dole",
None: "Nic",
Timezone: "Strefa czasowa",
"Search Engine Visibility": "Widoczność w wyszukiwarce",
"Allow indexing": "Zezwól na indeksowanie",
"Discourage search engines from indexing site": "Zniechęcaj wyszukiwarki do indeksowania strony",
"Change Password": "Zmień hasło",
"Current Password": "Aktualne hasło",
"New Password": "Nowe hasło",
"Repeat New Password": "Powtórz nowe hasło",
"Update Password": "Zaktualizuj hasło",
"Disable Auth": "Wyłącz autoryzację",
"Enable Auth": "Włącz autoryzację ",
Logout: "Wyloguj się",
Leave: "Opuść",
"I understand, please disable": "Rozumiem, proszę wyłączyć",
Confirm: "Potwierdź",
Yes: "Tak",
No: "Nie",
Username: "Nazwa użytkownika",
Password: "Hasło",
"Remember me": "Zapamiętaj mnie",
Login: "Zaloguj sie",
"No Monitors, please": "Proszę bez monitorów",
"add one": "dodaj jeden",
"Notification Type": "Typ powiadomienia",
Email: "Email",
Test: "Test",
"Certificate Info": "Informacje o certyfikacie",
"Resolver Server": "Server resolver",
"Resource Record Type": "Typ rekordu zasobów",
"Last Result": "Ostatni rekord",
"Create your admin account": "Utwórz swoje konto administratora",
"Repeat Password": "Powtórz hasło",
respTime: "Odp. Czas (ms)",
notAvailableShort: "N/A",
Create: "Create"
}

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Создайте аккаунт администратора", "Create your admin account": "Создайте аккаунт администратора",
"Repeat Password": "Повторите пароль", "Repeat Password": "Повторите пароль",
respTime: "Resp. Time (ms)", respTime: "Resp. Time (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Naprivi administratorski nalog", "Create your admin account": "Naprivi administratorski nalog",
"Repeat Password": "Ponovite lozinku", "Repeat Password": "Ponovite lozinku",
respTime: "Vreme odg. (ms)", respTime: "Vreme odg. (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "Наприви администраторски налог", "Create your admin account": "Наприви администраторски налог",
"Repeat Password": "Поновите лозинку", "Repeat Password": "Поновите лозинку",
respTime: "Време одг. (мс)", respTime: "Време одг. (мс)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -1,14 +1,14 @@
export default { export default {
languageName: "Swedish", languageName: "Svenska",
checkEverySecond: "Uppdatera var {0} sekund.", checkEverySecond: "Uppdatera var {0} sekund.",
"Avg.": "Genomsnitt ", "Avg.": "Genomsnittligt ",
retriesDescription: "Max antal försök innan tjänsten markeras som nere och en notis skickas", retriesDescription: "Max antal försök innan tjänsten markeras som nere och en notis skickas",
ignoreTLSError: "Ignorera TLS/SSL-fel för webbsidor med HTTPS", ignoreTLSError: "Ignorera TLS/SSL-fel för webbsidor med HTTPS",
upsideDownModeDescription: "Vänd upp och ner på statusen. Om tjänsten är nåbar visas den som NERE.", upsideDownModeDescription: "Vänd upp och ner på statusen. Om tjänsten är nåbar visas den som NERE.",
maxRedirectDescription: "Max antal omdirigeringar att följa. Välj 0 för att avaktivera omdirigeringar.", maxRedirectDescription: "Max antal omdirigeringar att följa. Välj 0 för att avaktivera omdirigeringar.",
acceptedStatusCodesDescription: "Välj statuskoder som räknas som lyckade.", acceptedStatusCodesDescription: "Välj statuskoder som räknas som lyckade.",
passwordNotMatchMsg: "Det bekräftade lösenordet stämmer ej överens.", passwordNotMatchMsg: "Det bekräftade lösenordet stämmer ej överens.",
notificationDescription: "Vänligen lägg till en notistjänst till övervakaren.", notificationDescription: "Vänligen lägg till en notistjänst till dina övervakare.",
keywordDescription: "Sök efter nyckelord i ren HTML eller JSON-svar. Sökningen är skiftkänslig.", keywordDescription: "Sök efter nyckelord i ren HTML eller JSON-svar. Sökningen är skiftkänslig.",
pauseDashboardHome: "Pausa", pauseDashboardHome: "Pausa",
deleteMonitorMsg: "Är du säker på att du vill ta bort den här övervakningen?", deleteMonitorMsg: "Är du säker på att du vill ta bort den här övervakningen?",
@ -33,10 +33,10 @@ export default {
Down: "Nere", Down: "Nere",
Pending: "Pågående", Pending: "Pågående",
Unknown: "Okänt", Unknown: "Okänt",
Pause: "Paus", Pause: "Pausa",
Name: "Namn", Name: "Namn",
Status: "Status", Status: "Status",
DateTime: "DatumTid", DateTime: "Datum & Tid",
Message: "Meddelande", Message: "Meddelande",
"No important events": "Inga viktiga händelser", "No important events": "Inga viktiga händelser",
Resume: "Återuppta", Resume: "Återuppta",
@ -44,17 +44,17 @@ export default {
Delete: "Ta bort", Delete: "Ta bort",
Current: "Nuvarande", Current: "Nuvarande",
Uptime: "Drifttid", Uptime: "Drifttid",
"Cert Exp.": "Certifikatsutgång", "Cert Exp.": "Certifikat utgår",
days: "dagar", days: "dagar",
day: "dag", day: "dag",
"-day": "-dag", "-day": " dagar",
hour: "timme", hour: "timme",
"-hour": "-timme", "-hour": " timmar",
Response: "Svar", Response: "Svar",
Ping: "Ping", Ping: "Ping",
"Monitor Type": "Övervakningstyp", "Monitor Type": "Övervakningstyp",
Keyword: "Nyckelord", Keyword: "Nyckelord",
"Friendly Name": "Vänligt Namn", "Friendly Name": "Namn",
URL: "URL", URL: "URL",
Hostname: "Värdnamn", Hostname: "Värdnamn",
Port: "Port", Port: "Port",
@ -67,14 +67,14 @@ export default {
Save: "Spara", Save: "Spara",
Notifications: "Notiser", Notifications: "Notiser",
"Not available, please setup.": "Ej tillgänglig, vänligen konfigurera.", "Not available, please setup.": "Ej tillgänglig, vänligen konfigurera.",
"Setup Notification": "Konfigurera Notis", "Setup Notification": "Ny Notistjänst",
Light: "Ljust", Light: "Ljust",
Dark: "Mörkt", Dark: "Mörkt",
Auto: "Automatisk", Auto: "Automatiskt",
"Theme - Heartbeat Bar": "Tema - Heartbeat Bar", "Theme - Heartbeat Bar": "Tema - Heartbeat Bar",
Normal: "Normal", Normal: "Normal",
Bottom: "Botten", Bottom: "Botten",
None: "Ingen", None: "Tomt",
Timezone: "Tidszon", Timezone: "Tidszon",
"Search Engine Visibility": "Synlighet på Sökmotorer", "Search Engine Visibility": "Synlighet på Sökmotorer",
"Allow indexing": "Tillåt indexering", "Allow indexing": "Tillåt indexering",
@ -107,6 +107,7 @@ export default {
"Last Result": "Senaste resultat", "Last Result": "Senaste resultat",
"Create your admin account": "Skapa ditt administratörskonto", "Create your admin account": "Skapa ditt administratörskonto",
"Repeat Password": "Upprepa Lösenord", "Repeat Password": "Upprepa Lösenord",
respTime: "Resp. Time (ms)", respTime: "Svarstid (ms)",
notAvailableShort: "N/A" notAvailableShort: "Ej Tillg.",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "创建管理员账号", "Create your admin account": "创建管理员账号",
"Repeat Password": "重复密码", "Repeat Password": "重复密码",
respTime: "Resp. Time (ms)", respTime: "Resp. Time (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "Create"
} }

View File

@ -108,5 +108,6 @@ export default {
"Create your admin account": "製作你的管理員帳號", "Create your admin account": "製作你的管理員帳號",
"Repeat Password": "重複密碼", "Repeat Password": "重複密碼",
respTime: "反應時間 (ms)", respTime: "反應時間 (ms)",
notAvailableShort: "N/A" notAvailableShort: "N/A",
Create: "建立"
} }

View File

@ -37,6 +37,7 @@ import svSE from "./languages/sv-SE";
import koKR from "./languages/ko-KR"; import koKR from "./languages/ko-KR";
import ruRU from "./languages/ru-RU"; import ruRU from "./languages/ru-RU";
import zhCN from "./languages/zh-CN"; import zhCN from "./languages/zh-CN";
import pl from "./languages/pl"
const routes = [ const routes = [
{ {
@ -114,6 +115,7 @@ const languageList = {
"ko-KR": koKR, "ko-KR": koKR,
"ru-RU": ruRU, "ru-RU": ruRU,
"zh-CN": zhCN, "zh-CN": zhCN,
"pl": pl,
}; };
const i18n = createI18n({ const i18n = createI18n({

View File

@ -11,7 +11,7 @@ export default {
mounted() { mounted() {
// Default Light // Default Light
if (! this.userTheme) { if (! this.userTheme) {
this.userTheme = "light"; this.userTheme = "auto";
} }
// Default Heartbeat Bar // Default Heartbeat Bar

View File

@ -213,6 +213,11 @@
<p> 기능은 <strong>Cloudflare Access와 같은 서드파티 인증</strong> Uptime Kuma 앞에 사용자를 위한 기능이에요.</p> <p> 기능은 <strong>Cloudflare Access와 같은 서드파티 인증</strong> Uptime Kuma 앞에 사용자를 위한 기능이에요.</p>
<p>신중하게 사용하세요.</p> <p>신중하게 사용하세요.</p>
</template> </template>
<template v-if="$i18n.locale === 'pl' ">
<p>Czy na pewno chcesz <strong>wyłączyć autoryzację</strong>?</p>
<p>Jest przeznaczony dla <strong>kogoś, kto ma autoryzację zewnętrzną</strong> przed Uptime Kuma, taką jak Cloudflare Access.</p>
<p>Proszę używać ostrożnie.</p>
</template>
</Confirm> </Confirm>
</div> </div>
</transition> </transition>

View File

@ -14,6 +14,15 @@
</p> </p>
<div class="form-floating"> <div class="form-floating">
<select id="language" v-model="$i18n.locale" class="form-select">
<option v-for="(lang, i) in $i18n.availableLocales" :key="`Lang${i}`" :value="lang">
{{ $i18n.messages[lang].languageName }}
</option>
</select>
<label for="language" class="form-label">{{ $t("Language") }}</label>
</div>
<div class="form-floating mt-3">
<input id="floatingInput" v-model="username" type="text" class="form-control" placeholder="Username" required> <input id="floatingInput" v-model="username" type="text" class="form-control" placeholder="Username" required>
<label for="floatingInput">{{ $t("Username") }}</label> <label for="floatingInput">{{ $t("Username") }}</label>
</div> </div>
@ -29,7 +38,7 @@
</div> </div>
<button class="w-100 btn btn-primary mt-3" type="submit" :disabled="processing"> <button class="w-100 btn btn-primary mt-3" type="submit" :disabled="processing">
Create {{ $t("Create") }}
</button> </button>
</form> </form>
</div> </div>
@ -49,6 +58,11 @@ export default {
repeatPassword: "", repeatPassword: "",
} }
}, },
watch: {
"$i18n.locale"() {
localStorage.locale = this.$i18n.locale;
},
},
mounted() { mounted() {
this.$root.getSocket().emit("needSetup", (needSetup) => { this.$root.getSocket().emit("needSetup", (needSetup) => {
if (! needSetup) { if (! needSetup) {