cayleygraph/cayley · error
Unexpected type for @id %T
Error message
Unexpected type for @id %T
What it means
normalizeQuads in match.go:142 inspects a Match pattern's "@id" field to synthesize a single-entity quad when the pattern produces no quads of its own. If the "@id" value is not a Go string, this error is thrown (note: the message prints idString's type, which equals id's type). It indicates the pattern's @id was supplied as a non-string JSON value.
Source
Thrown at query/linkedql/steps/match.go:142
patternClone := linkedql.GraphPattern{
"@context": context,
}
for key, value := range pattern {
patternClone[key] = value
}
return pattern
}
func quadsFromMap(o interface{}) ([]quad.Quad, error) {
reader := jsonld.NewReaderFromMap(o)
return quad.ReadAll(reader)
}
func normalizeQuads(quads []quad.Quad, pattern linkedql.GraphPattern) ([]quad.Quad, error) {
if id, ok := pattern["@id"]; ok && len(quads) == 0 {
idString, ok := id.(string)
if !ok {
return nil, fmt.Errorf("Unexpected type for @id %T", idString)
}
quads = append(quads, makeSingleEntityQuad(quad.IRI(idString)))
}
return quads, nil
}
func parsePattern(pattern linkedql.GraphPattern, ns *voc.Namespaces) ([]quad.Quad, error) {
contextualizedPattern := contextualizePattern(pattern, ns)
quads, err := quadsFromMap(contextualizedPattern)
if err != nil {
return nil, err
}
quads, err = normalizeQuads(quads, contextualizedPattern)
if err != nil {
return nil, err
}
if len(quads) == 0 && len(pattern) != 0 {
return nil, fmt.Errorf("Pattern does not parse to any quad. `{}` is the only pattern allowed to not parse to any quad")View on GitHub (pinned to 81dcd7d73e)
Solutions
- Set the pattern's @id to a plain string IRI.
- If @id comes from user JSON, coerce/validate it as string before constructing the GraphPattern.
- Check the %T in the message to identify which wrong type was supplied.
Example fix
// before
pattern := linkedql.GraphPattern{"@id": 42}
// after
pattern := linkedql.GraphPattern{"@id": "http://example.org/entity/42"} Defensive patterns
Strategy: validation
Validate before calling
id, ok := pattern["@id"]
if ok {
if _, isStr := id.(string); !isStr {
return fmt.Errorf("@id must be a string, got %T", id)
}
} Type guard
func idString(pattern map[string]interface{}) (string, bool) {
id, ok := pattern["@id"]
if !ok { return "", false }
s, ok := id.(string)
return s, ok
} Try / catch
quads, err := parsePattern(pattern, ctx)
if err != nil {
if strings.Contains(err.Error(), "Unexpected type for @id") {
// fix pattern construction: @id must be string
}
return err
} Prevention
- Always assign string IRIs to @id
- Validate user-supplied JSON so @id is coerced to string or rejected early
- Use typed constructors for GraphPattern fields where available
When it happens
Trigger: Building a linkedql Match / GraphPattern with "@id" set to a number, bool, map, or slice instead of a string, e.g. via unmarshalled JSON where @id was numeric.
Common situations: Programmatic pattern construction with the wrong Go type, or JSON queries where @id was written unquoted.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Expected %#v to be a map or a slice with a single map but in
- No matching values for the item %#v in %#v
- Unexpected type
- must execute a Step
- must execute a IteratorStep or PathStep
AI-assisted analysis of cayleygraph/cayley@81dcd7d73e (2026-09-06).
Data as JSON: /api/errors/f9bc65a6a5be3710.
Report an issue: GitHub.