xai-org/x-algorithm · error · SemanticCheckFailure

variable %s cannot be defined: there is no scope

Error message

variable %s cannot be defined: there is no scope

What it means

defineVariable refuses to bind a variable when the scope stack has only the root scope (size <= 1), because variables must live in a nested scope (function body, lambda, let, etc.). The root scope only holds types and units, not user variables.

Source

Thrown at botmaker/src/java/com/twitter/botmaker/compiler/CompilerContext.java:257

  CompilerScope addScope() throws SemanticCheckFailure {
    CompilerScope scope =
        new CompilerScope(NEXT_CONTEXT_ID.getAndIncrement(), currentScope());
    scopeList.addFirst(scope);
    return scope;
  }

  void removeScope() {
    scopeList.removeFirst();
  }

  void defineVariable(
      String variableName,
      Type returnType,
      ASTNode astNode) throws SemanticCheckFailure {

    if (scopeList.size() <= 1) {
      throw new SemanticCheckFailure(
          String.format("variable %s cannot be defined: there is no scope", variableName));
    }

    CompilerScope currentScope = scopeList.getFirst();
    Parameter parameter = Parameter.variable(variableName, returnType, astNode);
    currentScope.defineVariable(parameter);
  }

  void defineVariable(
      String variableName,
      ASTNode astNode) throws SemanticCheckFailure {
    defineVariable(variableName, astNode.getReturnType(), astNode);
  }

  Variable getVariable(String variableText) throws SemanticCheckFailure {
    for (CompilerScope scope : scopeList) {
      if (scope.isVariableDefined(variableText)) {
        Parameter parameter = scope.getVariable(variableText);

View on GitHub (pinned to 24c60942c5)

Solutions

  1. Move the variable definition inside a function body, lambda, or with/let construct that creates a nested scope
  2. If writing a custom transform, emit an addScope() before defining variables

Example fix

// before
val x = 1  // at root scope
// after
fn f() { val x = 1; x }
Defensive patterns

Strategy: try-catch

Try / catch

catch (SemanticCheckFailure e) { /* message names the variable; move definition into a scoped construct */ }

Prevention

When it happens

Trigger: Calling defineVariable from toVal/toWith/toDerivedFeatureFunction when compiling at root level without having pushed a child scope, e.g. a val definition placed outside a function/module body in the DSL.

Common situations: Placing let/val bindings at the top level of an expression where the grammar technically allows it but semantics forbid it; custom DSL transforms emitting variable definitions at root.

Related errors


AI-assisted analysis of xai-org/x-algorithm@24c60942c5 (2026-08-28). Data as JSON: /api/errors/e5d4f5b566c22dc8. Report an issue: GitHub.