Python / boto3

Secure Your AWS API Key in Python

boto3 reads credentials from environment variables, ~/.aws/credentials, or EC2 instance metadata. A leaked AKIA key lets attackers assume IAM roles, read S3 buckets, and run Lambda functions. IAM roles remove long-term keys entirely.

The Problem

This is what most Python codebases look like today. The AWS_SECRET_ACCESS_KEY key (AKIA...) lives directly in the process environment. If your repo, your CI logs, or your deployment config leaks — so does your key.

Python
# storage.py — real AWS credentials in environment
import os
import boto3

s3 = boto3.client(
    "s3",
    region_name="us-east-1",
    aws_access_key_id=os.environ["AWS_ACCESS_KEY_ID"],
    aws_secret_access_key=os.environ["AWS_SECRET_ACCESS_KEY"],
)

def upload_file(key: str, body: bytes) -> None:
    s3.put_object(
        Bucket="my-app-uploads",
        Key=key,
        Body=body,
    )

The Fix

AWS doesn't use a single bearer key: every request is signed with Signature Version 4 using your secret key. The KeyVault Edge proxy injects a key into a header and does not sign AWS requests, so it can't front AWS today. The right fix for AWS is to stop using long-term keys at all: give your workload an IAM role and let the SDK fetch short-lived credentials.

Python
# storage.py — no long-term keys: boto3 uses the IAM role's short-lived credentials
import boto3

# No credentials here. On EC2/ECS/Lambda/EKS boto3 picks up the role
# attached to the workload; in CI, use GitHub OIDC to assume a role.
s3 = boto3.client("s3", region_name="us-east-1")

def upload_file(key: str, body: bytes) -> None:
    s3.put_object(Bucket="my-app-uploads", Key=key, Body=body)

Setup in 4 steps

1

Create an IAM role with least privilege

Create a role that allows only what the app needs, e.g. s3:PutObject on arn:aws:s3:::my-app-uploads/*. Attach it to the EC2 instance profile, ECS task role, Lambda execution role or EKS service account.

2

Delete the long-term keys

Remove AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY from .env files, CI secrets and deployment config, then deactivate and delete the access key in IAM.

3

Use OIDC in CI instead of stored keys

For GitHub Actions, configure the aws-actions/configure-aws-credentials action with role-to-assume and an OIDC trust policy, so workflows get credentials that expire after the job.

4

Use KeyVault Edge for your bearer-key APIs

KeyVault Edge doesn't support AWS SigV4 signing yet. It does cover providers that authenticate with a single API key header, such as OpenAI, Anthropic, Stripe, SendGrid and Google AI.

Start protecting your keys

Your AWS key is one leaked .env file away from being exploited. With KeyVault Edge the real key stays at the edge, and the token that replaces it is capped, scoped and revocable in one click.