cayleygraph/cayley · error
can not parse %#v as a literal
Error message
can not parse %#v as a literal
What it means
parseLiteral converts a decoded JSON value into a quad.Value. It accepts plain scalars (string, number, bool) and JSON-LD value objects (maps with @value, optionally @language or @type). When the input matches none of these shapes it cannot be represented as a literal and this error is returned.
Source
Thrown at query/linkedql/registry.go:302
case float64:
i := int64(a)
if a == float64(i) {
return quad.Int(i), nil
}
return quad.Float(a), nil
case bool:
return quad.Bool(a), nil
case map[string]interface{}:
if val, ok := a["@value"].(string); ok {
if lang, ok := a["@language"].(string); ok {
return quad.LangString{Value: quad.String(val), Lang: lang}, nil
}
if typ, ok := a["@type"].(string); ok {
return quad.TypedString{Value: quad.String(val), Type: quad.IRI(typ)}, nil
}
}
}
return nil, fmt.Errorf("can not parse %#v as a literal", a)
}
func parseValue(a interface{}) (quad.Value, error) {
identifierString, err := parseIdentifierString(a)
if err == nil {
identifier, err := parseIdentifier(identifierString)
if err == nil {
return identifier, nil
}
}
lit, err := parseLiteral(a)
if err == nil {
return lit, nil
}
return nil, fmt.Errorf("can not parse JSON-LD value: %#v", a)
}
View on GitHub (pinned to 81dcd7d73e)
Solutions
- Pass a plain scalar (string, number, boolean) instead of an array or bare map.
- For typed/lang values, use the exact JSON-LD shape: {"@value": "...", "@type": "..."} or {"@value": "...", "@language": "en"}.
- If the value is a node reference, give it an "@id" so it parses as an identifier instead of reaching parseLiteral.
- For lists, expand them into multiple triples/steps rather than a single array literal.
Example fix
// before
{"@type": "http://www.w3.org/2001/XMLSchema#integer"} // missing @value
// after
{"@value": "42", "@type": "http://www.w3.org/2001/XMLSchema#integer"} Defensive patterns
Strategy: validation
Validate before calling
func isLiteralShape(v interface{}) bool {
switch v.(type) {
case string, float64, bool, int, int64:
return true
case map[string]interface{}:
_, ok := v.(map[string]interface{})["@value"]
return ok
}
return false
} Type guard
func asValueObject(v interface{}) (map[string]interface{}, bool) {
m, ok := v.(map[string]interface{})
if !ok { return nil, false }
_, has := m["@value"]
return m, has
} Try / catch
val, err := parseLiteral(v)
if err != nil && strings.Contains(err.Error(), "can not parse") {
return fmt.Errorf("literal fields accept scalars or {@value,...} objects, got %T", v)
} Prevention
- Never pass arrays or null where a single literal is expected — expand lists into multiple triples.
- Spell JSON-LD keywords exactly: "@value", "@type", "@language".
- Pre-validate step documents against the JSON-LD data model before registry calls.
When it happens
Trigger: parseValue falling through to parseLiteral with arrays, nested maps without @value, or nil — e.g. passing a JSON array as a step's object value, or a value object missing the required "@value" key.
Common situations: Authoring step documents with list-valued properties (RDF has no native list literal); value objects that use "@values" or misspell "@value"; nested node references where a literal was expected; null values in data sources.
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
- can not parse JSON-LD identifier: %#v
- unexpected type: %T
- blank node ID must start with "_:"
- expected a @id key
- cannot count iterator without a valid context
AI-assisted analysis of cayleygraph/cayley@81dcd7d73e (2026-09-06).
Data as JSON: /api/errors/147c92355a43793e.
Report an issue: GitHub.