{"record":{"id":"764dccda90ee3b95","repo":"cayleygraph/cayley","slug":"not-a-nosql-database-t","errorCode":null,"errorMessage":"not a nosql database: %T","messagePattern":"not a nosql database: %T","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"graph/nosql/shapes.go","lineNumber":45,"sourceCode":"\tcase shape.Composite:\n\t\tif s2, opt := s.Simplify().Optimize(ctx, qs); opt {\n\t\t\treturn s2, true\n\t\t}\n\t}\n\treturn s, false\n}\n\n// Shape is a shape representing a documents query with filters\ntype Shape struct {\n\tCollection string              // name of the collection\n\tFilters    []nosql.FieldFilter // filters to select documents\n\tLimit      int64               // limits a number of documents\n}\n\nfunc (s Shape) BuildIterator(qs graph.QuadStore) iterator.Shape {\n\tdb, ok := qs.(*QuadStore)\n\tif !ok {\n\t\treturn iterator.NewError(fmt.Errorf(\"not a nosql database: %T\", qs))\n\t}\n\treturn db.newIterator(s.Collection, s.Filters...)\n}\n\nfunc (s Shape) Optimize(ctx context.Context, r shape.Optimizer) (shape.Shape, bool) {\n\treturn s, false\n}\n\n// Quads is a shape representing a quads query\ntype Quads struct {\n\tLinks []Linkage // filters to select quads\n\tLimit int64     // limits a number of documents\n}\n\nfunc (s Quads) BuildIterator(qs graph.QuadStore) iterator.Shape {\n\tdb, ok := qs.(*QuadStore)\n\tif !ok {\n\t\treturn iterator.NewError(fmt.Errorf(\"not a nosql database: %T\", qs))","sourceCodeStart":27,"sourceCodeEnd":63,"githubUrl":"https://github.com/cayleygraph/cayley/blob/81dcd7d73e45136bc0d01802a8ba4685d8a533eb/graph/nosql/shapes.go#L27-L63","documentation":"nosql.Shape.BuildIterator requires the passed graph.QuadStore to be the concrete *nosql.QuadStore. Any other backend (memory, kv-wrapped stores, a mock) cannot execute nosql shape queries, so an iterator.Error carrying this message is returned instead of panicking.","triggerScenarios":"Calling shapes.Shape{...}.BuildIterator(qs) (or running a query via buildIterator) with a QuadStore that is not the nosql wrapper — e.g. qs came from graph.NewQuadStore(\"memstore\", ...) instead of nosql.","commonSituations":"Mixing backends: opening a memstore or generic KV store but issuing nosql-specific shape queries; tests that pass a fake QuadStore.","solutions":["Open the database through the nosql-backed backend so BuildIterator receives *nosql.QuadStore","Check which backend your config selected (storage flag) before issuing nosql shapes","Wrap the returned iterator with error handling — the error surfaces as iterator.NewError, not a panic","Use the backend-agnostic iterator APIs if you must support multiple QuadStore implementations"],"exampleFix":"// before\nit := nosql.Shape{Collection: \"quads\"}.BuildIterator(qs)\n// after\nif _, ok := qs.(*nosql.QuadStore); !ok {\n    return nil, fmt.Errorf(\"nosql shapes need a nosql QuadStore, got %T\", qs)\n}\nit := nosql.Shape{Collection: \"quads\"}.BuildIterator(qs)","handlingStrategy":"type-guard","validationCode":"if _, ok := qs.(*nosql.QuadStore); !ok { return fmt.Errorf(\"BuildIterator needs *nosql.QuadStore, got %T\", qs) }","typeGuard":"func asNoSQL(qs graph.QuadStore) (*nosql.QuadStore, bool) { s, ok := qs.(*nosql.QuadStore); return s, ok }","tryCatchPattern":"it := shape.BuildIterator(qs)\nif itErr := iterator.AsError(it); itErr != nil { // error-iterator check\n    return fmt.Errorf(\"iterator setup failed: %v\", itErr)\n}","preventionTips":["Match the query API to the backend you opened","Check the storage backend name in your config","Use nosql shapes only with nosql-backed stores","Fail fast with your own type assertion for clearer messages"],"tags":["iterator","wrong-backend","type-assertion"],"backgroundTag":"incompatible-source-type","analyzedSha":"81dcd7d73e45136bc0d01802a8ba4685d8a533eb","analyzedAt":"2026-09-06T06:14:12.358Z","contentChangedAt":"2026-09-06T06:14:12.358Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}