{"record":{"id":"1ffff739e6631302","repo":"alibaba/open-code-review","slug":"bedrock-denied-access-to-model-q-s-w-crede","errorCode":null,"errorMessage":"bedrock denied access to model %q (%s): %w\n  credentials resolved, so this is an authorization gap: the identity needs bedrock:InvokeModel on this model in this region, and the account needs model access enabled for it","messagePattern":"bedrock denied access to model %q \\((.+?)\\): %w\n  credentials resolved, so this is an authorization gap: the identity needs bedrock:InvokeModel on this model in this region, and the account needs model access enabled for it","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/llm/client.go","lineNumber":1131,"sourceCode":"\t\t\t\"  model access is granted per account and per region in the Bedrock console; an IAM policy alone does not enable it\", model, where, err)\n\tcase strings.Contains(msg, \"model identifier is invalid\"),\n\t\tstrings.Contains(msg, \"inference profile\") && strings.Contains(msg, \"not found\"):\n\t\treturn fmt.Errorf(\"bedrock rejected model %q (%s): %w\\n\"+\n\t\t\t\"  run `aws bedrock list-inference-profiles%s` to see what this account offers — IDs are account- and region-scoped, and a version suffix such as -v1:0 is invalid for the newer families\",\n\t\t\tmodel, where, err, listProfilesRegionArg(c.awsRegion))\n\t// Specific credential codes only. A bare \"expired\" would also claim an\n\t// expired TLS certificate is an SSO problem.\n\tcase strings.Contains(msg, \"ExpiredToken\"), strings.Contains(msg, \"ExpiredTokenException\"),\n\t\tstrings.Contains(msg, \"SSOProviderInvalidToken\"), strings.Contains(msg, \"InvalidGrantException\"),\n\t\tstrings.Contains(msg, \"NoCredentialProviders\"), strings.Contains(msg, \"failed to refresh cached credentials\"):\n\t\treturn fmt.Errorf(\"bedrock could not authenticate: AWS credentials are expired or unavailable (%s): %w\\n\"+\n\t\t\t\"  run `aws sso login%s`, or refresh whichever credential source this profile uses\", where, err, ssoLoginProfileArg(c.awsProfile))\n\t// \"not authorized to invoke this API operation\" is IAM's own wording, so it\n\t// belongs here rather than in the model-access branch above: the fix is a\n\t// policy change, not a console toggle.\n\tcase strings.Contains(msg, \"AccessDenied\"),\n\t\tstrings.Contains(msg, \"not authorized to invoke this API operation\"):\n\t\treturn fmt.Errorf(\"bedrock denied access to model %q (%s): %w\\n\"+\n\t\t\t\"  credentials resolved, so this is an authorization gap: the identity needs bedrock:InvokeModel on this model in this region, and the account needs model access enabled for it\", model, where, err)\n\t}\n\t// Everything else — ValidationException on max_tokens, a network reset, a\n\t// throttle — keeps the service's own wording. Guessing at a cause here would\n\t// send people after the wrong problem, which is the failure this function\n\t// exists to prevent.\n\treturn fmt.Errorf(\"bedrock request failed (%s): %w\", where, err)\n}\n\nfunc listProfilesRegionArg(region string) string {\n\tif region == \"\" {\n\t\treturn \"\"\n\t}\n\treturn \" --region \" + region\n}\n\n// anthropicThinkingBudgetTokens extracts budget_tokens from an\n// extra_body.thinking map. Returns ok=false for unrecognized shapes.","sourceCodeStart":1113,"sourceCodeEnd":1149,"githubUrl":"https://github.com/alibaba/open-code-review/blob/5cf97d0d15cbd41b602513c4be3bfec3cee5bf7f/internal/llm/client.go#L1113-L1149","documentation":"explainError (internal/llm/client.go:1131) is the last Bedrock branch: it matches AccessDenied and IAM's 'not authorized to invoke this API operation' wording — but only after the model-access branch, so reaching here means credentials resolved and account model access is enabled, yet the calling identity's IAM policy lacks bedrock:InvokeModel. The rewrite states this is an authorization gap requiring a policy change, not a console toggle.","triggerScenarios":"InvokeModel on a bedrock-runtime endpoint where the authenticated role/user's IAM policy lacks bedrock:InvokeModel (or bedrock:InvokeModelWithResponseStream) for that model ID/region, or a scoped-down Resource element excludes the model/inference-profile ARN.","commonSituations":"Deployed CI role with an S3-only policy used for reviews; wildcard model ARN replaced with a narrowed one that misses the new model; SCP or permission boundary stripping InvokeModel; inference-profile ARN not covered by the policy's Resource list.","solutions":["Attach an IAM policy granting bedrock:InvokeModel (and InvokeModelWithResponseStream) on the model/inference-profile ARNs in that region","If Resources are enumerated, add the missing model ARN and cross-region inference profile ARNs (us.anthropic.*, etc.)","Check for a permissions boundary or SCP denying bedrock:InvokeModel and get it adjusted","Verify with the IAM Policy Simulator or `aws iam simulate-principal-policy` for the exact action and ARN"],"exampleFix":"// before\n{\"Effect\":\"Allow\",\"Action\":\"bedrock:InvokeModel\",\"Resource\":\"arn:aws:bedrock:us-east-1::foundation-model/anthropic.claude-3-*\"}  # new model not matched\n// after\n{\"Effect\":\"Allow\",\"Action\":[\"bedrock:InvokeModel\",\"bedrock:InvokeModelWithResponseStream\"],\"Resource\":[\"arn:aws:bedrock:*::foundation-model/anthropic.*\",\"arn:aws:bedrock:*:<acct>:inference-profile/us.anthropic.*\"]}","handlingStrategy":"validation","validationCode":"out, err := exec.Command(\"aws\", \"iam\", \"simulate-principal-policy\",\n    \"--policy-source-arn\", roleArn,\n    \"--action-names\", \"bedrock:InvokeModel\",\n    \"--resource-arns\", modelArn).Output()\nif err != nil || !strings.Contains(string(out), \"allowed\") {\n    return fmt.Errorf(\"%s lacks bedrock:InvokeModel on %s\", roleArn, modelArn)\n}","typeGuard":null,"tryCatchPattern":"_, err := cl.Call(ctx, messages)\nif err != nil && strings.Contains(err.Error(), \"denied access to model\") {\n    return fmt.Errorf(\"add bedrock:InvokeModel for %s in %s to the calling identity's policy: %w\", modelID, region, err)\n}","preventionTips":["Grant bedrock:InvokeModel (and WithResponseStream) on model and inference-profile ARNs to the roles that review code","When narrowing Resource lists, include region-prefixed inference profile ARNs (us.anthropic.*)","Check permissions boundaries and SCPs for bedrock denies when onboarding new accounts","Run the IAM Policy Simulator after policy changes before deploying"],"tags":["aws","bedrock","iam","authorization","access-denied"],"backgroundTag":"access-denied-iam","analyzedSha":"5cf97d0d15cbd41b602513c4be3bfec3cee5bf7f","analyzedAt":"2026-09-02T02:08:09.116Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}