fix(client): update AWS credential handling to prefer BEDROCK_AWS_* environment variables (#937)

This commit is contained in:
Mattsson
2026-07-08 18:09:34 +02:00
committed by GitHub
parent b10cf2ec23
commit ae489cfdcb
3 changed files with 43 additions and 16 deletions
+15 -9
View File
@@ -1729,15 +1729,21 @@ export default function JournalEntryForm({
{t('clear_all')}
</Button>
)}
<Button
variant="outline"
onClick={handleSaveDraft}
disabled={!isBalanced || !description || !selectedPeriod || !!periodMismatch || isSubmitting || isSavingDraft || isUploading || !canWrite}
title={!canWrite ? t('read_only_tooltip') : t('save_draft_tooltip')}
>
{!canWrite ? <Lock className="mr-2 h-4 w-4" /> : isSavingDraft && <Loader2 className="mr-2 h-4 w-4 animate-spin" />}
{t('save_draft')}
</Button>
{/* Draft-saving rides on ?as_draft=true, which only the standard
journal-entries endpoint honors. A custom submitUrl (e.g. the
bank-transaction /book route) ignores the flag and commits a
numbered voucher, so the draft button must not render there. */}
{!submitUrl && (
<Button
variant="outline"
onClick={handleSaveDraft}
disabled={!isBalanced || !description || !selectedPeriod || !!periodMismatch || isSubmitting || isSavingDraft || isUploading || !canWrite}
title={!canWrite ? t('read_only_tooltip') : t('save_draft_tooltip')}
>
{!canWrite ? <Lock className="mr-2 h-4 w-4" /> : isSavingDraft && <Loader2 className="mr-2 h-4 w-4 animate-spin" />}
{t('save_draft')}
</Button>
)}
<Button
onClick={handleReview}
disabled={!isBalanced || !description || !selectedPeriod || !!periodMismatch || isSubmitting || isSavingDraft || isUploading || !canWrite}
@@ -246,7 +246,18 @@ export async function extractInvoiceFields(
return { data: emptyResult(), rawText: null }
}
if (!process.env.AWS_ACCESS_KEY_ID || !process.env.AWS_SECRET_ACCESS_KEY) {
// Prefer BEDROCK_AWS_* over the plain AWS_* names: on Vercel/Lambda the
// platform injects its own reserved AWS_* execution-role vars that shadow
// whatever is configured, so a hosted deploy must use the BEDROCK_AWS_* names
// (see lib/agent/composer/client.ts for the full explanation).
const awsRegion =
process.env.BEDROCK_AWS_REGION || process.env.AWS_REGION || 'eu-north-1'
const awsAccessKey =
process.env.BEDROCK_AWS_ACCESS_KEY_ID || process.env.AWS_ACCESS_KEY_ID
const awsSecretKey =
process.env.BEDROCK_AWS_SECRET_ACCESS_KEY || process.env.AWS_SECRET_ACCESS_KEY
if (!awsAccessKey || !awsSecretKey) {
log.warn('AWS Bedrock credentials missing: returning empty extraction', {
file_name_hash: createHash('sha256').update(input.fileName).digest('hex').slice(0, 12),
})
@@ -254,9 +265,9 @@ export async function extractInvoiceFields(
}
const client = new AnthropicBedrock({
awsRegion: process.env.AWS_REGION || 'eu-north-1',
awsAccessKey: process.env.AWS_ACCESS_KEY_ID,
awsSecretKey: process.env.AWS_SECRET_ACCESS_KEY,
awsRegion,
awsAccessKey,
awsSecretKey,
})
let rawText: string | null = null
+13 -3
View File
@@ -20,9 +20,19 @@ let cached: AnthropicBedrock | null = null
// API.
export function getAnthropic(): AnthropicBedrock {
if (cached) return cached
const awsRegion = process.env.AWS_REGION || 'eu-north-1'
const awsAccessKey = process.env.AWS_ACCESS_KEY_ID
const awsSecretKey = process.env.AWS_SECRET_ACCESS_KEY
// Read Bedrock creds from BEDROCK_AWS_* first, falling back to the plain
// AWS_* names for local dev. On Vercel the functions run on AWS Lambda, whose
// runtime injects its OWN reserved AWS_REGION / AWS_ACCESS_KEY_ID /
// AWS_SECRET_ACCESS_KEY / AWS_SESSION_TOKEN for the platform execution role
// (wrong account, wrong region, no Bedrock access). Those shadow anything set
// in the dashboard, so a hosted deploy MUST use the BEDROCK_AWS_* names or the
// stream comes back empty ("request ended without sending any chunks").
const awsRegion =
process.env.BEDROCK_AWS_REGION || process.env.AWS_REGION || 'eu-north-1'
const awsAccessKey =
process.env.BEDROCK_AWS_ACCESS_KEY_ID || process.env.AWS_ACCESS_KEY_ID
const awsSecretKey =
process.env.BEDROCK_AWS_SECRET_ACCESS_KEY || process.env.AWS_SECRET_ACCESS_KEY
// When both static keys are present, pass them. Otherwise omit them so the
// SDK falls back to the AWS credential provider chain (instance profile,
// IRSA, EKS pod identity, ...). The two-overload SDK refuses a mix.