Skip to content

feat: S14.10 custom-SD integrator guide + example (#549)#562

Merged
DavidCozens merged 3 commits into
mainfrom
feat/s14.10-custom-sd-guide
Jun 6, 2026
Merged

feat: S14.10 custom-SD integrator guide + example (#549)#562
DavidCozens merged 3 commits into
mainfrom
feat/s14.10-custom-sd-guide

Conversation

@DavidCozens

@DavidCozens DavidCozens commented Jun 6, 2026

Copy link
Copy Markdown
Owner

Purpose

Closes #549 — the user-facing payoff of the E14 (#64) foundation wave, and E14's
last story
. Documents and demonstrates authoring a custom SD-ELEMENT with the
safe two-type SD writer API (SolidSyslogSdElement / SolidSyslogSdValue) added
earlier in the epic, attached per-message via SolidSyslog_LogWithSd (S14.09).

Change Description

  • docs/structured-data.md — fleshed out into a full custom-SD integrator guide:
    implementing Format(base, element), registering an SD in Config.Sd[], the
    custom SD-ID name@enterprise convention + enterprise-number guidance, value
    escaping/streaming, the JSON-in-value pattern, and fail-loud name validation.
  • Worked custom SDBdd/Targets/Common/BddTargetCustomSd.{c,h} emits
    [example@32473 detail="Hello World"]. Lives in Common so all four BDD
    targets expose it (not Linux-only), registered in each target build + BddTargetTests.
  • send-custom interactive command (BddTargetInteractive.c) emits the worked
    element via SolidSyslog_LogWithSd.
  • Oracle round-trip BDDBdd/features/custom_sd.feature (@udp, one scenario)
    • steps in syslog_steps.py: the custom element reaches syslog-ng and detail
      decodes to Hello World.

The dedicated escape round-trip oracle BDD (originally folded in from S07.04 #68) was
dropped — see the note on #549. Escaping is unit-tested at the SolidSyslogSdValue
level; an oracle assertion on escaped output tests how syslog-ng (vs OTEL) re-renders
the value, not the library.

Test Evidence

  • BddTargetTests 68/68 green (includes new BddTargetCustomSdTest.cpp and the
    BddTargetInteractiveTest.cpp send-custom case).
  • Linux BDD target builds via the gcc docker compose service; custom_sd.feature
    passes against the real syslog-ng oracle (1 feature / 1 scenario / 3 steps green).

Areas Affected

docs/structured-data.md, Bdd/Targets/Common/, the four BDD target builds,
Bdd/features/ (feature + steps), Tests/Bdd/Targets/. Tier-3 BDD-target code +
docs only — no Core/Platform changes.

Summary by CodeRabbit

  • New Features

    • Added custom structured data support enabling users to attach caller-supplied structured data to syslog messages
    • Added new interactive command for testing custom structured data functionality
  • Documentation

    • Added comprehensive guide for authoring custom RFC 5424 structured data with usage examples and API requirements
  • Tests

    • Added BDD scenario tests for custom structured data round-trip validation
    • Added unit tests for custom structured data formatting
    • Extended test framework with structured data assertion capabilities

DavidCozens and others added 3 commits June 6, 2026 15:03
Add BddTargetCustomSd (Bdd/Targets/Common) — a minimal worked custom SD-ELEMENT
emitting [example@32473 detail="..."], the detail value containing ", \ and ]
so the upcoming oracle round-trip BDD can prove the library applies RFC 5424
PARAM-VALUE escaping. Wire a 'send-custom' interactive command that emits it via
SolidSyslog_LogWithSd, so all four BDD targets (Linux/Windows/FreeRtos/
FreeRtosLwip) expose it from the one shared Common runner. Registered in every
target build + BddTargetTests. Unit tests: the SD's escaped output and the
command dispatch/count.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Author docs/structured-data.md — the custom-SD integrator guide: the two-type
writer model (SdElement + SdValue), implementing a Format vtable with the
embed-base downcast for stateful data, SD-IDs / enterprise numbers, registering
via Config.Sd[] and SolidSyslog_LogWithSd (with the reentrancy note), and what
the library owns vs the integrator. Written around the real BddTargetCustomSd.

Simplify the worked custom SD to detail="Hello World" (per review — a clear
example, not muddied by escaped data). Add custom_sd.feature + a
send-custom/detail step pair (run_example gains a command arg) proving the
custom element round-trips through the oracle.

Per David: the dedicated escape round-trip oracle BDD is dropped — value
escaping is already covered by the SdValue unit tests, and the syslog-ng/OTEL
oracles re-render an escaped value differently, so an oracle assertion there
tests the oracle, not the library.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jun 6, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

This PR introduces a custom structured data example and integrator guide. A new BDD target module (BddTargetCustomSd) defines a singleton SD element with a formatter callback that emits an example element containing a detail parameter. The interactive BDD target gains a send-custom command that exercises the per-message SD API. Unit and BDD tests validate the implementation. Documentation guides users in authoring custom SD elements using the safe API.

Changes

Custom Structured Data Example & Documentation

Layer / File(s) Summary
Custom SD module definition
Bdd/Targets/Common/BddTargetCustomSd.h, Bdd/Targets/Common/BddTargetCustomSd.c
Header and implementation define a singleton custom structured-data element with an IANA enterprise number and formatter callback that emits an "example" SD element containing "detail"="Hello World".
Interactive target send-custom command
Bdd/Targets/Common/BddTargetInteractive.c
Interactive BDD target adds a send-custom N command handler that calls SolidSyslog_LogWithSd with the custom SD and reports sent count.
Cross-platform build wiring
Bdd/Targets/CMakeLists.txt, Bdd/Targets/FreeRtos/CMakeLists.txt, Bdd/Targets/FreeRtosLwip/CMakeLists.txt, Tests/Bdd/Targets/CMakeLists.txt
Custom SD source file integrated into Linux, Windows, FreeRTOS, FreeRTOS+LWIP, and test executable builds.
Unit tests
Tests/Bdd/Targets/BddTargetCustomSdTest.cpp, Tests/Bdd/Targets/BddTargetInteractiveTest.cpp
CppUTest cases validate the SD formatter output matches the expected example element and the send-custom command dispatches and counts correctly.
BDD feature and step definitions
Bdd/features/custom_sd.feature, Bdd/features/steps/syslog_steps.py
Gherkin scenario defines custom SD round-trip delivery; Python steps implement send-custom command and structured-data detail assertion with RFC 5424 escape handling.
Custom SD integrator guide
docs/structured-data.md
User-facing documentation covering the SD authoring pattern, implementation example, API overview, SD-ID and enterprise-number construction, value escaping and streaming, registration flows, and library/caller ownership boundaries.
Project tracking
DEVLOG.md
Entry documents custom-SD guide scope, cross-platform BDD exposure, acceptance decisions, validation status, and pending WSL execution of the feature scenario.

Sequence Diagram

sequenceDiagram
  participant User
  participant BDD
  participant Interactive as BddTarget<br/>Interactive
  participant SolidSyslog
  participant Formatter
  participant Oracle
  User->>BDD: run custom_sd.feature
  BDD->>Interactive: send-custom 1
  Interactive->>SolidSyslog: LogWithSd(msg, custom_sd)
  SolidSyslog->>Formatter: CustomSd_Format()
  Formatter->>Formatter: emit example@32473<br/>detail="Hello World"
  SolidSyslog->>Oracle: deliver syslog message
  BDD->>Oracle: assert detail="Hello World"
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related issues

  • DavidCozens/solid-syslog#549: This PR directly implements the acceptance criteria of the linked issue—completing the custom-SD integrator guide, adding a worked example with BDD wiring, and covering custom SD authoring patterns in documentation.
  • DavidCozens/solid-syslog#64: This PR delivers the concrete E14 "Custom Structured Data" feature implementation, providing example code, tests, and user-facing documentation for the structured-data extension point.

Possibly related PRs

  • DavidCozens/solid-syslog#561: This PR's custom SD test and BDD flow depend directly on the per-message SD API SolidSyslog_LogWithSd and SD formatting behavior introduced in that PR.
  • DavidCozens/solid-syslog#551: This PR's CustomSd_Format implementation relies on the SolidSyslogSdElement Begin/Param/End-style framing and parameter quoting semantics added in that PR.
  • DavidCozens/solid-syslog#307: Both PRs modify the prompt-protocol flow in syslog_steps.py; this PR extends the interactive command dispatch with send-custom, while that PR updates the shared run_example command-sending layer.

Poem

🐰 A custom SD hops in with hello,
Formatter callbacks make details mellow,
Build paths align from Linux to Cortex,
Tests and BDD dance their vortex,
The oracle grins at this structured delight!

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 20.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title 'feat: S14.10 custom-SD integrator guide + example (#549)' clearly summarizes the main change: adding documentation and a worked example for custom structured data in SolidSyslog.
Description check ✅ Passed The PR description provides comprehensive coverage of all template sections: Purpose (closes #549, E14's last story), Change Description (detailed breakdown of docs, worked SD, interactive command, oracle BDD), Test Evidence (test results and BDD pass status), and Areas Affected (specific module list).
Linked Issues check ✅ Passed The PR fully addresses #549's acceptance criteria: docs/structured-data.md is a complete integrator guide covering Format(), SD registration, SD-ID naming, value escaping, JSON-in-value, and validation; a worked custom-SD example exists in Common/ and is tested; oracle BDD custom_sd.feature verifies escape round-trip through syslog-ng.
Out of Scope Changes check ✅ Passed All changes align with #549's scope: documentation and BDD examples for custom SD with escaping. The dedicated escape oracle BDD was intentionally dropped per issue notes. No Core/Platform changes introduced—only tier-3 BDD-target code and docs, as explicitly stated in PR description.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/s14.10-custom-sd-guide

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@DEVLOG.md`:
- Around line 14749-14752: Update the DEVLOG entry for custom_sd by replacing
the “authored but not yet run” status with the actual executed state (or append
an explicit runtime context): locate the paragraph referencing
custom_sd.feature, behave, and the `@udp` custom_sd scenario and either change the
phrase to indicate it "passed" (e.g., "custom_sd.feature — executed and passed
on <date>") or add a parenthetical note with the run date, environment (WSL),
and confirmation of the detail "Hello World" round-trip so the release notes
aren’t stale.

In `@docs/structured-data.md`:
- Around line 6-8: The fenced code block containing the example line
[example@32473 detail="Hello World"] is missing a language tag and triggers
MD040; add a language identifier (e.g., text or syslog) to the opening fence so
it reads ```text (or ```syslog) before the line and keep the closing ```
unchanged to satisfy the linter and preserve the example content.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 49dcd2b6-f0f0-47c3-83ff-5781eea7e3a4

📥 Commits

Reviewing files that changed from the base of the PR and between 65bbf5b and b208d91.

📒 Files selected for processing (13)
  • Bdd/Targets/CMakeLists.txt
  • Bdd/Targets/Common/BddTargetCustomSd.c
  • Bdd/Targets/Common/BddTargetCustomSd.h
  • Bdd/Targets/Common/BddTargetInteractive.c
  • Bdd/Targets/FreeRtos/CMakeLists.txt
  • Bdd/Targets/FreeRtosLwip/CMakeLists.txt
  • Bdd/features/custom_sd.feature
  • Bdd/features/steps/syslog_steps.py
  • DEVLOG.md
  • Tests/Bdd/Targets/BddTargetCustomSdTest.cpp
  • Tests/Bdd/Targets/BddTargetInteractiveTest.cpp
  • Tests/Bdd/Targets/CMakeLists.txt
  • docs/structured-data.md

Comment thread DEVLOG.md
Comment on lines +14749 to +14752
### Pending → WSL
- The `custom_sd.feature` oracle round-trip is **authored but not yet run** — `behave` needs
the docker/syslog-ng oracle, which runs from WSL, not the devcontainer. Next step: pull the
branch in WSL, run the `@udp` `custom_sd` scenario, confirm `detail "Hello World"` round-trips.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Update validation status to avoid stale release notes.

This “not yet run” note conflicts with the PR objective/status context indicating custom_sd.feature already passed. Please align this section with the final executed state (or add explicit run date/context if it was pending at entry time).

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@DEVLOG.md` around lines 14749 - 14752, Update the DEVLOG entry for custom_sd
by replacing the “authored but not yet run” status with the actual executed
state (or append an explicit runtime context): locate the paragraph referencing
custom_sd.feature, behave, and the `@udp` custom_sd scenario and either change the
phrase to indicate it "passed" (e.g., "custom_sd.feature — executed and passed
on <date>") or add a parenthetical note with the run date, environment (WSL),
and confirmation of the detail "Hello World" round-trip so the release notes
aren’t stale.

Comment thread docs/structured-data.md
Comment on lines +6 to +8
```
[example@32473 detail="Hello World"]
```

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Add a language tag to the fenced example block.

This code fence is missing a language identifier and triggers MD040. Add text (or syslog) to keep lint green.

Proposed fix
-```
+```text
 [example@32473 detail="Hello World"]
</details>

<!-- suggestion_start -->

<details>
<summary>📝 Committable suggestion</summary>

> ‼️ **IMPORTANT**
> Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

```suggestion

🧰 Tools
🪛 markdownlint-cli2 (0.22.1)

[warning] 6-6: Fenced code blocks should have a language specified

(MD040, fenced-code-language)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/structured-data.md` around lines 6 - 8, The fenced code block containing
the example line [example@32473 detail="Hello World"] is missing a language tag
and triggers MD040; add a language identifier (e.g., text or syslog) to the
opening fence so it reads ```text (or ```syslog) before the line and keep the
closing ``` unchanged to satisfy the linter and preserve the example content.

Source: Linters/SAST tools

@github-actions

github-actions Bot commented Jun 6, 2026

Copy link
Copy Markdown
Contributor

☀️   Quality Summary

   🚦   build-linux-gcc: 100% successful (✔️ 1521 passed)
   🚦   build-freertos-host-tdd-plustcp: 100% successful (✔️ 1872 passed)
   🚦   build-linux-clang: 100% successful (✔️ 1453 passed)
   🚦   sanitize-linux-gcc: 100% successful (✔️ 1453 passed)
   🚦   integration-linux-openssl: 100% successful (✔️ 16 passed)
   🚦   integration-linux-mbedtls: 100% successful (✔️ 14 passed)
   🚦   integration-windows-openssl: 100% successful (✔️ 16 passed)
   🚦   bdd-linux-syslog-ng: 94% successful (✔️ 49 passed, 🙈 3 skipped)
   🚦   bdd-windows-otel: 88% successful (✔️ 46 passed, 🙈 6 skipped)
   🚦   bdd-freertos-qemu-plustcp: 87% successful (✔️ 45 passed, 🙈 7 skipped)
   🚦   bdd-freertos-qemu-lwip: 87% successful (✔️ 45 passed, 🙈 7 skipped)
   🚦   build-windows-msvc: 100% successful (✔️ 1298 passed)
   🚦   build-linux-tunable-override: 100% successful (✔️ 1453 passed)
   ⚠️   Clang-Tidy: No warnings
   ⚠️   CPPCheck: No warnings


Created by Quality Monitor v1.14.0 (#f3859fd). More details are shown in the GitHub Checks Result.

@DavidCozens DavidCozens merged commit e1f324b into main Jun 6, 2026
27 checks passed
@DavidCozens DavidCozens deleted the feat/s14.10-custom-sd-guide branch June 6, 2026 15:34
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

S14.10: Custom-SD integrator guide + example/BDD

1 participant