{"record":{"id":"c284c88815a06f86","repo":"goharbor/harbor","slug":"the-resource-cannot-be-null-c284c8","errorCode":null,"errorMessage":"the resource cannot be null","messagePattern":"the resource cannot be null","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/pkg/reg/adapter/quay/adapter.go","lineNumber":155,"sourceCode":"\t\t\t},\n\t\t},\n\t\tSupportedTriggers: []string{\n\t\t\tmodel.TriggerTypeManual,\n\t\t\tmodel.TriggerTypeScheduled,\n\t\t},\n\t}, nil\n}\n\n// PrepareForPush does the prepare work that needed for pushing/uploading the resource\n// eg: create the namespace or repository\nfunc (a *adapter) PrepareForPush(resources []*model.Resource) error {\n\tif !a.autoCreateNs {\n\t\treturn nil\n\t}\n\tnamespaces := []string{}\n\tfor _, resource := range resources {\n\t\tif resource == nil {\n\t\t\treturn errors.New(\"the resource cannot be null\")\n\t\t}\n\t\tif resource.Metadata == nil {\n\t\t\treturn errors.New(\"the metadata of resource cannot be null\")\n\t\t}\n\t\tif resource.Metadata.Repository == nil {\n\t\t\treturn errors.New(\"the namespace of resource cannot be null\")\n\t\t}\n\t\tif len(resource.Metadata.Repository.Name) == 0 {\n\t\t\treturn errors.New(\"the name of the namespace cannot be null\")\n\t\t}\n\t\tpaths := strings.Split(resource.Metadata.Repository.Name, \"/\")\n\t\tnamespace := paths[0]\n\t\tnamespaces = append(namespaces, namespace)\n\t}\n\n\tfor _, namespace := range namespaces {\n\t\terr := a.createNamespace(&model.Namespace{\n\t\t\tName: namespace,","sourceCodeStart":137,"sourceCodeEnd":173,"githubUrl":"https://github.com/goharbor/harbor/blob/7b2fd08cc568955cca339afeefab27372840d936/src/pkg/reg/adapter/quay/adapter.go#L137-L173","documentation":"Returned by the Quay adapter's PrepareForPush (src/pkg/reg/adapter/quay/adapter.go:155), which pre-creates namespaces when autoCreateNs is enabled. It rejects a nil *model.Resource element in the slice before touching resource.Metadata, because the next line dereferences it.","triggerScenarios":"Calling quay PrepareForPush with a slice containing a nil entry while the adapter was created with auto-namespace-creation enabled (registry endpoint configured for auto creating namespaces).","commonSituations":"Custom replication pipelines appending nil placeholders on fetch failure; slices built by appending conditional results; refactoring that introduces sparse resources.","solutions":["Fix the slice construction: never append nil; abort or skip-and-log the whole element on fetch error.","Pre-validate resources (see validationCode) to identify the index of the nil entry.","Note the guard only runs when autoCreateNs is true — if you do not need namespace auto-creation, configure the Quay endpoint without it, but the nil entry is still a caller bug worth fixing.","Add a unit test asserting no nil elements in the pipeline output."],"exampleFix":"// before\nvar resources []*model.Resource\nfor _, art := range arts {\n    if art == nil {\n        resources = append(resources, nil)\n    }\n}\n\n// after\nvar resources []*model.Resource\nfor _, art := range arts {\n    if art == nil {\n        continue // or return an error\n    }\n    resources = append(resources, art)\n}","handlingStrategy":"validation","validationCode":"for i, r := range resources {\n\tif r == nil {\n\t\treturn fmt.Errorf(\"resources[%d] is nil\", i)\n\t}\n}\n// optional: skip guard entirely by configuring the Quay endpoint without auto namespace creation","typeGuard":"func nonNilResources(rs []*model.Resource) bool {\n\tfor _, r := range rs {\n\t\tif r == nil {\n\t\t\treturn false\n\t\t}\n\t}\n\treturn true\n}","tryCatchPattern":"if err := a.PrepareForPush(resources); err != nil {\n\tif strings.Contains(err.Error(), \"the resource cannot be null\") {\n\t\t// nil element in slice: fix construction, filter nils\n\t}\n\treturn err\n}","preventionTips":["Never append nil; abort or skip-and-log the element.","Validate the slice before adapter calls.","Prefer creating Quay namespaces out-of-band if you disable autoCreateNs."],"tags":["go","quay","replication","validation","nil-check"],"backgroundTag":null,"analyzedSha":"7b2fd08cc568955cca339afeefab27372840d936","analyzedAt":"2026-08-16T00:00:10.961Z","schemaVersion":2},"datasetVersion":"2026-08-16T03:17:38.424Z"}