Skip to content

fix: OpMeta Input computation requires bits - #260

Open
thedavidmeister wants to merge 1 commit into
mainfrom
2026-08-25-issue-171
Open

fix: OpMeta Input computation requires bits#260
thedavidmeister wants to merge 1 commit into
mainfrom
2026-08-25-issue-171

Conversation

@thedavidmeister

Copy link
Copy Markdown
Contributor

Closes #171.

What the issue claimed

Input's docs describe a discriminated union — constant inputs are counted by
parameters, computed inputs are discriminated by bits (+ optional
computation) — but validation was per-field only, so two contradictory shapes
validated. Only one of the two is actually a defect.

Fixed: computation without bits

{"computation": "bits + 1"} with no bits is a computation whose reserved
bits keyword reads operand bits that were never allocated. Input.bits and
Input.computation are both documented "Required only for computed
(non-constant) inputs", and the sibling Output type in the same file already
encodes exactly this as an enum whose Computed(BitIntegerRange, Computation)
cannot be split. Upstream's op meta JSON schema agrees on the output side:
ComputedOutput lists bits as required.

Input now carries a struct-level #[validate(schema(...))] that rejects
computation with no bits. The repro from the issue,
OpMeta::try_from(br#"{"name":"add","inputs":[{"computation":"bits + 1"}]}"#),
returns Err on this branch.

test_opmeta_input_computation_validated's "valid" arm was that exact repro
shape, so it gains the bits it was always missing; the rejection is pinned by
the new test_opmeta_input_computation_requires_bits.

Not fixed, because it is not a defect: parameters with bits

The issue also called {"parameters": [..], "bits": [0, 3]} contradictory. It
is not — it is the canonical shape of every dynamic-input opcode. In
rainlanguage/rain-metadata, schemas/op.meta.schema.json makes parameters
required on InputArgs with bits optional beside it, and the shipped
examples carry both:

"inputs": {
  "bits": [0, 7],
  "parameters": [{ "name": "input", "spread": true }]
}

(examples/op-meta/Add.op.meta.json; Call.op.meta.json is the same shape.)

InputParameter.spread — "Specifies if an argument is dynamic in length" — has
no valid use at all if a parameter may not sit beside bits, and the inputs
doc already resolves the count without ambiguity: bits present means the count
derives from the bits, not from parameters.len(). Rejecting that shape would
reject add and call. test_opmeta_input_parameters_alongside_bits_is_valid
pins it as accepted so it does not get "fixed" later.

Not touched

The ValidationErrors::merge_all misuse that drops nested errors is #173, still
open; the NOTE comments pointing at it are unchanged.

QA

  • Discriminating tests: test_opmeta_input_computation_requires_bits — fails on
    base (verified by restoring base behaviour in place: dropped the new
    #[validate(schema(function = "validate_input_computation"))] attribute from
    Input and re-ran cargo test -p rain-metadata --lib meta::types::op::v1
    13 passed; 1 failed, the failure being
    assertion failed: OpMeta::try_from(br#"{"name":"add","inputs":[{"computation":"bits + 1"}]}"#.to_vec()).is_err(),
    i.e. the issue's own repro). The other two test edits are regression pins, not
    discriminating, and pass on base by design:
    test_opmeta_input_parameters_alongside_bits_is_valid (guards the add/call
    spread shape against a future over-strict "fix") and the amended
    test_opmeta_input_computation_validated (its ok arm now supplies bits).
    Full module run on this branch: 14 passed; 0 failed.
  • Mutations applied:
    • #[validate(schema(function = "validate_input_computation"))] on Input
      attribute removed → killed by test_opmeta_input_computation_requires_bits.
    • if input.computation.is_some() && input.bits.is_none()
      if input.bits.is_none() (drop the computation guard, over-reject every
      constant input) → killed by test_input_parameter_spread_defaults_false
      (pre-existing test).
    • if input.computation.is_some() && input.bits.is_none()
      if input.computation.is_some() (drop the bits guard, reject legitimate
      computed inputs) → killed by test_opmeta_input_computation_validated.
  • Oracle: the doc comments on OpMeta.inputs, Input.bits and
    Input.computation in this file (the issue's own stated intent oracle),
    cross-checked against the upstream op meta v1 JSON schema
    rainlanguage/rain-metadata schemas/op.meta.schema.json (ComputedOutput
    requires bits; InputArgs requires parameters) and its shipped
    examples/op-meta/Add.op.meta.json / Call.op.meta.json. Expected values come
    from those documents, not from the Rust implementation.
  • Category check: the issue names two shapes — (A) computation with no bits,
    (B) parameters together with bits. A is covered and now rejected. B is
    covered as a finding rather than a change: it is refuted above with the
    upstream schema and examples, and pinned as valid by a test, because enforcing
    it would reject the real add and call op metas. The issue's own triage
    framing flagged it for a human call; the evidence answers it, and both halves
    are resolved, so this closes OpMeta Input allows contradictory computed/constant shapes (computation without bits, parameters with bits) #171.

An Input carrying `computation` with no `bits` is a computed input that
never allocated the operand bits its computation reads, so schema-level
validation now rejects it.

`parameters` alongside `bits` stays valid: it is the spread shape every
dynamic-input op meta ships.

Closes #171

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Aug 25, 2026

Copy link
Copy Markdown

Warning

Review limit reached

Next included review available in 20 seconds.

View limit details

Limit details: You’ve used the included review currently available.

You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository.

Learn how review limits work.

Review configuration:

⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: dcb5e72e-78c7-483b-92b5-94539903132c

📥 Commits

Reviewing files that changed from the base of the PR and between 45ca96c and 399cd18.

📒 Files selected for processing (1)
  • crates/cli/src/meta/types/op/v1.rs

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.

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.

OpMeta Input allows contradictory computed/constant shapes (computation without bits, parameters with bits)

1 participant