Skip to content

fix(alpha): bind evaluation protocol evidence - #46

Merged
proerror77 merged 4 commits into
mainfrom
codex/alpha-evaluation-protocol-binding
Jul 15, 2026
Merged

fix(alpha): bind evaluation protocol evidence#46
proerror77 merged 4 commits into
mainfrom
codex/alpha-evaluation-protocol-binding

Conversation

@proerror77

@proerror77 proerror77 commented Jul 15, 2026

Copy link
Copy Markdown
Owner

Outcome

Binds every walk-forward, sealed-holdout, promotion, and strategy-bundle artifact to one versioned evaluation protocol hash so IC/RankIC/ICIR/RankICIR and post-cost Sharpe evidence cannot be reused under different splits, costs, label horizons, or metric definitions.

What changed

  • adds EvaluationProtocolV1 covering walk-forward split/purge/embargo/holdout, fee/funding/latency costs, label horizon/frequency, and ICIR/Sharpe definitions
  • verifies protocol hash across candidate evaluation, sealed evaluation registry payload, promotion record, strategy bundle, store readback, and live deployment artifacts
  • keeps legacy evidence readable while making it ineligible for validation/promotion (fail closed)
  • makes same-protocol sealed reruns idempotent and rejects any protocol drift without partial promotion state
  • verifies mission materialization metadata matches the requested label horizon and bucket frequency

Verification

  • cargo test -p alpha-domain --locked — 32 passed
  • cargo test -p alpha-engine --no-default-features --locked — 41 passed, 1 ignored live test
  • strict Clippy for alpha-domain + alpha-engine — passed
  • targeted fmt check — passed
  • git diff --check — passed

Full store/app/ONNX/live verification is intentionally delegated to GitHub CI / the Aliyun research plane to avoid a local bundled-DuckDB rebuild.

Summary by CodeRabbit

  • New Features

    • Added explicit evaluation protocol settings for dataset labeling, observation frequency, walk-forward validation, costs, and metrics.
    • CLI commands now accept label-horizon and observation-frequency parameters.
    • Evaluation and deployment evidence now records a protocol hash for traceability and integrity.
  • Bug Fixes

    • Added validation to reject mismatched dataset costs, materialization settings, or evaluation protocols.
    • Promotion and sealed-evaluation reuse now reject incompatible or non-canonical evidence.
  • Documentation

    • Updated CLI examples and clarified evaluation protocol definitions, including unannualized Sharpe calculations.

@coderabbitai

coderabbitai Bot commented Jul 15, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@proerror77, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 54 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 8c3a349a-2d21-4583-82d2-3098884d98cf

📥 Commits

Reviewing files that changed from the base of the PR and between 0b45e92 and e86d4b1.

📒 Files selected for processing (17)
  • rust_hft/alpha-harness/README.md
  • rust_hft/alpha-harness/app/src/cli.rs
  • rust_hft/alpha-harness/app/src/data_mission.rs
  • rust_hft/alpha-harness/app/src/governance.rs
  • rust_hft/alpha-harness/app/src/loop_control.rs
  • rust_hft/alpha-harness/app/src/mission.rs
  • rust_hft/alpha-harness/app/src/mission_runner.rs
  • rust_hft/alpha-harness/domain/src/lib.rs
  • rust_hft/alpha-harness/engine/Cargo.toml
  • rust_hft/alpha-harness/engine/src/engines/mod.rs
  • rust_hft/alpha-harness/engine/src/evaluation.rs
  • rust_hft/alpha-harness/engine/src/lib.rs
  • rust_hft/alpha-harness/onnx-evaluator/src/lib.rs
  • rust_hft/alpha-harness/store/Cargo.toml
  • rust_hft/alpha-harness/store/src/lib.rs
  • rust_hft/tools/collector/src/feature_matrix.rs
  • rust_hft/tools/collector/src/lib.rs
📝 Walkthrough

Walkthrough

The change introduces a versioned evaluation protocol, derives it from CLI validation settings, propagates it through dataset and evaluator flows, and binds its hash into candidate evidence, sealed evaluations, strategy bundles, and promotion records.

Changes

Evaluation protocol binding

Layer / File(s) Summary
Protocol contracts and CLI validation
rust_hft/alpha-harness/domain/src/lib.rs, rust_hft/alpha-harness/app/src/cli.rs, rust_hft/alpha-harness/app/src/mission_runner.rs
Adds EvaluationProtocolV1, protocol hashing and validation, CLI protocol construction, and materialization checks for label horizon and observation frequency.
Protocol-aware dataset and evaluator flow
rust_hft/alpha-harness/engine/*, rust_hft/alpha-harness/onnx-evaluator/src/lib.rs
Passes evaluation protocols through prepared datasets, engine contexts, formula evaluation, and ONNX evaluation while validating costs and ranges.
Application execution and evidence wiring
rust_hft/alpha-harness/app/src/mission.rs, rust_hft/alpha-harness/app/src/governance.rs, rust_hft/alpha-harness/app/src/loop_control.rs
Uses validation-derived protocols during mission and governance execution and records protocol hashes in sealed evidence and promotion payloads.
Canonical evidence and promotion checks
rust_hft/alpha-harness/store/src/lib.rs
Requires walk-forward, sealed evaluation, strategy bundle, and promotion protocol hashes to match during candidate selection and promotion.
Documentation and deployment fixtures
rust_hft/alpha-harness/README.md, rust_hft/apps/live/tests/*
Updates CLI examples and evaluation documentation, and adds protocol hashes to deployment bundle fixtures.

Estimated code review effort: 4 (Complex) | ~60 minutes

Sequence Diagram(s)

sequenceDiagram
  participant CLI as ValidationArgs
  participant Dataset as PreparedDataset
  participant Evaluator as FormulaEvaluator
  participant Evidence as CandidateEvaluation
  participant Store
  participant Bundle as StrategyBundle
  CLI->>Dataset: create protocol and prepare dataset
  Dataset->>Evaluator: provide protocol and rows
  Evaluator->>Evidence: emit evaluation and protocol hash
  Store->>Evidence: validate canonical walk-forward evidence
  Store->>Bundle: require matching evaluation_protocol_hash
Loading

Possibly related PRs

  • proerror77/monday#12: Updates overlapping sealed and canonical evidence checks in the governance and store paths.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 33.78% 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
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly matches the main change: binding evaluation protocol evidence across the alpha harness.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/alpha-evaluation-protocol-binding

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🧹 Nitpick comments (1)
rust_hft/alpha-harness/engine/src/evaluation.rs (1)

184-194: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Dead re-check + misleading error message after protocol.validate().

protocol.validate() (domain/src/lib.rs) already rejects zero initial_train_rows/validation_rows/fold_count/sealed_holdout_rows as part of its own || chain, so by the time control reaches Line 188 these four conditions can never be true — the explicit re-check is dead code. Additionally, map_err(|_| EvaluationError::InvalidConfiguration) discards the actual DomainError reason, so a protocol rejected for a negative cost, zero label horizon, or version mismatch is reported with the walk-forward-specific message "walk-forward configuration must use positive train, validation, holdout, and fold sizes", which is misleading for debugging.

♻️ Proposed cleanup
     protocol
         .validate()
         .map_err(|_| EvaluationError::InvalidConfiguration)?;
     let config = &protocol.walk_forward;
-    if config.initial_train_rows == 0
-        || config.validation_rows == 0
-        || config.fold_count == 0
-        || config.sealed_holdout_rows == 0
-    {
-        return Err(EvaluationError::InvalidConfiguration);
-    }
     if rows.iter().any(|row| {

Consider also giving EvaluationError::InvalidConfiguration a payload (or adding a dedicated variant) so the underlying DomainError message isn't discarded, e.g. InvalidConfiguration(String) populated from error.to_string().

🤖 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 `@rust_hft/alpha-harness/engine/src/evaluation.rs` around lines 184 - 194,
Remove the redundant zero-value check after protocol.validate() in the
evaluation flow, including the walk-forward-specific error return. Preserve the
validation error’s underlying DomainError details by updating the
protocol.validate() map_err handling and, if needed, the
EvaluationError::InvalidConfiguration definition and its consumers to carry or
otherwise expose the original message.
🤖 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.

Nitpick comments:
In `@rust_hft/alpha-harness/engine/src/evaluation.rs`:
- Around line 184-194: Remove the redundant zero-value check after
protocol.validate() in the evaluation flow, including the walk-forward-specific
error return. Preserve the validation error’s underlying DomainError details by
updating the protocol.validate() map_err handling and, if needed, the
EvaluationError::InvalidConfiguration definition and its consumers to carry or
otherwise expose the original message.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: b4ec5698-68e6-4449-9bc0-48ad6e5a30f3

📥 Commits

Reviewing files that changed from the base of the PR and between 2b82d59 and 0b45e92.

📒 Files selected for processing (17)
  • rust_hft/alpha-harness/README.md
  • rust_hft/alpha-harness/app/src/cli.rs
  • rust_hft/alpha-harness/app/src/governance.rs
  • rust_hft/alpha-harness/app/src/loop_control.rs
  • rust_hft/alpha-harness/app/src/mission.rs
  • rust_hft/alpha-harness/app/src/mission_runner.rs
  • rust_hft/alpha-harness/domain/src/lib.rs
  • rust_hft/alpha-harness/engine/src/engines/bayesian.rs
  • rust_hft/alpha-harness/engine/src/engines/mcts.rs
  • rust_hft/alpha-harness/engine/src/engines/mod.rs
  • rust_hft/alpha-harness/engine/src/evaluation.rs
  • rust_hft/alpha-harness/engine/src/formula_evaluator.rs
  • rust_hft/alpha-harness/engine/src/lib.rs
  • rust_hft/alpha-harness/onnx-evaluator/src/lib.rs
  • rust_hft/alpha-harness/store/src/lib.rs
  • rust_hft/apps/live/tests/deployment_artifacts.rs
  • rust_hft/apps/live/tests/deployment_envelope.rs

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 0b45e92ede

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

.sum::<f64>()
/ self.metrics.folds.len().max(1) as f64;
if self.evaluator_version.trim().is_empty()
if self.protocol_binding().is_err()

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P1 Badge Allow legacy v3 observations to replay

When resuming a mission that already has purged-walk-forward-v3 evaluations written before this change, serde defaults both new protocol fields to None, and AutoResearchKernel::historical_evaluation still calls validate() for non-v2 observations. This new unconditional protocol check therefore makes mission run/resume fail before proposing any new candidates, even though legacy records only need to be replayed for search state and should fail closed for validation/promotion; please tolerate or skip protocol-less legacy observations in the historical replay path.

Useful? React with 👍 / 👎.

Comment on lines +184 to +186
protocol
.validate()
.map_err(|_| EvaluationError::InvalidConfiguration)?;

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Validate label metadata before binding it

For standalone mission run/evaluate on OHLCV or imported feature manifests, the loaded ResearchRows do not carry any horizon or bucket-frequency metadata (the OHLCV loader derives a one-bar-ahead label), so accepting any protocol after only protocol.validate() lets evidence be minted with arbitrary label_horizon_buckets and observation_frequency_millis values that do not describe the actual labels. This undermines the new protocol hash for label definitions outside the durable materialization path; please verify the label spec against dataset metadata or reject datasets whose label spec cannot be proven.

Useful? React with 👍 / 👎.

Comment on lines +624 to +626
if protocol.content_hash()? != protocol_hash {
return Err(DomainError::InvalidEvaluationEvidence);
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Tie protocol splits to metric dimensions

If a malformed or hand-registered evaluation payload reaches the store, validate() now checks that the protocol hash matches the embedded protocol but never checks that the metrics were actually produced with that protocol’s split sizes. A walk-forward payload with two 30-row folds can therefore claim a protocol with a different fold_count or validation_rows and still be accepted by promotion as long as the sealed payload uses the same hash; please reject protocol/metric dimension mismatches in CandidateEvaluation::validate().

Useful? React with 👍 / 👎.

#[test]
fn bundle_staging_cleans_up_on_persistence_failure_without_partial_output() {
let (promotion, bundle) = promotion_fixture();
let directory = std::env::temp_dir().join(format!(
#[test]
fn conflicting_bundle_output_is_rejected_before_any_overwrite() {
let (_, bundle) = promotion_fixture();
let directory = std::env::temp_dir().join(format!(
let mut second = first.clone();
second.candidate_content_hash = "f".repeat(64);
second.bundle_hash = second.calculated_hash().unwrap();
let directory = std::env::temp_dir().join(format!(
let model_bytes = b"shared-onnx-model";
let (first, second) = conflicting_onnx_bundles_for_shared_model(model_bytes);

let directory = std::env::temp_dir().join(format!(
fn bundle_conflict_keeps_a_shared_model_referenced_by_the_winner() {
let model_bytes = b"shared-onnx-model";
let (first, second) = conflicting_onnx_bundles_for_shared_model(model_bytes);
let directory = std::env::temp_dir().join(format!(
@proerror77
proerror77 force-pushed the codex/alpha-evaluation-protocol-binding branch from 20ad1cd to dcf002f Compare July 15, 2026 22:46
@proerror77
proerror77 force-pushed the codex/alpha-evaluation-protocol-binding branch from dcf002f to e86d4b1 Compare July 15, 2026 23:20
@proerror77

Copy link
Copy Markdown
Owner Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: e86d4b1aa7

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

&candidate_iteration,
&candidate_artifact,
)?
|| walk_forward_protocol_hash.as_deref() != Some(sealed_protocol_hash)

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Require the mission protocol binding before advancing holdout

When a store has matching walk-forward and sealed evaluations but no mission_evaluation_protocol registry row (for example, evidence imported or written before the new binding was frozen), this helper still returns the candidate because it only compares the two evidence hashes to each other. progress_completed_mission uses this result to mark HoldoutPassed, so a LoopRun can advance on evidence that promote_candidate now correctly rejects as missing the immutable mission protocol binding. Please also require the mission binding hash to exist and equal sealed_protocol_hash here.

Useful? React with 👍 / 👎.

Comment on lines +279 to +282
if materialization.bucket_ms != validation.observation_frequency_millis
|| materialization.label_horizon_buckets != validation.label_horizon_buckets
{
bail!("evaluation label horizon or frequency does not match the materialization");

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Validate the protocol before creating Mission artifacts

For mission execute with a materialization horizon larger than the default purge (e.g. the LOB materializer default label_horizon_buckets = 5 while --purge-rows defaults to 1), this check passes because it only compares the supplied label facts, but ValidationArgs::evaluation_protocol later rejects purge_rows < horizon_buckets. By then execute has already imported the feature manifest and created the research mission in the result DB, so a bad protocol leaves partial artifacts instead of failing up front; construct/validate the EvaluationProtocolV1 here before any store writes.

Useful? React with 👍 / 👎.

@proerror77
proerror77 merged commit c39e28c into main Jul 15, 2026
20 checks passed
@proerror77
proerror77 deleted the codex/alpha-evaluation-protocol-binding branch July 16, 2026 08:19
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.

2 participants