feat: allow writes to BACnet properties other than Present_Value#42
feat: allow writes to BACnet properties other than Present_Value#42wz2b wants to merge 3 commits into
Conversation
|
The doWrite function changes look fine, however how would a user choose what property to write to? Currently our workflow is via the Write node, here the user can select what points they want to write to, the Application Tag, and Priority. For this to work, a propertyId selector would need to be added to the UI for the write node for the users to choose, and then added to the msg.options.pointsToWrite object, so that it can be passed on to the gateway node, and used in the doWrite function as |
Wires the new propertyId resolver to the Write node by adding a node-level Property dropdown alongside the existing Application Tag and Priority selectors, defaulting to PRESENT_VALUE for backward compatibility. The configured property is stamped onto each point in pointsToWrite on input, so doWrite() resolves it per-point as point.propertyId. Per-point overrides supplied via msg.options.pointsToWrite are preserved. Resolves the UI gap raised in PR review: without this, the resolver always received undefined and silently fell back to PRESENT_VALUE.
Code reviewReviewed the original commit (9a8063e) and pushed a follow-up fix as 3bb026d to address @arminbitpool's UI gap. Findings on the original commit:
Fix pushed (3bb026d):
The Mirroring the existing 🤖 Generated with Claude Code - If this code review was useful, please react with 👍. Otherwise, react with 👎. |
| <select id="node-input-propertyId"> | ||
| <option value="85">PRESENT_VALUE (85)</option> | ||
| <option value="81">OUT_OF_SERVICE (81)</option> | ||
| <option value="84">POLARITY (84)</option> | ||
| <option value="104">RELINQUISH_DEFAULT (104)</option> | ||
| <option value="22">COV_INCREMENT (22)</option> | ||
| <option value="45">HIGH_LIMIT (45)</option> | ||
| <option value="59">LOW_LIMIT (59)</option> | ||
| <option value="25">DEADBAND (25)</option> | ||
| <option value="28">DESCRIPTION (28)</option> | ||
| <option value="77">OBJECT_NAME (77)</option> | ||
| </select> |
There was a problem hiding this comment.
Should we only support these properties? or is there value in supporting more bacnet object property types.
There was a problem hiding this comment.
Good call — pushed 4ddf5ea to switch this from a closed <select> of 10 to a free-text <input> backed by a <datalist>. Users can now target any of the ~370 BACnet property identifiers — by name (any case/separator: PRESENT_VALUE, present_value, presentValue, present-value) or by numeric ID (85).
Datalist offers ~37 common writable properties as autocomplete suggestions. Empty input defaults to PRESENT_VALUE (placeholder makes that visible).
Verified with 16/16 resolver cases incl. empty/whitespace, numeric-string, mixed-case, and unknown-name (still throws).
There was a problem hiding this comment.
Thank you for this comment — it makes me realize I went overboard with this. I’m going back to ASHRAE 135 to figure out where I went off the rails.
There are some BACnet properties that are read-only by definition. There are others that may be writable, but are only meaningful to set when the object/point is created or configured. Anything that clients discover and cache — object name, object type, units, etc. — is risky to change dynamically because the client at the other end may never realize it changed.
I don’t want to set that trap for the user by exposing a capability that looks general-purpose but does not really make sense at runtime.
Out of hundreds of possible BACnet property identifiers, I think this node should probably support a curated runtime list, and treat numeric property resolution as an advanced escape hatch.
Normal Runtime Targets
PRESENT_VALUE— defaultOUT_OF_SERVICE— this is the one I originally needed
Simulation / Test Targets
RELIABILITY— useful for simulating fault conditionsEVENT_STATE— maybe useful, but I’m less confident this should be directly written in normal use. It's normally set by the ALARM logic described below. I'm on the fence on this one and leaning toward we leave it out, and add logic to compute it based on ASHRAE rules and the alarm parameters below if we want that.
Reliability indicates the health of the object. In many real BACnet devices, RELIABILITY is computed internally by the device and may be read-only. However, in a simulated or software-defined object model, allowing it to be set can be useful for testing and fault injection. It's another big enum with values like NO_FAULT_DETECTED, NO_SENSOR, OVER_RANGE, etc.
COV Configuration
COV_INCREMENT— controls proper BACnet COV reporting for analog values. It is not really normal for COV_INCREMENT to be adjusted dynamically. It's not part of the subscription contract, it's something normally set during point commissioning.
Alarm Configuration / Tuning
HIGH_LIMITLOW_LIMITDEADBANDTIME_DELAY
These drive intrinsic alarming. BACnet has a read-only summary flag named STATUS_FLAGS.IN_ALARM, and a property named EVENT_STATE, which can report states such as NORMAL, HIGH_LIMIT, LOW_LIMIT, FAULT, or OFF_NORMAL.
In most BACnet devices, software should not directly set STATUS_FLAGS. Alarm state is normally computed from PRESENT_VALUE, HIGH_LIMIT, LOW_LIMIT, DEADBAND, TIME_DELAY, and related event configuration.
Mostly Creation-Time / Configuration-Time
RELINQUISH_DEFAULT
This may be technically writable, but I usually think of it as something you set when creating/configuring the point, not as a normal runtime operation.
So I think the right answer is to go in the other direction: fewer enum values than I said, not more. I'm sorry, I should have thought about this a little harder at first. This discussion made things a bit more clear to me.
Replaces the closed Property dropdown with a free-text input plus a
datalist of common writable properties for autocomplete. Users can now
target any of the ~370 BACnet property identifiers — by name (any case
or separator style) or numeric ID — without us having to enumerate them
in the UI.
Resolver tweaks (bacnet_client.js):
- Empty / whitespace-only string defaults to PRESENT_VALUE.
- Numeric strings ("85") are accepted as raw property identifiers.
UI tweaks (bacnet_write.html):
- Property field is now <input type="text" list="..."> backed by a
datalist; placeholder shows "PRESENT_VALUE" for the default.
- Default value is now empty (was "85") so the placeholder is visible.
Addresses review feedback on PR bitpool#42 — the closed list was unnecessarily
limiting given the resolver already accepts any name or number.
No description provided.