vitessio/vitess · error

cannot reserve variables with a '_' prefix

Error message

cannot reserve variables with a '_' prefix

What it means

NewReservedVars builds a reserved-variable normalizer that generates bind variable names with the given prefix. A '_' prefix is forbidden because Vitess internally uses underscore-prefixed names for its own hidden variables; using '_' as user prefix would collide with internal system-generated variables and break normalization.

Source

Thrown at go/vt/sqlparser/reserved_vars.go:168

			return bvar
		}
	}
}

// NewReservedVars allocates a ReservedVar instance that will generate unique
// variable names starting with the given `prefix` and making sure that they
// don't conflict with the given set of `known` variables.
func NewReservedVars(prefix string, known BindVars) *ReservedVars {
	rv := &ReservedVars{
		prefix:   prefix,
		counter:  0,
		reserved: known,
		fast:     true,
		next:     []byte(prefix),
	}

	if prefix != "" && prefix[0] == '_' {
		panic("cannot reserve variables with a '_' prefix")
	}

	for bvar := range known {
		if strings.HasPrefix(bvar, prefix) {
			rv.fast = false
			break
		}
	}

	if prefix == "vtg" {
		rv.static = true
	}
	return rv
}

View on GitHub (pinned to 01a25a7d17)

Solutions

  1. Use a non-underscore prefix, e.g. "vt" or "bv"
  2. Validate user-supplied prefixes for a leading '_' before calling NewReservedVars
  3. If you need hidden variables, use Vitess's dedicated internal variable mechanisms instead of the reserved-var prefix

Example fix

// before
rv := sqlparser.NewReservedVars("_v", known)
// after
rv := sqlparser.NewReservedVars("v", known)
Defensive patterns

Strategy: validation

Validate before calling

func safePrefix(p string) error {
    if strings.HasPrefix(p, "_") {
        return fmt.Errorf("prefix %q must not start with '_'", p)
    }
    return nil
}

Prevention

When it happens

Trigger: Calling NewReservedVars("_", known) or any prefix starting with '_' (e.g. "_vt", "_inner") in tests or code that builds a normalizer.

Common situations: Test authors picking an intuitive '_'-prefixed prefix for internal-looking bind variables; refactoring that passes user-supplied prefix strings straight into NewReservedVars.

Related errors


AI-assisted analysis of vitessio/vitess@01a25a7d17 (2026-09-01). Data as JSON: /api/errors/510171ea8ad14d1b. Report an issue: GitHub.