different-ai/openwork · error · InterpreterRuntimeError

String.${name} expects number arguments.

Error message

String.${name} expects number arguments.

What it means

String.fromCharCode and String.fromCodePoint require every argument to be a number (a char code / code point). CodeMode validates each argument before calling the host static and throws this error as soon as any argument is not a number.

Source

Thrown at packages/codemode/src/stdlib/string.ts:40

  "padEnd",
  "charAt",
  "charCodeAt",
  "codePointAt",
  "at",
  "concat",
  "toString",
  "match",
  "matchAll",
  "search",
  "localeCompare",
  "normalize",
])

export const stringStatics = new Set(["fromCharCode", "fromCodePoint"])

export const invokeStringStatic = (name: string, args: Array<unknown>, node: AstNode): unknown => {
  const codes = args.map((arg) => {
    if (typeof arg !== "number") throw new InterpreterRuntimeError(`String.${name} expects number arguments.`, node)
    return arg
  })
  switch (name) {
    case "fromCharCode":
      return String.fromCharCode(...codes)
    case "fromCodePoint":
      return String.fromCodePoint(...codes)
    default:
      throw new InterpreterRuntimeError(`String.${name} is not available in CodeMode.`, node)
  }
}
import { type AstNode, InterpreterRuntimeError } from "../interpreter/model.js"

View on GitHub (pinned to 2b7df46e8a)

Solutions

  1. Convert each argument with Number() before calling: `String.fromCharCode(Number(code))`.
  2. Filter/validate the input array: `codes.filter(c => typeof c === "number")` then spread.
  3. Fix the producer of the values to emit numbers.
  4. For array input, use `...codes.map(Number)` only after validating all elements.

Example fix

// before
String.fromCharCode(...rawCodes) // rawCodes[1] is "65"
// after
String.fromCharCode(...rawCodes.map((c) => Number(c)))
Defensive patterns

Strategy: validation

Validate before calling

const nums = args.map(Number)
if (nums.some((n) => typeof n !== "number" || Number.isNaN(n))) throw new TypeError("all args must be numbers")
String.fromCharCode(...nums)

Type guard

const isNumberArray = (a) => Array.isArray(a) && a.every((x) => typeof x === "number")

Try / catch

try { s = String.fromCharCode(...codes) } catch (e) { s = "" }

Prevention

When it happens

Trigger: `String.fromCharCode("65")`, `String.fromCodePoint(null)`, or an array spread of mixed/undefined values passed to either static.

Common situations: Data decoded from JSON keeps code points as strings; a code-point array contains undefined holes; accidental string/number confusion.

Related errors


AI-assisted analysis of different-ai/openwork@2b7df46e8a (2026-09-01). Data as JSON: /api/errors/d9bd2ff06293298a. Report an issue: GitHub.