{"record":{"id":"83bf4dd4e804dbb9","repo":"nats-io/nats-server","slug":"stream-import-not-authorized","errorCode":null,"errorMessage":"stream import not authorized","messagePattern":"stream import not authorized","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server/errors.go","lineNumber":138,"sourceCode":"\tErrBadSampling = errors.New(\"bad sampling percentage, should be 1-100\")\n\n\t// ErrAccountValidation is returned when an account has failed validation.\n\tErrAccountValidation = errors.New(\"account validation failed\")\n\n\t// ErrAccountExpired is returned when an account has expired.\n\tErrAccountExpired = errors.New(\"account expired\")\n\n\t// ErrNoAccountResolver is returned when we attempt an update but do not have an account resolver.\n\tErrNoAccountResolver = errors.New(\"account resolver missing\")\n\n\t// ErrAccountResolverUpdateTooSoon is returned when we attempt an update too soon to last request.\n\tErrAccountResolverUpdateTooSoon = errors.New(\"account resolver update too soon\")\n\n\t// ErrAccountResolverSameClaims is returned when same claims have been fetched.\n\tErrAccountResolverSameClaims = errors.New(\"account resolver no new claims\")\n\n\t// ErrStreamImportAuthorization is returned when a stream import is not authorized.\n\tErrStreamImportAuthorization = errors.New(\"stream import not authorized\")\n\n\t// ErrStreamImportBadPrefix is returned when a stream import prefix contains wildcards.\n\tErrStreamImportBadPrefix = errors.New(\"stream import prefix can not contain wildcard tokens\")\n\n\t// ErrStreamImportDuplicate is returned when a stream import is a duplicate of one that already exists.\n\tErrStreamImportDuplicate = errors.New(\"stream import already exists\")\n\n\t// ErrServiceImportAuthorization is returned when a service import is not authorized.\n\tErrServiceImportAuthorization = errors.New(\"service import not authorized\")\n\n\t// ErrImportFormsCycle is returned when an import would form a cycle.\n\tErrImportFormsCycle = errors.New(\"import forms a cycle\")\n\n\t// ErrCycleSearchDepth is returned when we have exceeded our maximum search depth..\n\tErrCycleSearchDepth = errors.New(\"search cycle depth exhausted\")\n\n\t// ErrClientOrRouteConnectedToGatewayPort represents an error condition when\n\t// a client or route attempted to connect to the Gateway port.","sourceCodeStart":120,"sourceCodeEnd":156,"githubUrl":"https://github.com/nats-io/nats-server/blob/3a66a489d262bf89b71a71c955c94920394532f3/server/errors.go#L120-L156","documentation":"ErrStreamImportAuthorization is returned when a stream import is not authorized: the importing account has not authorized the subject being imported, i.e. account.checkStreamImportAuthorized fails for the source account, subject, and claim. The library refuses to add an import that the exporting account's exports/claims do not permit.","triggerScenarios":"AddStreamImport (both the standard and prefix variants at accounts.go:2711 and 2747) where the from-account's exports do not cover the subject or the export requires an activation token (imClaim) that is missing/invalid for this importing account.","commonSituations":"Importing a subject the other account never exported; using an activation token issued for a different account or subject; expired/revoked activation tokens; export marked private and no token supplied; subject pattern mismatch between export and import.","solutions":["Ensure the source account exports the subject (AddStreamExport or claim) and that the subject matches the import","If the export is private, generate a valid activation token for the importing account and pass it as the import claim","Regenerate expired/revoked activation tokens (nsc generate activation) and re-add the import","Verify account claims are up to date on both accounts before re-attempting the import"],"exampleFix":"// before\nacc.AddStreamImport(fooAcc, \"foo\", \"\") // fooAcc export is private, no token\n// after\ntok := genActivationFor(fooAcc, \"foo\", importAcc) // valid activation claim\nerr := importAcc.AddStreamImport(fooAcc, \"foo\", tok)","handlingStrategy":"validation","validationCode":"// before importing, confirm the export exists and covers the subject\nexports := fromAcc.Exports // via claims\nif !exportCoversSubject(exports, from) { return errors.New(\"subject not exported by source account\") }\nif isPrivateExport(exports, from) && imClaim == nil { return errors.New(\"private export requires activation token\") }","typeGuard":"func importAuthorized(from *Account, subject string, claim *jwt.ActivationClaims) bool {\n\treturn from.checkStreamImportAuthorized(fromAccCtx, subject, claim) == nil\n}","tryCatchPattern":"if err := acc.AddStreamImport(fromAcc, subject, tok); err != nil {\n\tif errors.Is(err, ErrStreamImportAuthorization) { /* regenerate activation token or fix exports */ }\n}","preventionTips":["Verify the source account exports the exact subject before importing","For private exports, always generate a fresh activation token for the importing account","Re-issue tokens after key rotation or revocation"],"tags":["nats","server","authorization","stream-import"],"backgroundTag":"authorization-denied","analyzedSha":"3a66a489d262bf89b71a71c955c94920394532f3","analyzedAt":"2026-09-02T04:41:54.247Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T15:18:49.778Z"}