Skip to content

feat(validator): B80-4/5/6 — service-state + schema codegen + wiring#372

Merged
itcmsgr merged 2 commits intomainfrom
fix/b80-4-service-state-checks
Apr 13, 2026
Merged

feat(validator): B80-4/5/6 — service-state + schema codegen + wiring#372
itcmsgr merged 2 commits intomainfrom
fix/b80-4-service-state-checks

Conversation

@itcmsgr
Copy link
Copy Markdown
Owner

@itcmsgr itcmsgr commented Apr 13, 2026

Summary

Three v1.80 blockers in one PR:

B80-4: Dead daemon detection. nftband not running → DEGRADED, not PROTECTED.
B80-5: Schema codegen. scripts/generate-go-schema.sh reads canonical shell schema.
B80-6: Validator wiring. types.go chain/set vars → generated aliases.

B80-4 — Service-state checks

  • Three-state model: RUNNING / STOPPED / ERROR
  • ADJ-1: transition states (activating, deactivating, reloading) → STOPPED (not ERROR)
  • VAL-SERVICE-001 finding when nftband != RUNNING
  • Lab validated: stop → DEGRADED, start → PROTECTED

B80-5 — Schema codegen

  • scripts/generate-go-schema.sh sources nft_schema.sh, generates schema_generated.go
  • Deterministic (byte-identical on re-run)
  • Generated helper-chain universe = 6 entries (3 shell-declared + 3 DDoS fragment sub-chains)
  • Does NOT generate anchors (strict order, validator-only concept)

B80-6 — Validator wiring

  • types.go: RequiredBaseChains, RequiredHelperChains, RequiredSetsIPv4, RequiredSetsIPv6 → Generated* aliases
  • RequiredAnchors stays manually maintained (strict order)
  • No parallel hardcoded lists remain

Scope

internal/validator/ (types.go, validator.go, validator_test.go, schema_generated.go) + scripts/generate-go-schema.sh. No shell. No CLI. No runtime. No pipeline.

Test plan

  • 15/15 PASS on lab4 (full validator suite)
  • Lab validation: stop nftband → DEGRADED, start → PROTECTED
  • Determinism check: 2 generator runs → same md5
  • 5 review checkpoints verified (types.go completeness, anchor contract, 6 helpers, required/all distinction, family symmetry)
  • CI

Refs: V1.80_ROADMAP/MASTER_TODO.md B80-4, B80-5, B80-6

🤖 Generated with Claude Code

@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented Apr 13, 2026

Dependency Review

✅ No vulnerabilities or license issues or OpenSSF Scorecard issues found.

Snapshot Warnings

⚠️: No snapshots were found for the head SHA d54d308.
Ensure that dependencies are being submitted on PR branches and consider enabling retry-on-snapshot-warnings. See the documentation for more information and troubleshooting advice.

Scanned Files

None

@itcmsgr itcmsgr force-pushed the fix/b80-4-service-state-checks branch from b9d918a to 2826b45 Compare April 13, 2026 08:24
A system with correct kernel structure but a dead nftband daemon is not
truly protected. The daemon manages runtime objects (BotGuard, LoginMon,
scoring) that exist only while it runs.

Three-state model (aligns with v1.82 health model direction):
  RUNNING  — service active, full protection
  STOPPED  — inactive/failed/dead/activating/deactivating/reloading
  ERROR    — systemctl query itself failed

Both STOPPED and ERROR produce VAL-SERVICE-001 (SeverityError) → DEGRADED.
Only RUNNING allows PROTECTED.

ADJ-1: transition states (activating, deactivating, reloading) map to
STOPPED, not ERROR. Prevents misleading ERROR findings during rebuild
windows when the daemon restarts.

ADJ-2: TestServiceStateActivating test case covers the transition state.

Design: nftables.service is NOT checked — if nftables were down,
LoadRulesetJSON would already fail → StatusDown. nftband being down is
the subtler failure: kernel structure looks correct but runtime
detection/scoring is absent.

Lab validation (lab4, live):
  nftband running   → status=protected, nftband=RUNNING     ✓
  nftband stopped   → status=degraded,  nftband=STOPPED     ✓
                      VAL-SERVICE-001 finding emitted        ✓
  nftband restarted → status=protected, nftband=RUNNING     ✓

Tests: 15/15 PASS on lab4 (7 new service-state tests). No regressions.

Scope: 3 files in internal/validator/ only. No shell. No CLI. No
runtime. No pipeline.

Refs: V1.80_ROADMAP/MASTER_TODO.md B80-4

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@itcmsgr itcmsgr force-pushed the fix/b80-4-service-state-checks branch from 2826b45 to 940c651 Compare April 13, 2026 08:29
@itcmsgr itcmsgr changed the title feat(validator): B80-4 service-state checks — dead daemon → DEGRADED feat(validator): B80-4/5/6 — service-state + schema codegen + wiring Apr 13, 2026
@itcmsgr itcmsgr force-pushed the fix/b80-4-service-state-checks branch from 2598328 to d583029 Compare April 13, 2026 08:50
Eliminates schema drift between shell (nft_schema.sh) and Go (validator).

B80-5: Generator script (scripts/generate-go-schema.sh)
- Reads cli/lib/nftban/lib/nft_schema.sh as canonical source
- Extracts sorted key lists from bash associative arrays
- Applies validator-specific augmentation: DDoS fragment sub-chains
  (ddos_sanity, ddos_penalty, ddos_prefix) are structurally required
  but not declared in NFTBAN_IPV4_HELPER_CHAINS. Added as documented
  extension. Resulting helper-chain set = 6 entries.
- Deterministic: two runs produce byte-identical output
- Does NOT generate anchors (strict order, validator-only concept)

B80-6: Validator wiring
- RequiredBaseChains, RequiredHelperChains, RequiredSetsIPv4,
  RequiredSetsIPv6 in types.go are now aliases to generated vars
- RequiredAnchors stays manually maintained (strict order)
- No parallel hardcoded string lists remain in types.go
- Test mocks updated: http_bot_guard added to helper chain fixtures

Generated helper-chain universe (6 entries):
  ddos_penalty, ddos_prefix, ddos_protection, ddos_sanity,
  http_bot_guard, portscan_detection

Schema source chain:
  nft_schema.sh -> generate-go-schema.sh -> schema_generated.go -> types.go
  (anchors: types.go only, manually maintained)

Full validator suite: 15/15 PASS on lab4. No regressions.

Refs: V1.80_ROADMAP/MASTER_TODO.md B80-5, B80-6

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@itcmsgr itcmsgr force-pushed the fix/b80-4-service-state-checks branch from d583029 to d54d308 Compare April 13, 2026 14:37
@itcmsgr itcmsgr merged commit dbac50c into main Apr 13, 2026
6 checks passed
@itcmsgr itcmsgr deleted the fix/b80-4-service-state-checks branch April 13, 2026 14:41
itcmsgr added a commit that referenced this pull request Apr 13, 2026
v1.80 closes the structural truth-surface hardening line. Protection
state now fails correctly for broken kernel structure, empty required
chains, dead required runtime, schema drift, and duplicate schema
authority.

v1.80.0 does not change the effective detection/scoring model;
effectiveness tuning remains future work (BUG-1 / v1.81+).

Blockers closed: B80-1 through B80-8 + BUG-6 (NOT-A-BUG).
PRs: #368, #369, #370, #371, #372, #373.

Bumps VERSION 1.79.3 -> 1.80.0.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
itcmsgr added a commit that referenced this pull request Apr 13, 2026
v1.80 closes the structural truth-surface hardening line. Protection
state now fails correctly for broken kernel structure, empty required
chains, dead required runtime, schema drift, and duplicate schema
authority.

v1.80.0 does not change the effective detection/scoring model;
effectiveness tuning remains future work (BUG-1 / v1.81+).

Blockers closed: B80-1 through B80-8 + BUG-6 (NOT-A-BUG).
PRs: #368, #369, #370, #371, #372, #373.

Bumps VERSION 1.79.3 -> 1.80.0.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
itcmsgr added a commit that referenced this pull request Apr 13, 2026
v1.80 closes the structural truth-surface hardening line. Protection
state now fails correctly for broken kernel structure, empty required
chains, dead required runtime, schema drift, and duplicate schema
authority.

v1.80.0 does not change the effective detection/scoring model;
effectiveness tuning remains future work (BUG-1 / v1.81+).

Blockers closed: B80-1 through B80-8 + BUG-6 (NOT-A-BUG).
PRs: #368, #369, #370, #371, #372, #373.

Bumps VERSION 1.79.3 -> 1.80.0.

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
itcmsgr added a commit that referenced this pull request Apr 27, 2026
…ked files (#508)

Closes repo hygiene audit finding H-05: 3 internal-roadmap
references in tracked code/docs that are not resolvable by a
public reader.

Per locked rule "first verify the H-05 sites still apply, then
fix only confirmed live ones": each site was grep-verified in
the current tree before edit.

Changes:
- CHANGELOG.md (v1.80.0 release block) — drop trailing "Refs:"
  subsection pointing at V1.80_ROADMAP/MASTER_TODO.md. PR list
  (#371/#372/#373) above remains the canonical release record.
- cli/lib/nftban/core/nftban_ip_and_stats.sh:73 — remove sentence
  pointing at V1.80_ROADMAP/MASTER_TODO.md B80-1 discussion
  dated 2026-04-11. Replace with (B80-1) so the planning tag
  survives without the unresolvable file path.
- internal/loginmon/pipeline/doc.go:75 — remove (see DEC-1..9
  in MASTER_TODO.md) parenthetical from package doc. Surrounding
  sentence preserved.

Verification:
  git grep -nE "V1\.80_ROADMAP|MASTER_TODO\b" -- ":(exclude).claude/*"
  → empty after this PR.

Out of scope (deferred):
- H-07 / H-08 — version-sync (README badge, STATUS.md).
  Explicitly NOT in this slice (no version-sync work).
- H-09 / H-16 / H-19 — separate Phase A slices.

Lifecycle completion lane (PR-25..PR-30) remains explicitly OPEN.

Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
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.

1 participant