{"record":{"id":"6071aa0a3dbfe762","repo":"gastownhall/beads","slug":"list-dep-metadata-sourceid-must-not-be-empty","errorCode":null,"errorMessage":"list dep metadata: sourceID must not be empty","messagePattern":"list dep metadata: sourceID must not be empty","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/storage/domain/dependency.go","lineNumber":519,"sourceCode":"func (u *dependencyUseCaseImpl) ListByWispIDs(ctx context.Context, wispIDs []string, filter DepListFilter) (DepBulkResult, error) {\n\treturn u.list(ctx, wispIDs, filter, true)\n}\n\nfunc (u *dependencyUseCaseImpl) ListWispWithIssueMetadata(ctx context.Context, wispID string, filter DepListFilter) ([]*types.IssueWithDependencyMetadata, error) {\n\treturn u.listWithMetadata(ctx, wispID, filter, true)\n}\n\nfunc (u *dependencyUseCaseImpl) IterWispWithIssueMetadata(ctx context.Context, wispID string, filter DepListFilter) (storage.Iter[types.IssueWithDependencyMetadata], error) {\n\treturn u.iterWithMetadata(ctx, wispID, filter, true)\n}\n\nfunc (u *dependencyUseCaseImpl) CountByWispID(ctx context.Context, wispID string, filter DepListFilter) (int64, error) {\n\treturn u.countByID(ctx, wispID, filter, true)\n}\n\nfunc (u *dependencyUseCaseImpl) listWithMetadata(ctx context.Context, sourceID string, filter DepListFilter, useWisp bool) ([]*types.IssueWithDependencyMetadata, error) {\n\tif sourceID == \"\" {\n\t\treturn nil, fmt.Errorf(\"list dep metadata: sourceID must not be empty\")\n\t}\n\tout, err := u.depRepo.ListWithIssueMetadata(ctx, sourceID, DepListOpts{\n\t\tTypes:         filter.Types,\n\t\tDirection:     filter.Direction,\n\t\tUseWispsTable: useWisp,\n\t})\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"list dep metadata: %w\", err)\n\t}\n\treturn out, nil\n}\n\nfunc (u *dependencyUseCaseImpl) iterWithMetadata(ctx context.Context, sourceID string, filter DepListFilter, useWisp bool) (storage.Iter[types.IssueWithDependencyMetadata], error) {\n\tif sourceID == \"\" {\n\t\treturn nil, fmt.Errorf(\"iter dep metadata: sourceID must not be empty\")\n\t}\n\tit, err := u.depRepo.IterWithIssueMetadata(ctx, sourceID, DepListOpts{\n\t\tTypes:         filter.Types,","sourceCodeStart":501,"sourceCodeEnd":537,"githubUrl":"https://github.com/gastownhall/beads/blob/71377f276968b452ee607177637970a4ff888584/internal/storage/domain/dependency.go#L501-L537","documentation":"Validation guard in listWithMetadata: the source issue ID whose dependency metadata is being listed is empty. Rather than issuing a doomed repository call, the use-case returns this explicit validation error.","triggerScenarios":"Calling ListWithIssueMetadata or ListWispWithIssueMetadata with sourceID == \"\".","commonSituations":"Caller constructed an issue struct whose ID field was never populated (issue not yet persisted); a lookup returned empty and its value was passed through unguarded; string-typed ID variables defaulting to zero value.","solutions":["Ensure the source issue is created/persisted and its ID fetched before listing metadata","Add a caller-side empty check before invoking the list APIs","Trace where the empty ID originates (usually an unsaved record or failed lookup)","Use the issue object returned from Create/Get rather than a locally built struct"],"exampleFix":"// before\nmetas, err := u.ListWithIssueMetadata(ctx, issue.ID, filter) // issue.ID == \"\"\n// after\nif issue.ID == \"\" {\n\treturn fmt.Errorf(\"issue not persisted\")\n}\nmetas, err := u.ListWithIssueMetadata(ctx, issue.ID, filter)","handlingStrategy":"validation","validationCode":"if sourceID == \"\" {\n\treturn fmt.Errorf(\"cannot list dep metadata: source ID is empty\")\n}","typeGuard":"func hasID(id string) bool { return id != \"\" }","tryCatchPattern":"metas, err := u.ListWithIssueMetadata(ctx, sourceID, filter)\nif err != nil && strings.Contains(err.Error(), \"sourceID must not be empty\") {\n\t// caller bug: fix the ID source, not retryable\n}","preventionTips":["Never pass IDs from structs that were not persisted via Create","Check the return value of Get/Create before using its ID field","Add empty-ID assertions at service boundaries","Treat this error as a caller bug — do not retry"],"tags":["validation","dependency","empty-id"],"backgroundTag":"empty-required-id","analyzedSha":"71377f276968b452ee607177637970a4ff888584","analyzedAt":"2026-08-30T18:55:39.744Z","schemaVersion":2},"datasetVersion":"2026-08-30T23:17:21.991Z"}