HKUDS/Vibe-Trading · error · ValueError

legs[{index}] has invalid strike or qty: {exc}

Error message

legs[{index}] has invalid strike or qty: {exc}

What it means

Thrown when a leg's strike or qty fails numeric conversion — the key is missing (KeyError), the value is a non-numeric string/list (TypeError/ValueError), or an enormous number overflows float conversion. The chained exception message carries the underlying conversion error.

Source

Thrown at agent/src/tools/options_payoff_tool.py:245

def _coerce_legs(raw: Any) -> list[OptionLeg]:
    """Parse and validate raw JSON-style leg objects."""
    if not isinstance(raw, list) or not raw:
        raise ValueError("legs must be a non-empty array")
    if len(raw) > _MAX_LEGS:
        raise ValueError(f"legs may contain at most {_MAX_LEGS} entries")

    legs: list[OptionLeg] = []
    for index, item in enumerate(raw):
        if not isinstance(item, dict):
            raise ValueError(f"legs[{index}] must be an object")
        option_type = str(item.get("option_type") or "").strip().lower()
        try:
            strike = float(item["strike"])
            raw_qty = item["qty"]
            qty_number = float(raw_qty)
        except (KeyError, TypeError, ValueError, OverflowError) as exc:
            raise ValueError(f"legs[{index}] has invalid strike or qty: {exc}") from exc
        if isinstance(raw_qty, bool) or not qty_number.is_integer():
            raise ValueError(f"legs[{index}].qty must be a non-zero integer")
        qty = int(qty_number)
        raw_premium = item.get("premium")
        try:
            premium = None if raw_premium is None else float(raw_premium)
        except (TypeError, ValueError, OverflowError) as exc:
            raise ValueError(f"legs[{index}].premium must be numeric or null") from exc
        legs.append(OptionLeg(option_type, strike, qty, premium))
    return legs


def _required_float(kwargs: dict[str, Any], name: str) -> float:
    """Read a required finite float."""
    if name not in kwargs or kwargs[name] is None or kwargs[name] == "":
        raise ValueError(f"{name} is required")
    try:
        value = float(kwargs[name])

View on GitHub (pinned to 80ffdda44c)

Solutions

  1. Ensure both strike and qty are present and numeric (strings like "100.5" are fine)
  2. Strip currency/separator formatting before passing: float(raw.replace(',',''))
  3. If fields come from user input, coerce and validate them in your own schema first

Example fix

// before
{"option_type": "call", "strike": "100 USD", "qty": "1"}
// after
{"option_type": "call", "strike": 100.0, "qty": 1}
Defensive patterns

Strategy: validation

Validate before calling

for leg in legs:
    for k in ("strike", "qty"):
        try:
            float(leg[k])
        except (KeyError, TypeError, ValueError):
            raise ValueError(f"leg field {k} missing/non-numeric: {leg}")

Type guard

def leg_numerics_ok(leg: dict) -> bool:
    try:
        float(leg["strike"]); float(leg["qty"])
        return True
    except (KeyError, TypeError, ValueError, OverflowError):
        return False

Try / catch

try:
    execute(kwargs)
except ValueError as e:
    if "invalid strike or qty" in str(e):
        highlight_bad_leg_to_user(e)

Prevention

When it happens

Trigger: leg missing the strike or qty key; strike="abc"; qty=[1]; qty=1e400 in raw text; qty=None. e.g. {"option_type":"call","strike":100} (no qty) triggers it.

Common situations: Handwritten JSON with typos or omitted fields; LLM-generated legs that drop qty; string numbers with currency symbols or commas ("1,000").

Related errors


AI-assisted analysis of HKUDS/Vibe-Trading@80ffdda44c (2026-08-28). Data as JSON: /api/errors/0be49f32aaf4af16. Report an issue: GitHub.