Skip to content

Commit

Permalink
THELMABIOTEL-TBLIVE-NODERED: Add logic for future component with rece…
Browse files Browse the repository at this point in the history
…iver logic like discard frames
  • Loading branch information
crisconru committed Jul 5, 2024
1 parent 83d0899 commit a00f7d0
Show file tree
Hide file tree
Showing 2 changed files with 324 additions and 0 deletions.
226 changes: 226 additions & 0 deletions packages/thelmabiotel-tblive-nodered/src/receiver.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,226 @@
<!-- Definition -->
<script type="text/javascript">
const checkSerialNumber = (/** @type string */ sn) => {
const num = Number(sn)
if (!Number.isInteger(num)) return false
return !(sn.length < 6 || 7 < sn.length)
}

const checkFrequency = (freq) => {
if (Number.isNaN(freq)) return false
if (!Number.isInteger(freq)) return false
return (63 <= freq && freq <= 77)
}

RED.nodes.registerType("cma-thelmabiotel-tblive", {
// Category
category: "CoreMarine",
// UI
color: "#ccc4b0",
icon: "cma-logo-blue.png",
label: function () {
const { name, firmware } = this;
return `TB-Live ${firmware}`;
},
paletteLabel: "TB-Live parser",
labelStyle: function () { return this.name ? "node_label_italic" : "" },
align: "left", // 'right'
// button: {
// // toggle: "buttonState",
// enabled: function() {
// return !this.changed
// },
// visible: function() {
// return this.hasButton
// },
// onclick: function() {}
// },
// Input - Outputs
inputs: 1,
outputs: 1,
inputLabels: "TB-Live data",
outputLabels: "Parsed data",
// Logic
defaults: {
name: { value: "" },
firmware: {
value: "1.0.1",
required: true,
},
// Receiver
receiverRequired: {
value: false,
required: true
},
receiverSerialNumber: {
value: "1234567",
required: false,
validate: checkSerialNumber,
},
receiverFrequency: {
value: 69,
required: false,
validate: checkFrequency
},
// Emitter 1
emitter1Required: {
value: false,
required: true
},
emitter1SerialNumber: {
value: "1234567",
required: false,
validate: checkSerialNumber,
},
emitter1Frequency: {
value: 69,
required: false,
validate: checkFrequency,
},
// Emitter 2
emitter2Required: {
value: false,
required: true
},
emitter2SerialNumber: {
value: "1234567",
required: false,
validate: checkSerialNumber,
},
emitter2Frequency: {
value: 69,
required: false,
validate: checkFrequency,
},
// Emitter 3
emitter3Required: {
value: false,
required: true
},
emitter3SerialNumber: {
value: "1234567",
required: false,
validate: checkSerialNumber,
},
emitter3Frequency: {
value: 69,
required: false,
validate: checkFrequency,
},
},
// credentials: {},
oneditprepare: function() {
$("#node-input-firmware").typedInput({
types: [
{
value: "1.0.1",
options: ["1.0.1", "1.0.2"]
}
]
})
},
// oneditsave: function() {},
// oneditcancel: function() {},
// oneditdelete: function() {},
// oneditresize: function() {},
// onpaletteadd: function() {},
// onpaletteremove: function() {},
});
</script>

<!-- Edit dialog -->
<script type="text/html" data-template-name= "cma-thelmabiotel-tblive">
<!-- Name -->
<div class="form-row">
<label for="node-input-name"><i class="fa fa-tag"></i> Name</label>
<input type="text" id="node-input-name" placeholder="TB-Live parser" />
</div>
<!-- Firmware -->
<div class="form-row">
<label for="node-input-firmware"><i class="fa fa-tag"></i> Firmware</label>
<input type="text" id="node-input-firmware" checked/>
</div>
<!-- RECEIVER -->
<!-- Receiver Required -->
<div class="form-row">
<label for="node-input-receiverRequired"><i class="fa fa-tag"></i> Receiver</label>
<input type="checkbox" id="node-input-receiverRequired">
</div>
<!-- Receiver Serial Number -->
<div class="form-row">
<label for="node-input-receiverSerialNumber"><i class="fa fa-tag"></i> Receiver SerialNumber</label>
<input type="text" id="node-input-receiverSerialNumber" placeholder="1234567" />
</div>
<!-- Receiver Frequency -->
<div class="form-row">
<label for="node-input-receiverFrequency"><i class="fa fa-tag"></i> Receiver Frequency</label>
<input type="number" id="node-input-receiverFrequency" placeholder="69" />
</div>
<!-- EMITTER 1 -->
<!-- Emitter 1 Required -->
<div class="form-row">
<label for="node-input-emitter1Required"><i class="fa fa-tag"></i> Emitter 1</label>
<input type="checkbox" id="node-input-emitter1Required">
</div>
<!-- Emitter 1 Serial Number -->
<div class="form-row">
<label for="node-input-emitter1SerialNumber"><i class="fa fa-tag"></i> Emitter 1 SerialNumber</label>
<input type="text" id="node-input-emitter1SerialNumber" placeholder="1234567" />
</div>
<!-- Emitter 1 Frequency -->
<div class="form-row">
<label for="node-input-emitter1Frequency"><i class="fa fa-tag"></i> Emitter 1 Frequency</label>
<input type="number" id="node-input-emitter1Frequency" placeholder="69" />
</div>
<!-- EMITTER 2 -->
<!-- Emitter 2 Required -->
<div class="form-row">
<label for="node-input-emitter2Required"><i class="fa fa-tag"></i> Emitter 2</label>
<input type="checkbox" id="node-input-emitter2Required">
</div>
<!-- Emitter 2 Serial Number -->
<div class="form-row">
<label for="node-input-emitter2SerialNumber"><i class="fa fa-tag"></i> Emitter 2 SerialNumber</label>
<input type="text" id="node-input-emitter2SerialNumber" placeholder="1234567" />
</div>
<!-- Emitter 2 Frequency -->
<div class="form-row">
<label for="node-input-emitter2Frequency"><i class="fa fa-tag"></i> Emitter 2 Frequency</label>
<input type="number" id="node-input-emitter2Frequency" placeholder="69" />
</div>
<!-- EMITTER 3 -->
<!-- Emitter 3 Required -->
<div class="form-row">
<label for="node-input-emitter3Required"><i class="fa fa-tag"></i> Emitter 3</label>
<input type="checkbox" id="node-input-emitter3Required">
</div>
<!-- Emitter 3 Serial Number -->
<div class="form-row">
<label for="node-input-emitter3SerialNumber"><i class="fa fa-tag"></i> Emitter 3 SerialNumber</label>
<input type="text" id="node-input-emitter3SerialNumber" placeholder="1234567" />
</div>
<!-- Emitter 3 Frequency -->
<div class="form-row">
<label for="node-input-emitter3Frequency"><i class="fa fa-tag"></i> Emitter 3 Frequency</label>
<input type="number" id="node-input-emitter3Frequency" placeholder="69" />
</div>
</script>

<!-- Help text -->
<script type="text/markdown" data-help-name= "cma-thelmabiotel-tblive">
Parser of TB-Live propietary protocol sentences [check @coremarine/thelmabiotel-tblive package docs](https://www.npmjs.com/package/@coremarine/thelmabiotel-tblive)

### Input

TODO

### Output

TODO

### Details

TODO

</script>

98 changes: 98 additions & 0 deletions packages/thelmabiotel-tblive-nodered/src/receiver.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
const v = require('valibot')
const { TBLive: Parser, ReceiverSchema, EmitterSchema } = require('@coremarine/thelmabiotel-tblive')

// const isString = value => (typeof value === 'string' || value instanceof String)
// const isBoolean = value => (typeof value === 'boolean')
// const isNullOrUndefined = value => value === null || value === undefined

const setParser = (parser, config) => {
parser.firmware = config.firmware
// Receiver
if (config.receiverRequired) {
const receiver = v.parse(
ReceiverSchema,
{
firmware: config.firmware,
serialNumber: config.receiverSerialNumber
}
)
// Emitters
const emitters = []
if (config.emitter1Required) {
const emitter1 = v.parse(
EmitterSchema,
{
serialNumber: config.emitter1SerialNumber,
frequency: config.emitter1Frequency
}
)
emitters.push(emitter1)
}
if (config.emitter2Required) {
const emitter2 = v.parse(
EmitterSchema,
{
serialNumber: config.emitter2SerialNumber,
frequency: config.emitter2Frequency
}
)
emitters.push(emitter2)
}
if (config.emitter3Required) {
const emitter3 = v.parse(
EmitterSchema,
{
serialNumber: config.emitter3SerialNumber,
frequency: config.emitter3Frequency
}
)
emitters.push(emitter3)
}
parser.receiver = (emitters.length === 0) ? { ...receiver } : v.parse(ReceiverSchema, { ...receiver, emitters })
}
}

const cleanUndefineds = (msg) => {
Object.keys(msg).forEach(key => {
if (msg[key] === undefined) {
delete msg[key]
}
})
}

module.exports = function (RED) {
// Component
function TBLiveParser (config) {
RED.nodes.createNode(this, config)
const node = this
Object.assign(node, config)
// Logic
let parser = null
try {
parser = new Parser()
setParser(parser, config)
} catch (err) {
node.error(err, 'problem setting up TBLive parser')
}
// Input
node.on('input', (msg, send, done) => {
let error = null
try {
const { payload } = msg
// Payload
msg.payload = parser.parseData(payload)
// Clean undefined props
cleanUndefineds(msg)
// Send msg
send(msg)
} catch (err) {
error = err
} finally {
// Finish
if (done) { (error === null) ? done() : done(error) }
}
})
}
// Register
RED.nodes.registerType('cma-thelmabiotel-tblive', TBLiveParser)
}

0 comments on commit a00f7d0

Please sign in to comment.