Skip to content

feat(research): gate MCTS on authenticated cohorts - #387

Merged
proerror77 merged 2 commits into
mainfrom
codex/mission-v3-mcts-324-authenticated
Jul 26, 2026
Merged

feat(research): gate MCTS on authenticated cohorts#387
proerror77 merged 2 commits into
mainfrom
codex/mission-v3-mcts-324-authenticated

Conversation

@proerror77

@proerror77 proerror77 commented Jul 26, 2026

Copy link
Copy Markdown
Owner

Change contract

Allow the shared prediction MCTS runner to consume only a freshly verified authenticated snapshot partition, preserve catalog order, exclude crossing events, release held-out rows only after a durable selected checkpoint, bind the immutable evaluator image across resumes, and durably stage task-isolated held-out evaluator evidence.

Out of scope

Typed receipts are intentionally a dependent #324 layer: execution and publication remain separate merge and rollback units. A separate PRD is unnecessary because issue #324 already defines the approved parent behavior contract.

Dependency / merge order

Focused validation

  • cargo test -p ploy-research --lib --no-default-features: 339 passed.
  • cargo clippy -p ploy-research --all-targets --no-default-features --no-deps -- -D warnings.
  • cargo fmt -p ploy-research -- --check.
  • git diff --check.
  • 717 additions across 9 files against origin/main, below the 750-line guardrail.
  • Counterexamples cover reduced-tree exhaustion, selection/checkpoint mismatch, immutable-image resume drift, missing/unassigned partition markets, and held-out access before selection.
  • Independent correctness review is clean; scope review is satisfied by this explicit execution-only contract.

Rollout / rollback impact

No runtime, result-publication, or collector rollout. The new evaluator trait is sealed, so this layer cannot be invoked by an external evaluator before the trusted built-in implementation lands. Rollback is this PR only; legacy MCTS behavior remains unchanged.

@coderabbitai

coderabbitai Bot commented Jul 26, 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: 29 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 Plus

Run ID: c844bcd8-b1b7-4f66-83fa-6c7b0d42a18f

📥 Commits

Reviewing files that changed from the base of the PR and between 5a4c6ae and 0945626.

📒 Files selected for processing (5)
  • rust_hft/prediction-markets/config/research_missions/polymarket-btc-5m.example.json
  • rust_hft/prediction-markets/config/research_missions/polymarket-sol-5m.example.json
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_run.rs
📝 Walkthrough

Walkthrough

The change adds authenticated Mission V3 prediction-MCTS execution, validates sealed mission and snapshot identities, partitions authenticated snapshots into training and held-out views, and publishes content-addressed receipt evidence. It also updates policy fingerprints and example mission snapshot identifiers.

Changes

Authenticated MCTS

Layer / File(s) Summary
Mission and snapshot identity validation
rust_hft/prediction-markets/crates/ploy-research/src/prediction_mission_v3.rs, rust_hft/prediction-markets/crates/ploy-research/src/research_snapshot.rs
Mission authentication now binds the current policy snapshot, and authenticated snapshot readback verifies sealed-cache state and manifest identities.
Admitted mission MCTS execution
rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts.rs, rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_run.rs
MCTS construction validates admitted Mission V3 compatibility, while durable execution separates admitted inputs from legacy bridges and exposes selection evidence.
Authenticated partitions and receipts
rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs
Authenticated snapshot views, evaluator adaptation, held-out validation, and task-scoped content-addressed receipts are implemented and tested.
Policy fingerprint and configuration wiring
rust_hft/prediction-markets/crates/ploy-research/src/lib.rs, rust_hft/prediction-markets/crates/ploy-research/src/prediction_loop.rs, rust_hft/prediction-markets/config/research_missions/*.json
The new module contributes to the policy fingerprint, and BTC/SOL example missions use updated policy snapshot identifiers.

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

Sequence Diagram(s)

sequenceDiagram
  participant MissionV3
  participant AuthenticatedTrial
  participant PredictionMctsEngine
  participant AuthenticatedRunner
  participant ReceiptStore

  MissionV3->>AuthenticatedTrial: validate admitted mission and snapshot identity
  AuthenticatedTrial->>AuthenticatedTrial: build training and held-out partitions
  AuthenticatedTrial->>PredictionMctsEngine: construct admitted MCTS engine
  AuthenticatedTrial->>AuthenticatedRunner: run or resume authenticated trial
  AuthenticatedRunner-->>AuthenticatedTrial: return selection and evaluator evidence
  AuthenticatedTrial->>ReceiptStore: publish content-addressed receipt reference
Loading

Possibly related PRs

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 28.57% 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
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.
Title check ✅ Passed The title is concise and accurately reflects the authenticated-cohort MCTS gating change.
Description check ✅ Passed Most required sections are present and specific; the scope exception section should be simplified to None per the template.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/mission-v3-mcts-324-authenticated

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.

@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: fc572108f0

ℹ️ 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".

Comment thread rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_run.rs Outdated
@proerror77
proerror77 force-pushed the codex/mission-v3-mcts-324-authenticated branch from fc57210 to 5a4c6ae Compare July 26, 2026 16:56

@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 (2)
rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs (2)

449-482: 🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Consider grouping rows once instead of rescanning per market.

snapshot_view scans all observations and all pm_book_snapshots once per market id, and authenticated_snapshot_views calls it twice (train + held-out), so cost grows as markets x rows. Fine for the three-event fixture, but it becomes the dominant cost on a real cohort. A single grouping pass keyed by event_id, then indexed lookup in catalog order, preserves the existing ordering and error semantics.

♻️ Sketch: group once, then index in catalog order
 fn snapshot_view(
     snapshot: &ResearchSnapshot,
     ordered_market_ids: &[String],
 ) -> Result<AuthenticatedTrainingSnapshot, String> {
+    let mut observations_by_market: BTreeMap<&str, Vec<&FactorObservation>> = BTreeMap::new();
+    for row in &snapshot.observations {
+        observations_by_market
+            .entry(row.event_id.as_str())
+            .or_default()
+            .push(row);
+    }
+    let mut books_by_market: BTreeMap<&str, Vec<&ResearchPmBookSnapshot>> = BTreeMap::new();
+    for row in &snapshot.pm_book_snapshots {
+        books_by_market
+            .entry(row.event_id.as_str())
+            .or_default()
+            .push(row);
+    }
     let mut observations = Vec::new();
     let mut pm_book_snapshots = Vec::new();
     for market_id in ordered_market_ids {
-        let before = observations.len();
-        observations.extend(
-            snapshot
-                .observations
-                .iter()
-                .filter(|row| row.event_id == *market_id)
-                .cloned(),
-        );
-        if observations.len() == before {
-            return Err(format!(
-                "authenticated snapshot has no observations for {market_id}"
-            ));
-        }
-        pm_book_snapshots.extend(
-            snapshot
-                .pm_book_snapshots
-                .iter()
-                .filter(|row| row.event_id == *market_id)
-                .cloned(),
-        );
+        let rows = observations_by_market
+            .get(market_id.as_str())
+            .ok_or_else(|| {
+                format!("authenticated snapshot has no observations for {market_id}")
+            })?;
+        observations.extend(rows.iter().copied().cloned());
+        if let Some(books) = books_by_market.get(market_id.as_str()) {
+            pm_book_snapshots.extend(books.iter().copied().cloned());
+        }
     }
🤖 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/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs`
around lines 449 - 482, Optimize snapshot_view by grouping observations and
pm_book_snapshots once by event_id, then assembling both output collections by
looking up each market_id in ordered_market_ids. Preserve catalog-order
grouping, cloned rows, and the existing error when a market has no observations,
while avoiding per-market rescans of the full snapshot collections.

508-533: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add a counterexample for the receipt namespace guard.

The two partition counterexamples are here, but the entrypoint's two other fail-closed branches — "authenticated receipt exists before held-out completion" (Line 296) and "authenticated receipt escaped its task namespace" (Line 303) — have no test. A small tmpdir fixture that writes an authenticated-receipt-ref.json pointing outside task_dir/receipts would pin the namespace guard without needing a full evaluator.

🤖 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/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs`
around lines 508 - 533, Add a focused test in the existing tests module for the
authenticated receipt namespace guard in the entrypoint logic, covering a
receipt reference that resolves outside task_dir/receipts and asserting the
operation fails closed. Use a temporary-directory fixture to create the task
directory and authenticated-receipt-ref.json pointing to an external receipt,
without constructing a full evaluator; also preserve coverage for the existing
pre-held-out-completion rejection branch if needed by the surrounding test
setup.
🤖 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/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs`:
- Around line 449-482: Optimize snapshot_view by grouping observations and
pm_book_snapshots once by event_id, then assembling both output collections by
looking up each market_id in ordered_market_ids. Preserve catalog-order
grouping, cloned rows, and the existing error when a market has no observations,
while avoiding per-market rescans of the full snapshot collections.
- Around line 508-533: Add a focused test in the existing tests module for the
authenticated receipt namespace guard in the entrypoint logic, covering a
receipt reference that resolves outside task_dir/receipts and asserting the
operation fails closed. Use a temporary-directory fixture to create the task
directory and authenticated-receipt-ref.json pointing to an external receipt,
without constructing a full evaluator; also preserve coverage for the existing
pre-held-out-completion rejection branch if needed by the surrounding test
setup.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 9f82570b-7350-423d-8a7d-e9a748d57079

📥 Commits

Reviewing files that changed from the base of the PR and between 9b42fe8 and 5a4c6ae.

📒 Files selected for processing (9)
  • rust_hft/prediction-markets/config/research_missions/polymarket-btc-5m.example.json
  • rust_hft/prediction-markets/config/research_missions/polymarket-sol-5m.example.json
  • rust_hft/prediction-markets/crates/ploy-research/src/lib.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_loop.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_authenticated.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mcts_run.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/prediction_mission_v3.rs
  • rust_hft/prediction-markets/crates/ploy-research/src/research_snapshot.rs

@proerror77
proerror77 merged commit dc49e2f into main Jul 26, 2026
40 checks passed
@proerror77
proerror77 deleted the codex/mission-v3-mcts-324-authenticated branch July 26, 2026 17: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.

1 participant