Endpoint Discovery

The central question for any application running against Simfra is: how does your code find the emulator? The answer depends on where the code is running.

Prerequisites

Lambda

Lambda functions require zero configuration. Simfra injects all necessary environment variables into the Lambda container automatically:

Variable Value Purpose
AWS_ENDPOINT_URL http://<simfra-host>:4599 Routes all SDK calls to Simfra
AWS_REGION Function's configured region Region for API calls
AWS_DEFAULT_REGION Function's configured region Fallback region
AWS_ACCESS_KEY_ID From STS AssumeRole Execution role credentials
AWS_SECRET_ACCESS_KEY From STS AssumeRole Execution role credentials
AWS_SESSION_TOKEN From STS AssumeRole Session token for temporary credentials

Simfra assumes the function's execution role via STS to generate real temporary credentials, matching how AWS Lambda provisions the execution environment. If the role assumption fails (role doesn't exist, trust policy mismatch), Simfra falls back to root credentials.

Your Lambda code needs no changes:

import boto3

def handler(event, context):
    # boto3 reads AWS_ENDPOINT_URL automatically
    # Calls route to Simfra, not real AWS
    s3 = boto3.client('s3')
    s3.put_object(Bucket='my-bucket', Key='hello.txt', Body=b'Hello')

ECS Tasks

ECS task containers also receive automatic injection:

Variable Value Purpose
AWS_ENDPOINT_URL http://<simfra-host>:4599 Routes all SDK calls to Simfra
AWS_DEFAULT_REGION Cluster's region Region for API calls
AWS_ACCESS_KEY_ID Root credentials Authentication
AWS_SECRET_ACCESS_KEY Root credentials Authentication

Secrets defined in the task definition (referencing Secrets Manager or SSM Parameter Store) are resolved using the task's execution role and injected as environment variables before the container starts.

// No endpoint override needed - AWS_ENDPOINT_URL is set
const { DynamoDBClient, PutItemCommand } = require('@aws-sdk/client-dynamodb');
const client = new DynamoDBClient({});

EC2 Instances

EC2 instances use the Instance Metadata Service (IMDS) for credential discovery, matching real AWS behavior. When an instance has an IAM instance profile attached, Simfra sets:

Variable Value Purpose
AWS_EC2_METADATA_SERVICE_ENDPOINT http://<simfra-host>:4599/_simfra/imds/<instance-id>/<token> IMDS endpoint for credential retrieval
AWS_REGION Instance's region Region for API calls
AWS_DEFAULT_REGION Instance's region Fallback region

The SDK's default credential chain discovers IMDS credentials automatically. Code running on EC2 instances works without changes:

import boto3
# SDK discovers credentials via IMDS automatically
s3 = boto3.client('s3', region_name='us-east-1')

When no instance profile is attached, Simfra injects static root credentials (AWS_ACCESS_KEY_ID / AWS_SECRET_ACCESS_KEY) as a fallback.

IMDS provides the same metadata paths as real AWS:

  • /latest/meta-data/instance-id
  • /latest/meta-data/ami-id
  • /latest/meta-data/instance-type
  • /latest/meta-data/placement/availability-zone
  • /latest/meta-data/iam/security-credentials/<role-name>

Host Applications

Applications running directly on the host (outside Docker) must configure the endpoint manually:

export AWS_ENDPOINT_URL=http://localhost:4599
export AWS_ACCESS_KEY_ID=AKIAIOSFODNN7EXAMPLE
export AWS_SECRET_ACCESS_KEY=wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY
export AWS_DEFAULT_REGION=us-east-1

The default port is 4599, configurable via SIMFRA_PORT. All AWS services are multiplexed on this single port - no per-service endpoint configuration is needed.

For per-language setup, see SDK Configuration.

DNS Resolution

Simfra runs a per-account DNS container that resolves service DNS names within Docker networks:

  • simfra.local resolves to the Simfra gateway IP (configurable via SIMFRA_HOSTNAME)
  • Service DNS names - RDS endpoints (e.g., mydb.abc123.us-east-1.rds.simfra.dev), ALB DNS names, ElastiCache endpoints - resolve to the correct container IPs
  • Route53 hosted zones are served by the same DNS container

All Docker containers created by Simfra are configured to use this DNS container (via --dns), so DNS resolution works transparently. Containers can reach other Simfra-managed resources by their DNS names, just like in a real AWS VPC.

The domain suffix defaults to simfra.dev (configurable via SIMFRA_DOMAIN_SUFFIX).

Next Steps