{"id":25633828,"url":"https://github.com/jledun/io-buffer-worker","last_synced_at":"2025-02-22T22:32:58.399Z","repository":{"id":57275602,"uuid":"173307479","full_name":"jledun/io-buffer-worker","owner":"jledun","description":"A node.js buffer encoder / decoder for PLC data communication","archived":false,"fork":false,"pushed_at":"2019-03-04T17:33:39.000Z","size":12,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-02-13T09:03:52.421Z","etag":null,"topics":["buffer","encoder-decoder","industrial-automation","modbus","plc","protocol-buffers","s7"],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jledun.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2019-03-01T13:35:00.000Z","updated_at":"2019-03-06T08:04:20.000Z","dependencies_parsed_at":"2022-09-15T19:12:49.455Z","dependency_job_id":null,"html_url":"https://github.com/jledun/io-buffer-worker","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jledun%2Fio-buffer-worker","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jledun%2Fio-buffer-worker/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jledun%2Fio-buffer-worker/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jledun%2Fio-buffer-worker/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jledun","download_url":"https://codeload.github.com/jledun/io-buffer-worker/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":240245901,"owners_count":19771028,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["buffer","encoder-decoder","industrial-automation","modbus","plc","protocol-buffers","s7"],"created_at":"2025-02-22T22:32:41.341Z","updated_at":"2025-02-22T22:32:58.387Z","avatar_url":"https://github.com/jledun.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# io-buffer-worker\nA node.js buffer encoder / decoder for PLC data communication.\n\nThis project is aimed to provide basic conversion from buffer to javascript object or from javascript object to buffer based on a json description file.\n\nThe data profile must always reflect the data table defined in the PLC.\n\nYou're free to create the needed javascript object structure you need.\n\nI've built this library because it's not easy to define string length and boolean doesn't exist in Google's protocol buffer.\n\n# Install\n\n```bash\n$ npm install io-buffer-worker\n```\n\n# Use\n\n```javascript\nconst BufferWorker = require('io-buffer-worker');\n\nconst options = {\n  endianess: 'LE' // default value: BE\n}\n\n// encode\nBufferWorker.encode('path/to/json/description/file.json', dataToEncode, options).then(\n  data =\u003e console.log(data)\n).catch(\n  err =\u003e console.log(err)\n);\n\n// decode\nBufferWorker.decode('path/to/json/description/file.json', bufferToDecode, options).then(\n  data =\u003e console.log(data)\n).catch(\n  err =\u003e console.log(err)\n);\n```\n\n# API\n\n## BufferWorker.encode\n\n**Params :**\n\n* buffer and object description file : (string|array) **required**\n\npath to file or object description array\n\n* dataToEncode : (object) **required**\n\nThe content you want to encode.\n\n* options : (object) not mandatory\n\nSee Options\n\n**Returns :**\n\na promise with a Node.js Buffer as parameter.\n\n## BufferWorker.decode\n\n**Params :**\n\n* buffer and object description file : (string|array) **required**\n\npath to file or object description array\n\n* bufferToDecode : (Buffer) **required**\n\nThe buffer you want to decode into a formatted object.\n\n* options : (object) not mandatory\n\nSee Options\n\n**Returns :**\n\na promise with a result object as parameter.\n\n## Promises\n\nBecause `encode` and `decode` functions return promise, it can be used with async / await.\n\n## Buffer and Object description file param\n\nThe `path/to/json/description/file.json` can be absolue or relative.\n\nBoth `encode` and `decode` accept the content of the file as parameter instead of a path, for example :\n\n```javascript\nBufferWorker.decode(require('path/to/json/description/file.json'), bufferToDecode, options)\n```\n\nThe description file can then be generated by program at runtime.\n\n## Options\n\n* endianness : \"BE\" for Big Endian, \"LE\" for Little Endian\n\n# Define buffer fields \n\nAll length numbers is a count of bytes (8 bits) to stay close to the PLC data types, 'cos we're stick to low level programming ;-)\n\n## General representation of a field\n\n```json\n{\n  \"name\": \"(string) your custom object property name\",\n  \"type\": \"(string) the PLC data type\",\n  \"default\": \"defaut value if object property is not defined before encoding\",\n  \"offset\": \"(unsigned integer) the first byte position number\",\n  \"bitnumber\": \"(unsigned integer between 0 and 15) required for 'BOOL' only : the bit position in the byte read at offset\",\n  \"length\": \"(unsigned integer) required for 'STRING' and 'ARRAY OF ...' only : length of the string or char array\",\n  \"properties\": \"(array of properties) required to define an object\",\n  \"array\": \"(array of array of properties) required to define an array of objects\"\n}\n```\n\n## PLC Data types\n\n* BOOL (2 bytes + bit number parameter, from 0 to 15)\n* BYTE (1 byte length)\n* INT/UINT/WORD (2 bytes length)\n* DINT/UDINT/DWORD (4 bytes length)\n* REAL (4 bytes length)\n* CHAR (1 byte length)\n* ARRAY OF [BOOL | INT | UINT | DINT | UDINT | WORD | DWORD | REAL | CHAR] (`length` bytes as a parameter)\n* STRING (`length` bytes as a parameter, an alias for ARRAY OF CHAR)\n* S7STRING (`maxlength` and `length` are set by PLC, Siemens typed string with maximum length et real length in the first two bytes)\n\n**S7STRING format :**\n\n```javascript\n{\n  maxlength: 16, // Integer\n  length: 8,     // Integer\n  value: \"value\" // String\n}\n```\n\n\n## BOOL\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"BOOL\",\n  \"default\": false,\n  \"offset\": 32,\n  \"bitnumber\": 4\n}\n```\n\n## INT\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"INT\",\n  \"default\": 0,\n  \"offset\": 6\n}\n```\n\n## UINT\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"UINT\",\n  \"default\": 0,\n  \"offset\": 2\n}\n```\n\n## WORD\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"WORD\",\n  \"default\": 0,\n  \"offset\": 8\n}\n```\n\n## DINT\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"DINT\",\n  \"default\": 0,\n  \"offset\": 10\n}\n```\n\n## UDINT\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"UDINT\",\n  \"default\": 0,\n  \"offset\": 56\n}\n```\n\n## DWORD\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"DWORD\",\n  \"default\": 0,\n  \"offset\": 32\n}\n```\n\n## REAL\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"REAL\",\n  \"default\": 0,\n  \"offset\": 26\n}\n```\n\n## CHAR\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"CHAR\",\n  \"default\": \"\",\n  \"offset\": 4\n}\n```\n\n## ARRAY OF [BOOL|INT|UINT|WORD|DINT|UDINT|DWORD|REAL|BYTE|CHAR]\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"ARRAY OF [BOOL|INT|UINT|WORD|DINT|UDINT|DWORD|REAL|BYTE|CHAR]\",\n  \"default\": false,\n  \"offset\": 32,\n  \"length\": 64\n}\n```\n\n## STRING[32]\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"STRING\",\n  \"default\": \"\",\n  \"offset\": 4,\n  \"length\": 32\n}\n```\n\n## S7STRING\n\n```json\n{\n  \"name\": \"fieldName\",\n  \"type\": \"S7STRING\",\n  \"default\": \"\",\n  \"offset\": 4,\n}\n```\n\n# Object structure\n\nThe json description file has to reflect the source / result javascript object structure from buffer byte #0 to buffer max length.\n\n**The json description file is an array of objects.**\n\nAn object can have `properties` to generate sub-object.\n\nAn object can have `array` property to generate array of objects.\n\n## Basic example\n\n```json\n[\n  {\n    \"name\": \"fieldName1\",\n    \"type\": \"INT\",\n    \"default\": 0,\n    \"offset\": 0\n  }, {\n    \"name\": \"fieldName2\",\n    \"properties\": [\n      {\n        \"name\": \"objectPropertyName1\",\n        \"type\": \"BOOL\",\n        \"default\": false,\n        \"offset\": 2,\n        \"bitnumber\": 0\n      }, {\n        \"name\": \"objectPropertyName2\",\n        \"type\": \"BOOL\",\n        \"default\": false,\n        \"offset\": 2,\n        \"bitnumber\": 3\n      }\n    ]\n  }, {\n    \"name\": \"fieldName3\",\n    \"array\": [\n      [\n        {\n          \"name\": \"objectPropertyName3\",\n          \"type\": \"BOOL\",\n          \"default\": false,\n          \"offset\": 4,\n          \"bitnumber\": 0\n        }, {\n          \"name\": \"objectPropertyName4\",\n          \"type\": \"BOOL\",\n          \"default\": false,\n          \"offset\": 4,\n          \"bitnumber\": 1\n        }\n      ], [\n        {\n          \"name\": \"objectPropertyName3\",\n          \"type\": \"BOOL\",\n          \"default\": false,\n          \"offset\": 4,\n          \"bitnumber\": 2\n        }, {\n          \"name\": \"objectPropertyName4\",\n          \"type\": \"BOOL\",\n          \"default\": false,\n          \"offset\": 4,\n          \"bitnumber\": 3\n        }\n      ]\n    ]\n  }, {\n    \"name\": \"fieldName2\",\n    \"properties\": [\n      {\n        \"name\": \"objectPropertyName5\",\n        \"type\": \"STRING\",\n        \"default\": false,\n        \"offset\": 6,\n        \"length\": 16\n      }, {\n        \"name\": \"objectPropertyName6\",\n        \"type\": \"REAL\",\n        \"default\": false,\n        \"offset\": 22\n      }\n    ]\n  }, {\n    \"name\": \"fieldName3\",\n    \"type\": \"ARRAY OF UINT\",\n    \"default\": 0,\n    \"offset\": 26,\n    \"length\": 12\n  }\n]\n```\n\nThe example above will result in, the values are just example of what you could have in your PLC :\n\n```json\n{\n  fieldName1: 32,\n  fieldName2: {\n    objectPropertyName1: false,\n    objectPropertyName2: true,\n    objectPropertyName5: \"00001254\",\n    objectPropertyName6: 56.37\n  },\n  fieldName3: [\n    {\n      objectPropertyName3: false,\n      objectPropertyName4: true\n    }, {\n      objectPropertyName3: true,\n      objectPropertyName4: false\n    }\n  ],\n  fieldName4: [\n    32,\n    3424,\n    7654,\n    0,\n    0,\n    0,\n    0,\n    0,\n    0,\n    7,\n    0,\n    0\n  ]\n}\n```\n\n# Contributing\n\nPlease, open an issue or a pull request.\n\nFor your code contributions, please, keep in mind to stay as simple as possible and use functional programming as much as possible.\n\nAll async function must return a promise, callbacks are not allowed.\n\nAll errors must throw an error exception with locatable and unique message.\n\nFeel free to format your code or mine with documentation in english language.\n\nBecause I learn javascript by myself and english is not my native language, there's surely a lack in documentation or spelling / grammar errors. Please, don't blame me and feel free to fix ;-)\n\nYou'll find some commits for backup in the history : git is for versionning but it's also my backup tool, some commits may not be usefull but, by the way, that's how I work.\n\n# TODO\n\n* create a TODO list\n\n# Contributors\n\n* Julien Ledun \u003cj.ledun@iosystems.fr\u003e\n\nEnjoy!\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjledun%2Fio-buffer-worker","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjledun%2Fio-buffer-worker","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjledun%2Fio-buffer-worker/lists"}