From 533fdb5032584c481f3391466496458b5a1c4447 Mon Sep 17 00:00:00 2001 From: Reallag Date: Thu, 12 Oct 2023 20:17:39 +0200 Subject: [PATCH] feat: podpora pro notifikace per user --- server/.env.template | 2 +- server/src/notifikace.ts | 79 ++++++++++++++++++++++++---------------- server/src/utils.ts | 23 +++++++++++- types/Types.ts | 4 ++ 4 files changed, 74 insertions(+), 34 deletions(-) diff --git a/server/.env.template b/server/.env.template index b79ae13..e0e7e77 100644 --- a/server/.env.template +++ b/server/.env.template @@ -24,6 +24,6 @@ # To je užitečné pro odesílání upozornění na různé servery Gotify s různými klíči API. # Struktura dat je ve formátu JSON a je uložena jako řetězec. # GOTIFY_SERVERS_AND_KEYS='[{"server":"https://notification.server.eu", "api_keys":["key1", "key2"]},{"server":"https://notification.server2.eu", "api_keys":["key3", "key4"]}]' -#NTFY_HOST = "http://192.168.0.113:80/topic" +#NTFY_HOST = "http://192.168.0.113:80" #NTFY_USERNAME="username" #NTFY_PASSWD="password" diff --git a/server/src/notifikace.ts b/server/src/notifikace.ts index 25face5..4cf7b14 100644 --- a/server/src/notifikace.ts +++ b/server/src/notifikace.ts @@ -1,10 +1,14 @@ /** Notifikace pro gotify*/ -import {GotifyServer, NotififaceInput, NotifikaceData} from '../../types'; +import {ClientData, GotifyServer, NotififaceInput, NotifikaceData} from '../../types'; import axios, {AxiosError} from 'axios'; import dotenv from 'dotenv'; import path from 'path'; import {log} from "util"; +import {getToday} from "./service"; +import {formatDate, getUsersByLocation} from "./utils"; +import getStorage from "./storage"; +const storage = getStorage(); const ENVIRONMENT = process.env.NODE_ENV || 'production' dotenv.config({path: path.resolve(__dirname, `../.env.${ENVIRONMENT}`)}); @@ -55,40 +59,51 @@ export const ntfyCall = async (data: NotififaceInput) => { const url = process.env.NTFY_HOST const username = process.env.NTFY_USERNAME; const password = process.env.NTFY_PASSWD; - if (url && username && password) { - const token = Buffer.from(`${username}:${password}`, 'utf8').toString('base64'); - console.log(url,username,password) - axios({ - url: url, - method: 'POST', // PUT works too - data: `${data.udalost} - spustil:${data.user}`, - headers: { - 'Authorization': `Basic ${token}`, - 'Tag':'meat_on_bone' - } - }) - .then(response => { - console.log(response.data); - }) - .catch(error => { - console.error(error); - }); - } else { - if (!url) { - console.log("NTFY_HOST není definován v env") - } - if (!username) { - console.log("NTFY_USERNAME není definován v env") - } - if (!password) { - console.log("NTFY_PASSWD není definován v env") - } + if (!url) { + console.log("NTFY_HOST není definován v env") + return } + if (!username) { + console.log("NTFY_USERNAME není definován v env") + return + } + if (!password) { + console.log("NTFY_PASSWD není definován v env") + return + } + const today = formatDate(getToday()); + let clientData: ClientData = await storage.getData(today); + const userByCLocation = getUsersByLocation(clientData.choices, data.user) + + const token = Buffer.from(`${username}:${password}`, 'utf8').toString('base64'); + const promises = userByCLocation.map(async user => { + try { + const response = await axios({ + url: `${url}/${user}`, + method: 'POST', + data: `${data.udalost} - spustil:${data.user}`, + headers: { + 'Authorization': `Basic ${token}`, + 'Tag': 'meat_on_bone' + } + }); + console.log(response.data); + } catch (error) { + console.error(error); + } + }) + + return promises; + } /** Zavolá notifikace na všechny konfigurované způsoby notifikace, přetížení proměných na false pro jednotlivé způsoby je vypne*/ export const callNotifikace = async ({input, teams = true, gotify = false, ntfy = true}: NotifikaceData) => { + const notifications = []; if (ntfy) { - await ntfyCall(input) + const ntfyPromises = await ntfyCall(input); + if (ntfyPromises) { + notifications.push(...ntfyPromises); + } } /* Zatím není if (teams) { @@ -96,8 +111,8 @@ export const callNotifikace = async ({input, teams = true, gotify = false, ntfy }*/ // Add more notifications as necessary - const notifications = []; -//gotify bych řekl, že už je deprecated + + //gotify bych řekl, že už je deprecated if (gotify) { const gotifyPromises = await gotifyCall(input, gotifyData); notifications.push(...gotifyPromises); diff --git a/server/src/utils.ts b/server/src/utils.ts index 1dbd885..9475529 100644 --- a/server/src/utils.ts +++ b/server/src/utils.ts @@ -1,3 +1,5 @@ +import {Choices, groupedUsers} from "../../types"; + /** Vrátí datum v ISO formátu. */ export function formatDate(date: Date) { let currentDay = String(date.getDate()).padStart(2, '0'); @@ -83,4 +85,23 @@ export const checkBodyParams = (req: any, paramNames: string[]) => { // TODO umístit do samostatného souboru -export class InsufficientPermissions extends Error { } \ No newline at end of file +export class InsufficientPermissions extends Error { } + +export const getUsersByLocation=(data: Choices, login: string): string[]=> { + const result: string[] = []; + + for (const location in data) { + if (data.hasOwnProperty(location)) { + if (data[location][login]) { + for (const username in data[location]) { + if (data[location].hasOwnProperty(username)) { + result.push(username); + } + } + break; // Exit the loop early since the login was found + } + } + } + + return result; +} \ No newline at end of file diff --git a/types/Types.ts b/types/Types.ts index 6b36600..38b2e97 100644 --- a/types/Types.ts +++ b/types/Types.ts @@ -156,4 +156,8 @@ export enum FeatureRequest { SAFETY = "Zvýšená ochrana proti chybám uživatele (potvrzovací dialogy, překliky, ...)", UI = "Celkové vylepšení UI/UX", DEVELOPMENT = "Zlepšení dokumentace/postupů pro ostatní vývojáře" +} +export type groupedUsers = { + location: string; + users: string[]; } \ No newline at end of file