Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
43 changes: 43 additions & 0 deletions src/api/providers/__tests__/bedrock-custom-arn.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,32 @@ describe("Bedrock ARN Handling", () => {
expect(result.crossRegionInference).toBe(false)
})

it("should correctly extract modelType and modelId from application-inference-profile ARN", () => {
const handler = createHandler()
const arn =
"arn:aws:bedrock:eu-west-1:123456789012:application-inference-profile/abcd1234-ef56-7890-abcd-ef1234567890"

const result = (handler as any).parseArn(arn, "eu-west-1")

expect(result.isValid).toBe(true)
expect(result.modelType).toBe("application-inference-profile")
expect(result.modelId).toBe("abcd1234-ef56-7890-abcd-ef1234567890")
expect(result.region).toBe("eu-west-1")
expect(result.crossRegionInference).toBe(false)
})

it("should correctly parse application-inference-profile ARN with alphanumeric profile ID", () => {
const handler = createHandler()
const arn = "arn:aws:bedrock:us-west-2:123456789012:application-inference-profile/my-custom-profile"

const result = (handler as any).parseArn(arn, "us-west-2")

expect(result.isValid).toBe(true)
expect(result.modelType).toBe("application-inference-profile")
expect(result.modelId).toBe("my-custom-profile")
expect(result.crossRegionInference).toBe(false)
})

it("should return isValid: false for simple ARN format", () => {
const handler = createHandler()
const arn = "arn:aws:bedrock:us-east-1:123456789012:some-other-resource"
Expand Down Expand Up @@ -228,6 +254,23 @@ describe("Bedrock ARN Handling", () => {
expect((handler as any).client.config.region).toBe("eu-west-1")
})

it("should use full ARN as model ID for application-inference-profile ARNs", () => {
const arn =
"arn:aws:bedrock:eu-west-1:123456789012:application-inference-profile/abcd1234-ef56-7890-abcd-ef1234567890"
const handler = createHandler({
awsCustomArn: arn,
awsRegion: "eu-west-1",
})

const model = handler.getModel()

// For application-inference-profile ARNs, the full ARN should be used as the model ID
expect(model.id).toBe(arn)
expect(model.info).toHaveProperty("maxTokens")
expect(model.info).toHaveProperty("contextWindow")
expect(model.info.supportsImages).toBe(true)
})

it("should log region mismatch warning when ARN region differs from provided region", () => {
// Spy on logger.info which is called when there's a region mismatch
const infoSpy = vitest.spyOn(logger, "info")
Expand Down
16 changes: 15 additions & 1 deletion src/api/providers/bedrock.ts
Original file line number Diff line number Diff line change
Expand Up @@ -923,6 +923,7 @@ export class AwsBedrockHandler extends BaseProvider implements SingleCompletionH
* - Prompt Router: arn:aws:bedrock:us-west-2:123456789012:prompt-router/anthropic-claude
* - Inference Profile: arn:aws:bedrock:us-west-2:123456789012:inference-profile/anthropic.claude-v2
* - Cross Region Inference Profile: arn:aws:bedrock:us-west-2:123456789012:inference-profile/us.anthropic.claude-3-5-sonnet-20241022-v2:0
* - Application Inference Profile: arn:aws:bedrock:eu-west-1:123456789012:application-inference-profile/my-profile-id
* - Custom Model (Provisioned Throughput): arn:aws:bedrock:us-west-2:123456789012:provisioned-model/my-custom-model
* - Imported Model: arn:aws:bedrock:us-west-2:123456789012:imported-model/my-imported-model
*
Expand Down Expand Up @@ -1025,6 +1026,18 @@ export class AwsBedrockHandler extends BaseProvider implements SingleCompletionH
id: bedrockDefaultPromptRouterModelId,
info: JSON.parse(JSON.stringify(bedrockModels[bedrockDefaultPromptRouterModelId])),
}
} else if (modelType === "application-inference-profile") {
// Application inference profiles use opaque IDs (often UUIDs) that don't reveal the underlying model.
// Provide reasonable defaults assuming the underlying model is likely a modern Claude model,
// since that's the most common use case for Bedrock application inference profiles.
model = {
id: bedrockDefaultModelId,
info: {
...JSON.parse(JSON.stringify(bedrockModels[bedrockDefaultModelId])),
supportsImages: true,
supportsPromptCache: false,
},
}
} else {
// Use heuristics for model info, then allow overrides from ProviderSettings
const guessed = this.guessModelInfoFromId(modelId)
Expand Down Expand Up @@ -1318,7 +1331,8 @@ Please verify:
2. If using an ARN, verify the ARN is correct and points to a valid model
3. Your AWS credentials have permission to access this model (check IAM policies)
4. The region in the ARN matches the region where the model is deployed
5. If using a provisioned model, ensure it's active and not in a failed state`,
5. If using a provisioned model, ensure it's active and not in a failed state
6. If using an application inference profile, enter the full ARN in the "Custom ARN" field (not the model selector)`,
logLevel: "error",
},
NOT_FOUND: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ export const BedrockCustomArn = ({ apiConfiguration, setApiConfigurationField }:
<li>
arn:aws:bedrock:eu-west-1:123456789012:inference-profile/eu.anthropic.claude-3-7-sonnet-20250219-v1:0
</li>
<li>arn:aws:bedrock:eu-west-1:123456789012:application-inference-profile/your-profile-id</li>
<li>arn:aws:bedrock:us-west-2:123456789012:provisioned-model/my-provisioned-model</li>
<li>arn:aws:bedrock:us-east-1:123456789012:default-prompt-router/anthropic.claude:1</li>
</ul>
Expand Down
Loading