DEM-PRODUCER-HTF fix: a venue that cannot serve the window is an absence, not a failure - #93
Merged
Merged
Conversation
…NCE, not a failure Found by the afi-gateway boundary proof (the one CI job that runs the reactor against the REAL coinbase feed): every submission 500'd after HTF merged. Cause, and why it is a real defect rather than a test-environment quirk: coinbase has no weekly bar (ccxt's own timeframes table), so the registered `1w` window's fetch threw and aborted the whole determination. Any coinbase-backed composition would have been permanently unscoreable in production too — which is not what the slot intended, and not what D-DEM-5(4)(b) means by a producer that "may legitimately not emit" a fact. The fix keeps the two cases strictly apart, because conflating them WOULD be the fall-back the owner's constraint forbids: - a timeframe the SELECTED VENUE does not offer is a CAPABILITY fact, known before any request is made: the window is not requested at all, no sub-block is emitted, and the registered mapping's declared `absent` member recodes it to neutral as a RECORDED default (D-DEM-5(4)(b)); - a fetch that FAILS for a timeframe the venue DOES offer is a real failure and still aborts the determination — fail closed, never fall back. - adapters/exchanges/types.ts: PriceFeedAdapter advertises `supportedTimeframes` (optional; absent = unknown, so every timeframe is attempted and nothing is silently skipped). The two ccxt adapters expose ccxt's own table; the deterministic test feed advertises the fixture timeframes. - technicalLocalAdapter: skips an unoffered window (logged), otherwise unchanged. - htfProducer.test.ts: three new cases — the unoffered window is never REQUESTED and lands as a declared absence; a fetch failure on an offered window still refuses; a feed with no capability table is treated as offering everything. - INTENTIONAL_DIFFS.md: recorded as residual (5) — a coinbase-backed composition scores weeklyBias=neutral permanently, capping its structure at 0.6. blofin (the production feed) offers both windows. Zero golden movement: goldens run on the deterministic feed, which offers both. 794/794 green; typecheck green. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Residual (5): a venue that does not offer a registered higher-timeframe window yields that bias as a declared absence for every signal it serves — coinbase has no weekly bar, so a coinbase-backed composition caps structure at 0.6; blofin (the production feed) offers both. The capability is checked before the request; a genuine fetch failure still refuses. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
|
Kilo Code Review could not run — your account is out of credits. Add credits or switch to a free model to enable reviews on this change. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What broke, and how it was found
The afi-gateway boundary proof — the one CI job that runs the reactor against the real coinbase feed — started returning 500 on every submission after the HTF slot merged.
Cause: coinbase has no weekly bar (ccxt's own
timeframestable), so the registered1wwindow's fetch threw and aborted the determination. This is not a test-environment quirk: any coinbase-backed composition would have been permanently unscoreable in production, which the slot never intended and which is not what D-DEM-5(4)(b) means by a producer that "may legitimately not emit" a fact.The fix keeps two cases strictly apart
Conflating them would be exactly the fall-back your constraint forbids:
absentmember recodes it to neutral as a recorded default;PriceFeedAdapternow advertisessupportedTimeframes(optional — absent means unknown, so every timeframe is attempted and nothing is silently skipped). The two ccxt adapters expose ccxt's own table.Recorded, not hidden
INTENTIONAL_DIFFS.mdgains residual (5): a coinbase-backed composition scoresweeklyBias = neutralpermanently, capping its structure at 0.6. blofin — the production feed — offers both1dand1w, so production is unaffected.Three new tests: the unoffered window is never requested and lands as a declared absence; a fetch failure on an offered window still refuses; a feed with no capability table is treated as offering everything. Zero golden movement (the goldens run on the deterministic feed, which offers both windows). 794/794 green.
🤖 Generated with Claude Code