Skip to content

feat(sdk): add ScenarioBuilder class to OO-SDK#748

Open
sid-rl wants to merge 2 commits intomainfrom
siddarth/sdk-scenario-builder
Open

feat(sdk): add ScenarioBuilder class to OO-SDK#748
sid-rl wants to merge 2 commits intomainfrom
siddarth/sdk-scenario-builder

Conversation

@sid-rl
Copy link
Contributor

@sid-rl sid-rl commented Mar 19, 2026

CodeAnt-AI Description

Add a fluent ScenarioBuilder to construct and push scenarios from the SDK

What Changed

  • Expose a new ScenarioBuilder and a sdk.scenario.builder(name) entrypoint so callers can build scenario parameters with a chainable API instead of assembling raw objects.
  • Builder lets users set environment (blueprint or snapshot or working directory), problem statement, additional context, metadata, reference output, required env vars/secrets, validation type, and add multiple scorer types (test command, shell command, bash script, python script, AST-grep, custom).
  • Scorer weights are normalized to sum to 1.0; build() enforces required fields and throws clear errors if the problem statement is missing or no scorers are configured. push() validates, creates the scenario on the platform, and returns a Scenario instance.
  • Tests added to cover builder behavior, weight normalization, environment mutual exclusion (blueprint vs snapshot), validation errors, push() API calls, and integration in smoketests.

Impact

✅ Shorter scenario setup code
✅ Clearer validation errors when required fields are missing
✅ Fewer manual API calls to assemble and create scenarios

💡 Usage Guide

Checking Your Pull Request

Every time you make a pull request, our system automatically looks through it. We check for security issues, mistakes in how you're setting up your infrastructure, and common code problems. We do this to make sure your changes are solid and won't cause any trouble later.

Talking to CodeAnt AI

Got a question or need a hand with something in your pull request? You can easily get in touch with CodeAnt AI right here. Just type the following in a comment on your pull request, and replace "Your question here" with whatever you want to ask:

@codeant-ai ask: Your question here

This lets you have a chat with CodeAnt AI about your pull request, making it easier to understand and improve your code.

Example

@codeant-ai ask: Can you suggest a safer alternative to storing this secret?

Preserve Org Learnings with CodeAnt

You can record team preferences so CodeAnt AI applies them in future reviews. Reply directly to the specific CodeAnt AI suggestion (in the same thread) and replace "Your feedback here" with your input:

@codeant-ai: Your feedback here

This helps CodeAnt AI learn and adapt to your team's coding style and standards.

Example

@codeant-ai: Do not flag unused imports.

Retrigger review

Ask CodeAnt AI to review the PR again, by typing:

@codeant-ai: review

Check Your Repository Health

To analyze the health of your code repository, visit our dashboard at https://app.codeant.ai. This tool helps you identify potential issues and areas for improvement in your codebase, ensuring your repository maintains high standards of code health.

@codeant-ai
Copy link
Contributor

codeant-ai bot commented Mar 19, 2026

CodeAnt AI is reviewing your PR.


Thanks for using CodeAnt! 🎉

We're free for open-source projects. if you're enjoying it, help us grow by sharing.

Share on X ·
Reddit ·
LinkedIn

@sid-rl sid-rl changed the title add ScenarioBuilder class to OO-SDK feat(sdk): add ScenarioBuilder class to OO-SDK Mar 19, 2026
@sid-rl sid-rl requested review from alb-rl, dines-rl and james-rl March 19, 2026 00:56
@codeant-ai
Copy link
Contributor

codeant-ai bot commented Mar 19, 2026

Sequence Diagram

This PR adds a new fluent builder flow for creating scenarios from the OO SDK. Users can now start from sdk.scenario.builder(name), compose scenario settings and scorers, then push a validated payload to create and receive a Scenario object.

sequenceDiagram
    participant User
    participant ScenarioOps
    participant ScenarioBuilder
    participant ScenariosAPI
    participant Scenario

    User->>ScenarioOps: builder scenario name
    ScenarioOps-->>User: ScenarioBuilder instance
    User->>ScenarioBuilder: Configure problem environment and scorers
    User->>ScenarioBuilder: push
    ScenarioBuilder->>ScenariosAPI: Create scenario with built params
    ScenariosAPI-->>ScenarioBuilder: Created scenario id
    ScenarioBuilder-->>User: Scenario object from id
Loading

Generated by CodeAnt AI

@codeant-ai codeant-ai bot added the size:XL This PR changes 500-999 lines, ignoring generated files label Mar 19, 2026
@codeant-ai
Copy link
Contributor

codeant-ai bot commented Mar 19, 2026

Nitpicks 🔍

🔒 No security issues identified
⚡ Recommended areas for review

  • Missing module
    The new re-export references './scenario-builder'. Confirm that the module file exists at that path, is included in the package build output, and is exposed via package "exports" (if used). Also verify the file is added to source control and to any bundler/tsconfig include settings so consumers won't get a missing-module error.

  • Runtime vs Type export
    Ensure ScenarioBuilder is a runtime value (class/function/const). If './scenario-builder' only exports types, the re-export should use export type { ... }. Also verify whether './scenario-builder' uses a default export — a mismatch (named vs default) would cause runtime import failures for consumers.

  • Possible Circular Import
    A top-level import of ScenarioBuilder was added. This can create a runtime circular dependency if scenario-builder imports anything from this module (or other modules that import this file). Verify runtime import order and consider lazy-loading the builder to avoid circular- import initialization issues.

  • No runtime guard
    The builder method instantiates ScenarioBuilder directly. If the imported symbol is undefined at runtime (due to circular import), this will throw a less-informative TypeError. Add a defensive check or lazy import so the error is clearer and easier to recover from.

  • Environment parameters payload
    The environment parameters object is always created with keys blueprint_id, snapshot_id, and working_directory, but some values may be null. APIs often prefer omitting absent fields rather than sending null. Consider only including keys that have meaningful values to avoid unexpected server behavior.

Comment on lines +438 to +439
if (weight <= 0) {
throw new Error(`Scorer weight must be positive, got ${weight}`);
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggestion: addScorer only checks weight <= 0, which allows non-finite values like NaN and Infinity. Those values pass the check but break normalization in build() (s.weight / totalWeight), producing invalid weights (NaN) that will cause malformed scoring payloads and API failures. Validate that weight is finite before accepting it. [logic error]

Severity Level: Major ⚠️
- ❌ Scenario creation payload can contain null scorer weights.
- ⚠️ `runloop.scenario.builder(...).push()` may fail API validation.
Suggested change
if (weight <= 0) {
throw new Error(`Scorer weight must be positive, got ${weight}`);
if (!Number.isFinite(weight) || weight <= 0) {
throw new Error(`Scorer weight must be a finite positive number, got ${weight}`);
Steps of Reproduction ✅
1. Use the public OO-SDK entrypoint `ScenarioOps.builder()` at `src/sdk.ts:1988-1990` to
create a `ScenarioBuilder` instance (normal scenario creation flow exposed to users).

2. Add a scorer with a non-finite computed weight (for example `1/0` or `0/0`) through
`addTestCommandScorer()` at `src/sdk/scenario-builder.ts:156-170`, which forwards to
`addScorer()` at `src/sdk/scenario-builder.ts:437-442`.

3. In `addScorer()` (`src/sdk/scenario-builder.ts:438`), `if (weight <= 0)` does not
reject `NaN`/`Infinity`, so invalid weight is stored in `_scorers`.

4. Call `push()` (`src/sdk/scenario-builder.ts:431-434`) or `build()` (`:366-408`):
normalization computes `weight: s.weight / totalWeight` (`:378-382`), then request
serialization in `src/core.ts:335` uses `JSON.stringify`, which serializes non-finite
numbers to `null`, producing invalid scorer weights in `/v1/scenarios` create payload
(`src/resources/scenarios/scenarios.ts:37-39`).
Prompt for AI Agent 🤖
This is a comment left during a code review.

**Path:** src/sdk/scenario-builder.ts
**Line:** 438:439
**Comment:**
	*Logic Error: `addScorer` only checks `weight <= 0`, which allows non-finite values like `NaN` and `Infinity`. Those values pass the check but break normalization in `build()` (`s.weight / totalWeight`), producing invalid weights (`NaN`) that will cause malformed scoring payloads and API failures. Validate that weight is finite before accepting it.

Validate the correctness of the flagged issue. If correct, How can I resolve this? If you propose a fix, implement it and please make it concise.
👍 | 👎

@codeant-ai
Copy link
Contributor

codeant-ai bot commented Mar 19, 2026

CodeAnt AI finished reviewing your PR.

@github-actions
Copy link

github-actions bot commented Mar 19, 2026

❌ Object Smoke Tests Failed

Test Results

❌ Some smoke tests failed

Failed Tests:

  • smoketest: object-oriented devbox › devbox suspend and resume › suspend and resume devbox
  • smoketest: object-oriented devbox › devbox suspend and resume › resumeAsync - resume without waiting

Please fix the failing tests before checking coverage.

📋 View full test logs

@sid-rl sid-rl force-pushed the siddarth/sdk-scenario-builder branch from a4e4e2f to e6202b8 Compare March 19, 2026 01:21
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size:XL This PR changes 500-999 lines, ignoring generated files

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant