Skip to content

Release Notes - Version 0.1.4

Released: 2026-03-16

🗑️ Removed

  • Modbus Server datablock:
  • Removed CompositeDataBlock: allowed to define properties for each register instead of using datablocks.

  • PowerValidator placeholder removed — the stub class created during initial scaffolding (core/power_validator.py and its 14 tests) has been deleted; it had no role in the production firmware

🎉 What's New

  • Phase 1 Sprint 3 planning document (docs/internal/management/planning/phase1-sprint3.md) — 4-week sprint (2026-03-16 to 2026-04-10): hardware platform, CAN transport, HAL, DIO stack, DBC parser, and ndrs-atn onboarding (83 SP core across ndrs-npm, ndrs-kmk, ndrs-atn)

  • Task Management subsystem (INFRA-010 to INFRA-014) added to task-roadmap.md — 5 new tasks (13 SP); project totals updated to 218 tasks / 905 SP

  • Coverage badge auto-generation via shields.io static URL (no extra files or services):

  • Coverage badge (![codecov]) uses the Codecov umbrella logo (?logo=codecov&logoColor=white) via shields.io — no Codecov service account required
  • Updated inline by sync-readme.yml on every push to main — no placeholder file needed
  • Coverage policy (safety-critical project): ≥90% brightgreen (acceptable), ≥75% yellow (warning), <75% red (failing)
  • Area-specific minimums documented in README.md and copilot-instructions.md: safety-critical 100%, all other areas ≥90%

  • sync-readme.yml expanded (.github/workflows/sync-readme.yml):

  • Renamed workflow: Sync README VersionSync README Badges
  • Added FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true to suppress Node.js 20 deprecation warning
  • Now runs on every push to main (removed paths: [pyproject.toml] filter and pull_request trigger)
  • Added Python + uv setup steps to run pytest --cov=code --cov-report=term-missing | tee coverage.txt
  • Added Extract coverage percentage and Pick badge color steps
  • Replaces shields.io badge URL in-place with sed; version badge updated in the same step
  • Single git commit for both coverage + version badge changes (git diff --cached guard)

  • CI pipeline fixes and improvements (.github/workflows/ci.yml):

  • Fixed bandit missing from uv run by adding bandit[toml] (>=1.7.0) to [dependency-groups].dev in pyproject.toml
  • Removed Codecov integration; replaced with GitHub Actions job summary (coverage table written to $GITHUB_STEP_SUMMARY via coverage report --format=markdown)
  • Removed --cov-report=xml from pytest command (no longer needed without Codecov)
  • Added CI Summary job (Job 5): runs if: always() after all jobs, writes a markdown status table (✅/❌/⏭️) for each job to the workflow summary page

  • README.md overhaul with updated structure and content:

  • Added dynamic version badge (reads from pyproject.toml via shields.io)
  • Added CI status badge and Codecov coverage badge
  • Added Ruff badge (replaces Black reference)
  • Updated Communication Interfaces table: RS-485 row now shows 9600 baud (default) and correct purpose (end-device data collection)
  • Updated Project Structure to reflect actual repository layout (packaging/, mock/, playground/, template/)
  • Updated Source Code Structure (code/bess_rcu/) with all real subdirectories (adapters, database, devices, drivers, models, server, tasks, utils)
  • Added new documentation links: Release Process, Project Architecture, Quick Reference, Hardware Guide, API Specification, Troubleshooting
  • Fixed broken planning doc links: docs/planning/docs/internal/management/planning/
  • Replaced Black/pylint references with Ruff (formatter + linter)
  • Updated deployment example: hardcoded 0.1.2<version> placeholder
  • Removed stale footer (Last Updated / Version / Status lines)

  • Public Modbus Server Documentation

  • added (draft) modbus server docs under /docs/public
  • BESS_RCU Server applications:
  • created register map for bess_rcu
  • implemented modbus server application
  • sync with redis database
  • AC Meter and Isometer applications
  • created /devices directory which replaced /hardware
  • implemented polling and updating values to redis database feature
  • preprocessed data
  • created register map for each device
  • added unit test for each application
  • Hardware Setup & Verification tasks (Section 1A) in task-roadmap.md:
  • 9 new tasks (HARDWARE-001 to HARDWARE-009) for EDATEC Gateway validation
  • Tasks cover: Gateway setup, RS-485 testing, I/O verification, CAN interface testing, network configuration, deployment testing, and hardware compatibility validation
  • Assigned to Sprint 2 (Phase 1) for early hardware risk mitigation
  • Owner: ndrs-npm - Gateway acts as development/test center
  • Total effort: 73h / 48 Story Points
  • Updated summary statistics: 213 total tasks, 892 SP, ~1,358 hours

  • Comprehensive documentation and feature enhancements for BESS RCU (#79)

  • update: implement redis integration in modbus, and add ac-meter, isometer, bess_rcu server applications (#76)

✨ Improvements

  • phase1-sprint3.md refined: temperature sensor corrected to XY-MD02 Modbus RTU (was DS18B20 1-Wire); Modbus references updated to ModbusWrapperClient; gateway and DBC vendor risks removed (hardware confirmed, foxbms.dbc already present); ndrs-atn onboarding scoped to standalone device classes only (no BaseTask); Slack replaced with GitHub Issues; ISS-01 resolved; branch strategy updated to personal-branch model (ndrs-npm/ndrs-kmk/ndrs-atn)

  • phase1-sprint2.md updated: SENSOR-028 and SENSOR-029 (data preprocessing, 6 SP) added to ndrs-kmk backlog as unplanned completed tasks

  • task-roadmap.md: INFRA-006/007, STATE-001/002/003 marked ✅; DIO-009 renamed to I/O Controller Task (TaskIO BaseTask subclass)

  • phase1-sprint2.md retrospective added: actuals (45/62 SP), completed/carryover statuses, retrospective notes, and carryover table (10 tasks, 38 SP)

  • sprint-template updated: added Sprint Context, Risk Register, Onboarding Notes, Implementation Approach blocks, DoD reminder, and carryover section

  • Full application lifecycle orchestrationuv run bess-rcu run now starts a complete, production-grade firmware process:

  • app.py: main orchestrator that loads config, sets up logging, drives the state machine (UNINITIALIZED → INITIALIZING → NORMAL), runs all tasks, and shuts down cleanly on Ctrl-C or SIGTERM
  • core/state_machine.py: 6-state FSM (UNINITIALIZED, INITIALIZING, NORMAL, FAULT, MAINTENANCE, SHUTDOWN); safe request_shutdown() callable from any state
  • core/task_manager.py: async periodic task scheduler with per-task success/failure metrics and immediate cancellation on stop
  • core/plugin_system.py: plugin loader that discovers .py files from a plugins/ directory at runtime; no core code changes needed to add site-specific behaviour

  • Built-in system health monitoring — a heartbeat task fires at the top of every minute and writes a single structured log line:

Health OK | pid=12345 | uptime=2d 03h 14m | CPU=12.4% | MEM=142/512MiB(27.7%) | Disk=18.2/32.0GiB(56.9%) | cycle=42
  • Automatically promotes to WARNING with a detail line when CPU, memory, or disk exceeds configurable thresholds (defaults: 80 / 80 / 85 %)
  • Optional full report mode adds load averages and thread / file-descriptor counts
  • Configured via bess_rcu.health_check: in config/config.yaml
  • psutil>=6.0 added as a required runtime dependency

  • Smart configuration loadingutils/config_loader.py:

  • Resolves the config file from four sources in order: explicit --config argument, BESS_RCU_CONFIG_PATH env var, system path /etc/bess-rcu/config/config.yaml, then the project-local ./config/config.yaml
  • Auto-loads a .env file in development (no-op on production hardware)
  • Startup banner clearly reports which source was used (explicit, env_var, system, project_default, or none)
  • BESS_RCU__* env vars override any config value without editing the YAML file

  • Professional CLI version outputbess-rcu --version / -v now prints a three-line banner (firmware version, product name, copyright) instead of a plain version string

  • Production systemd deployment — full hardened service setup under packaging/systemd/:

  • bess-rcu.service: Type=notify, WatchdogSec=30, resource limits (MemoryMax=512M, CPUQuota=80%), automatic restart on failure, and comprehensive security restrictions
  • bess-rcu-watchdog.service: separate unit that feeds /dev/watchdog (hardware WDT) every 10 s, independently of the application process
  • packaging/config/bess-rcu.default: Debian /etc/default/ environment file that centralises all variables consumed by the firmware and the service units

  • Pydantic v2 configuration models — five new model modules and a root aggregator covering every config.yaml subsection, all following the <DomainName>Fields metadata-separation pattern:

  • models/health_check.py: HealthCheckConfig, HealthCheckThresholds
  • models/logging_config.py: LoggingConfig, LoggingFileConfig, LogRotationMode
  • models/can.py: CanConfig with FD-mode cross-validation and CanInterfaceType enum (socketcan/kvaser/pcan/virtual/…)
  • models/modbus.py: ModbusConfig hierarchy with smart interface auto-detection (replaces mandatory active_interface), TcpInterfaceConfig, RtuInterfaceConfig (stop-bit/parity validation), and ModbusDeviceConfig
  • models/redis_config.py: RedisConfig with connection-pool settings, TLS/mTLS (RedisTlsConfig), key-prefix namespace, and retry configuration
  • models/config.py: AppConfig root aggregator (version + bess_rcu) and parse_config() entry-point

  • config/config.yaml redesigned — Modbus (interface replacing active_interface with smart auto-detection, unit_id, per-device timeout_s/retries/poll_interval_s; iface.tcp/rtu → top-level tcp/rtu per device; new isometer and temp_sensor devices added), CAN (interface, channel, bitrate, fd_mode, fd_data_bitrate, receive_own_messages, timeout_s), and Redis (connection pool, TLS, key prefix, retry settings) sections redesigned to industry standard and validated by the new Pydantic models; all inline comments moved to section block comments (YAML linter compliance)

  • load_typed_config() — new function in utils/config_loader.py that combines YAML loading with Pydantic validation, returning a fully typed AppConfig object

  • Unit and integration test suite — 368 tests, all passing:

  • State machine — 44 tests covering every transition and edge case
  • Task manager — 21 tests covering registration, lifecycle, metrics, and error callbacks
  • BaseTask — 35 tests covering hooks, context storage, metrics, scheduling, and repr
  • SystemHealthTask / config models — 39 tests covering thresholds, report modes, disk fallback, and cycle counter
  • Config loader — 55 tests covering deep-merge, env-var overrides, placeholder substitution, path resolution, _meta provenance, and load_typed_config()
  • CLI — 14 tests covering --version output, parser arguments, and PEP 440 version format
  • Pydantic config models — 131 tests covering all model validations, defaults, cross-field validators, and edge cases across modbus, can, redis, health_check, logging_config, and config modules
  • Integration smoke tests — 7 subprocess tests that launch bess-rcu run and verify the startup banner, environment reporting, and absence of tracebacks

  • config/config.yaml restructured — all firmware settings are now nested under a single bess_rcu: root key (health_check:, logging:, can:); obsolete flat keys (log_level, output_dir, plugin_dir) removed

  • health_check.py renamed to task_health_check.py for naming consistency with the task_*.py convention; no functional changes

  • Version string uses importlib.metadata__version__ in __init__.py and cli.py now read the version from pyproject.toml at runtime, eliminating the stale mismatch that existed between the three files

  • Modbus Server and Client features update:

  • Server-side Data Model: allowed to define each register, create a register map, and store in datablock for a given map
  • Server-side Data Validation: stricter schema validation using pydantic
  • Client-side floating point read: able to poll floating point register values
  • Redis Integration: integrated redis into both server-side and client-side allowing not to handle pymodbus datastore object directly
  • GitHub issue creation script (10.create-github-issues.ps1) modernized to v2.0:
  • Simplified usage: Only -TaskID parameter required (e.g., .\10.create-github-issues.ps1 -TaskID "CAN-012")
  • Optional milestone: -MilestoneId is now optional (can be set later in GitHub UI)
  • Optional labels: -Labels parameter optional (can be set later in GitHub UI)
  • Performance optimization: Parses entire roadmap once and builds hashtable for O(1) task lookups (efficient with 1000+ tasks)
  • Auto-detection: Automatically detects section from TaskID (no need to specify section title)
  • Updated file path: Now reads from docs/internal/management/planning/task-roadmap.md
  • Improved help: Updated examples to show simplified usage patterns
  • Backward compatible: Old parameters still work if provided

  • Phase 1 implementation plan in task-roadmap.md:

  • Added Hardware Setup & Verification as explicit step in Sprint 2
  • Updated deliverables to include validated hardware platform
  • Reorganized weeks to accommodate hardware verification tasks

  • utils/logger.py → thin backward-compatible re-export from base_logger.py; all existing imports unchanged

  • utils/config_loader.py → imports BaseConfigLoader from base_config_loader.py; retains only BESSRCUConfigLoader definition
  • utils/__init__.py → updated to import directly from base_logger and base_config_loader
  • core/task_manager.py_run_task_loop failure branch now calls await task.on_error(exc) after updating metrics; exceptions raised inside on_error are caught and logged without stopping the task loop; increments task._execution_count on success

  • models/README.md generalised — rewritten from YAML-configuration-specific to a generic Pydantic v2 template suitable for any domain (API bodies, Modbus/CAN payloads, domain objects, task metrics, etc.); YAML loading retained as one example pattern. Orphaned "Full Template" section removed following deletion of _model_template.py.

  • Update code coverage requirements and enhance testing documentation (#84)

  • Update formatting and linting tools in documentation (#80)
  • feat(modbus): update new datamodel and configuration for server-side and support floating point read in client-side (#72)

Full Changelog: View on GitHub