add mapper. add v2 handler. add tag description short and full versions. delete topic[1-5]. #5

Merged
APervov merged 5 commits from edge5modbus into main 2026-06-19 06:15:29 +00:00
2 changed files with 7 additions and 18 deletions
Showing only changes of commit 10dbdb2120 - Show all commits

View File

@@ -3,10 +3,9 @@
"private": true, "private": true,
"type": "module", "type": "module",
"scripts": { "scripts": {
"dev": "node --env-file-if-exists=.env ./node_modules/tsx/dist/cli.mjs watch src/index.ts", "dev": "tsx watch --env-file=.env src/index.ts",
NBizyaev marked this conversation as resolved Outdated

флаги указывающие на
--env-file=.env
--env-file-if-exists=.env
просто пробрасываются к node:

"dev": "tsx watch --env-file=.env src/index.ts"
флаги указывающие на `--env-file=.env` `--env-file-if-exists=.env` просто пробрасываются к node: ``` "dev": "tsx watch --env-file=.env src/index.ts" ```
"start": "node --env-file-if-exists=.env ./node_modules/tsx/dist/cli.mjs src/index.ts",
"build": "tsc", "build": "tsc",
NBizyaev marked this conversation as resolved Outdated

Скрипт start тут вообще не нужен.
В продакшне

FROM node:22-alpine
WORKDIR /app
COPY . .
RUN npm install
RUN npm run build         # tsc → dist/
CMD ["node", "dist/index.js"] # скомпилированный код запускается с помощью node

а переменные окружения возьмутся собственно из окружения (например из портейнера)

Скрипт start тут вообще не нужен. В продакшне ``` FROM node:22-alpine WORKDIR /app COPY . . RUN npm install RUN npm run build # tsc → dist/ CMD ["node", "dist/index.js"] # скомпилированный код запускается с помощью node ``` а переменные окружения возьмутся собственно из окружения (например из портейнера)
"typecheck": "tsc --noEmit" "start": "node --env-file=.env dist/index.js"

ну обычно так и оставляют

"scripts": {
  "dev":   "tsx watch --env-file=.env src/index.ts", // запуск во время разработки
  "build": "tsc", // компиляция, сборка в бандл dist
  "start": "node --env-file=.env dist/index.js" // проверка бандла
}
ну обычно так и оставляют ```json "scripts": { "dev": "tsx watch --env-file=.env src/index.ts", // запуск во время разработки "build": "tsc", // компиляция, сборка в бандл dist "start": "node --env-file=.env dist/index.js" // проверка бандла } ```
}, },
"dependencies": { "dependencies": {
"@types/node": "^25.9.1", "@types/node": "^25.9.1",

View File

@@ -1,25 +1,15 @@
const DEFAULT_CLOUD_INGEST_URL = 'http://localhost:3100/ingest' const DEFAULT_CLOUD_INGEST_URL = 'http://localhost:3101/ingest'
Review

Значения по умолчанию для переменных окружения должны быть вынесены в отдельный модуль валидации значений переменных окружения.

Значение переменной CLOUD_INGEST_URL является критическим для такого сервиса как mqtt-ingest, при не указанном значении CLOUD_INGEST_URL сервис не сможет отправлять данные, а значит - выполнять свою функцию, а значит в случае отсутствия значения CLOUD_INGEST_URL - приложение при старте должно ругнуться и не запуститься вовсе, чтобы при деплое на продакшн, это сразу было заметно.

Значения по умолчанию для переменных окружения должны быть вынесены в отдельный модуль валидации значений переменных окружения. Значение переменной CLOUD_INGEST_URL является критическим для такого сервиса как mqtt-ingest, при не указанном значении CLOUD_INGEST_URL сервис не сможет отправлять данные, а значит - выполнять свою функцию, а значит в случае отсутствия значения CLOUD_INGEST_URL - приложение при старте должно ругнуться и не запуститься вовсе, чтобы при деплое на продакшн, это сразу было заметно.
export const cloudIngestUrl = export const cloudIngestUrl =
process.env.CLOUD_INGEST_URL ?? DEFAULT_CLOUD_INGEST_URL process.env.CLOUD_INGEST_URL ?? DEFAULT_CLOUD_INGEST_URL
function getHeaders(): Record<string, string> {
const headers: Record<string, string> = {
'content-type': 'application/json',
}
const apiKey = process.env.CLOUD_INGEST_API_KEY?.trim()
if (apiKey) {
headers['x-api-key'] = apiKey
}
return headers
}
export function postCloudIngest(body: unknown): Promise<Response> { export function postCloudIngest(body: unknown): Promise<Response> {
NBizyaev marked this conversation as resolved
Review

function getHeaders(): Record<string, string> {
return {
'content-type': 'application/json',
'x-api-key': process.env.CLOUD_INGEST_API_KEY
}
}

function getHeaders(): Record<string, string> { return { 'content-type': 'application/json', 'x-api-key': process.env.CLOUD_INGEST_API_KEY } }
return fetch(cloudIngestUrl, { return fetch(cloudIngestUrl, {
method: 'POST', method: 'POST',
headers: getHeaders(), headers: {
'content-type': 'application/json',
'x-api-key': process.env.CLOUD_INGEST_API_KEY as string,
},
body: JSON.stringify(body), body: JSON.stringify(body),
}) })
} }