From 8f1404c299d73b1cca1b970ce4f1484d6b0f7445 Mon Sep 17 00:00:00 2001 From: Sergey Yarkov Date: Fri, 3 Nov 2023 09:53:22 +0300 Subject: [PATCH] discrete input and outputs monitor --- data.db | Bin 20480 -> 20480 bytes index.d.ts | 4 ++-- migrations/001-init.sql | 11 +++++++---- public/index.html | 14 +++++++------- services/modbus.service.js | 7 +++++-- utils/number.js | 2 ++ validators/display-value.schema.js | 4 ++-- 7 files changed, 25 insertions(+), 17 deletions(-) diff --git a/data.db b/data.db index 4b0af30dc8b13cb45d3c805575068659ca8c77c1..e469ca15a1829573566e6c0a9a1101d6919a02b6 100644 GIT binary patch delta 522 zcmZozz}T>Wae}nqAqEBpRv?A~Mumww#v+Fp^wM7P0)<#O7#R2?dD6HPI5sx+vU9b_ zvapM5YBIK$PL|_PWMrP~!1143M?uNOQwc=+PqyRCWe2jH{QZ3<=S!DuR^ZBHVr1Fe z#Z%49%G}Su+`qB0m6>lw9wR%0=z75>|IED1lF5Sd0h{|o%Ghw3v^igTE_1yOFBhkV zp#jiz=lr~qqWm0%#N?99{5*w{%7Rp&^~O31AW4wbV8?hWX+pFZ0!4#M5=%;p6&!sW zgM1Akib29~#r`nGMrewSAc~E2_)%3`Po5wWG+9ADVDftTP#GS+?+pBJ`ET=| zn12F)4SxoID8CWEDBt(Zf(qC9;$(Q(8PpjW1x1lvV#Lhk;tz6zG&e|=6IIrb86v63 z#m->N$RQ|-#ox>>p5U+!wO`N1$bW}{{|?Z)Wae}nqRt5$JRv?A~MyZK9#-dvp^wM7P0)<#OL>TxZdD6HPI7BupDlA~< zYT;yI7uVEeZ1d6J2dd2<&}H8U%V0RxM{ z#zr+3zUjV<>p1Dpw)Bc#=tnXP%bCJV~Xo4i&& zoQ;wH1_S?%&4LD}`CWkyQe)s|5LRd6WfEoNWD0Q(Ftjw%Gc>c%Gte_MFlPLw+K`u@ wm&(EX0_1p3{!j+~xBR#HPx5c$U(7#&zlJ}9KNM(`HUH#L{q>t!9RBbF0Dam+Bme*a diff --git a/index.d.ts b/index.d.ts index c114aae..369ca53 100644 --- a/index.d.ts +++ b/index.d.ts @@ -10,8 +10,8 @@ export type AppConfig = { log_interval_ms: number; }; -export type RegisterType = "HR" | "IR" -export type NumberType = 'UI16' | 'I16' | 'UI32' | 'I32' | 'FP32' +export type RegisterType = "HR" | "IR" | "DI" | "DO"; +export type NumberType = 'UI16' | 'I16' | 'UI32' | 'I32' | 'FP32' | 'BOOL'; export type DisplayValue = { data?: number; diff --git a/migrations/001-init.sql b/migrations/001-init.sql index bb9ad93..08f6fa3 100644 --- a/migrations/001-init.sql +++ b/migrations/001-init.sql @@ -34,8 +34,8 @@ CREATE TABLE IF NOT EXISTS "display_values" ( "name" VARCHAR(32) NOT NULL, "slave_id" INTEGER NOT NULL, "reg_addr" INTEGER DEFAULT 0 NOT NULL CHECK(reg_addr >= 0 AND reg_addr <= 65534), - "reg_type" VARCHAR(3) NOT NULL CHECK(reg_type IN("HR", "IR")) DEFAULT "IR", - "reg_format" VARCHAR(5) NOT NULL CHECK(reg_format IN("UI16", "I16", "UI32", "I32", "FP32")) DEFAULT "UI16", + "reg_type" VARCHAR(3) NOT NULL CHECK(reg_type IN("HR", "IR", "DI", "DO")) DEFAULT "IR", + "reg_format" VARCHAR(5) NOT NULL CHECK(reg_format IN("UI16", "I16", "UI32", "I32", "FP32", "BOOL")) DEFAULT "UI16", PRIMARY KEY("id"), FOREIGN KEY("slave_id") REFERENCES modbus_slaves("id") ON DELETE CASCADE ); @@ -48,7 +48,7 @@ CREATE TABLE IF NOT EXISTS "display_values" ( -- -- JSON Format: -- -- { -- -- graph: [{ reg_addr: 1 value: 4 }], --- -- display_values: [{ reg_addr: 1, name: "CV1" }] +-- -- display_values: [{ ... }] -- -- } -- "data" TEXT NOT NULL, -- PRIMARY KEY("id"), @@ -74,7 +74,10 @@ INSERT INTO "display_values" ( (6, "SP", 2, 15, "UI16", "IR"), (7, "CV1", 3, 16, "UI16", "HR"), (8, "CV2", 3, 17, "FP32", "HR"), - (9, "SP", 3, 15, "UI16", "IR"); + (9, "SP", 3, 15, "UI16", "IR"), + (10, "Control action type", 3, 0, "BOOL", "DI"), + (11, "Status ALARM1", 3, 1, "BOOL", "DO"), + (12, "Status ALARM2", 3, 2, "BOOL", "DO"); -------------------------------------------------------------------------------- -- Down -------------------------------------------------------------------------------- diff --git a/public/index.html b/public/index.html index cd81eac..c5bc604 100644 --- a/public/index.html +++ b/public/index.html @@ -287,7 +287,7 @@ +
+ diff --git a/services/modbus.service.js b/services/modbus.service.js index 0799227..9afa17d 100644 --- a/services/modbus.service.js +++ b/services/modbus.service.js @@ -82,7 +82,7 @@ export const modbusService = { /** * @param {number} addr - * @param {"HR" | "IR" | "DI"} type + * @param {import("..").RegisterType} type * @param {import("..").NumberType} format * @return {Promise} buffer data */ @@ -108,7 +108,10 @@ export const modbusService = { data = await modbusClient.readInputRegisters(addr, len); break; case "DI": - data = await modbusClient.readDiscreteInputs(addr, len); + data = await modbusClient.readDiscreteInputs(addr, 1); + break; + case "DO": + data = await modbusClient.readCoils(addr, 1); break; default: throw new Error("Incorrect modbus register type!"); diff --git a/utils/number.js b/utils/number.js index 97484e9..e6829b7 100644 --- a/utils/number.js +++ b/utils/number.js @@ -18,4 +18,6 @@ export function readNumberFromBuf(buf, type, order) { if (type === 'UI32' && order === 'LE') return Buffer.from(buf).readUint32LE(); if (type === 'I32' && order === 'LE') return Buffer.from(buf).readInt32LE(); if (type === 'FP32' && order === 'LE') return Buffer.from(buf).readFloatLE(); + + if (type === 'BOOL') return Buffer.from(buf).readUint8(); } \ No newline at end of file diff --git a/validators/display-value.schema.js b/validators/display-value.schema.js index 3e3259c..e2e13e6 100644 --- a/validators/display-value.schema.js +++ b/validators/display-value.schema.js @@ -5,8 +5,8 @@ export const displayValueSchema = object({ name: string().required(), slave_id: number().required(), reg_addr: number().min(0).max(65534).required(), - reg_format: string().oneOf(["UI16", "I16", "UI32", "I32", "FP32"]).required(), - reg_type: string().oneOf(["HR", "IR"]).required() + reg_format: string().oneOf(["UI16", "I16", "UI32", "I32", "FP32", "BOOL"]).required(), + reg_type: string().oneOf(["HR", "IR", "DI", "DO"]).required() }) export const removeDisplayValueSchema = displayValueSchema.pick(['id']); \ No newline at end of file