Compute
Instances you can shell into.
EC2 instances are containers. Two images, Ubuntu 24.04 and Debian 12, boot real VMs under QEMU, with KVM when the host has it. EBS, AMIs, Auto Scaling, ECS (Fargate) and ECR too.

HomeCloud speaks the AWS APIs. Point Terraform, the AWS CLI or boto3 at it, and Lambda, RDS and EC2 come up as real containers and VMs on your own hardware. One binary, about 30 services, open source.
curl -fsSL https://homecloud.pages.dev/scripts/install.sh | sh
Then run homecloud serve and open 127.0.0.1:8080. Needs Docker Engine, Docker Desktop or OrbStack.
irm https://homecloud.pages.dev/scripts/install.ps1 | iex
In PowerShell. Then run homecloud serve and open 127.0.0.1:8080. Needs Docker Desktop.
docker run -d --name homecloud -p 127.0.0.1:8080:8080 \
-v /var/run/docker.sock:/var/run/docker.sock \
-v homecloud-data:/data ghcr.io/solinode/homecloud
docker logs homecloud shows the root console password once. Images for amd64 and arm64.
$ eval "$(homecloud aws-env)"
$ terraform apply -auto-approve
aws_s3_bucket.assets: Creation complete
aws_db_instance.orders: Creation complete
aws_lambda_function.api: Creation complete
Apply complete! Resources: 3 added.
$ docker ps --format '{{.Image}}' | head -3
postgres:17-alpine
public.ecr.aws/lambda/python:3.12
cgr.dev/chainguard/minio:latest
Tested with the tools you already use
How it works
HomeCloud speaks the AWS wire protocols (SigV4, awsJson, awsQuery, REST), so the tools you already use only need a different endpoint. homecloud aws-env prints it, with the access keys it created on first start.
# AWS_ENDPOINT_URL, keys and region
eval "$(homecloud aws-env)"
aws sts get-caller-identity
aws s3 mb s3://demo
echo hi | aws s3 cp - s3://demo/hello.txt
aws sqs create-queue --queue-name jobs
provider "aws" {
region = "us-east-1"
# buckets by path, not by host name
s3_use_path_style = true
}
resource "aws_sqs_queue" "jobs" {
name = "jobs"
}
# the provider reads AWS_ENDPOINT_URL too
Your tools
HomeCloud :8080
Docker on your host
| Client | Status | Notes |
|---|---|---|
| AWS CLI v2 | Tested | The compatibility suite drives the real aws CLI in CI. |
| boto3 | Tested | In CI, including Cognito SRP sign-in through pycognito. |
| Terraform, OpenTofu | Tested | The stock hashicorp/aws provider, plus the nightly modules suite. |
| CloudFormation | Tested | Stacks, change sets, updates with rollback, the boto3 waiters. |
| AWS CDK | Partly | Synthesized templates deploy through change sets; cdk deploy end to end is not verified yet. |
| Other SDKs, Pulumi | Expected | Same protocols and SigV4, but not covered by tests. Reports welcome. |
What runs
Each service is something real underneath, so an integration test hits the same kind of thing production does. All of it is managed through the AWS CLI, SDKs and Terraform, and shows up in the console.
Compute
EC2 instances are containers. Two images, Ubuntu 24.04 and Debian 12, boot real VMs under QEMU, with KVM when the host has it. EBS, AMIs, Auto Scaling, ECS (Fargate) and ECR too.

Databases
| RDS | PostgreSQL · MySQL · MariaDB |
|---|---|
| ElastiCache | Redis · Valkey · Memcached |
| DynamoDB | GSIs, transactions, PartiQL, TTL, streams |
aws rds create-db-instance \
--engine postgres --engine-version 17 \
--db-instance-identifier orders ...
# runs postgres:17-alpine on your VPC network
Serverless
aws lambda invoke \
--function-name api:live \
out.json
{ "StatusCode": 200,
"ExecutedVersion": "3" }
Versions, aliases, layers, function URLs, SQS and stream triggers. API Gateway HTTP APIs and Step Functions.
Networking
Identity & security
{
"Effect": "Allow",
"Action": "s3:GetObject",
"Condition": { "StringEquals":
{ "aws:PrincipalTag/team": "web" } }
}
Conditions, roles, permissions boundaries and iam:PassRole. STS, Cognito, KMS, Secrets Manager, SSM Parameter Store.
Storage
Messaging
Standard and FIFO queues with DLQs, filter policies, EventBridge rules and Scheduler.
Observability
CloudWatch alarms, Logs Insights, and CloudTrail: a record of every API call.

Infrastructure as code
Change sets, and updates that roll back on failure. No nested stacks or custom resources yet.
Limits, up front
us-east-1), one account| Area | Services | What does the work |
|---|---|---|
| Compute | EC2, EBS, AMIs, Auto Scaling, ECS (Fargate), ECR | Instances are containers you can shell into. Two images, Ubuntu 24.04 and Debian 12, boot real VMs under QEMU, with KVM when the host has it. |
| Storage | S3, EFS | MinIO, with versioning, lifecycle, presigned URLs and bucket policies. EFS is Docker volumes. |
| Databases | RDS, ElastiCache, DynamoDB | Real PostgreSQL, MySQL and MariaDB; Redis, Valkey and Memcached. DynamoDB with GSIs, transactions, PartiQL, TTL and streams. |
| Serverless | Lambda, API Gateway (HTTP APIs), Step Functions | AWS's own Lambda runtime images. Versions, aliases, layers, function URLs, SQS and stream triggers. |
| Messaging | SQS, SNS, EventBridge, Scheduler | Standard and FIFO queues with DLQs; SNS to SQS, Lambda and HTTP with filter policies. |
| Networking | VPC, security groups, ELB v2, Route 53, ACM | Security groups are iptables rules. Load balancers are nginx, DNS is CoreDNS, certificates come from a private CA. |
| Identity & security | IAM, STS, Cognito, KMS, Secrets Manager, SSM Parameter Store | One policy evaluator for every service, with conditions, roles, permissions boundaries and iam:PassRole. |
| Observability | CloudWatch, CloudWatch Logs, CloudTrail | Metrics and logs for every resource, alarms, Logs Insights, and a record of every API call. |
| Infrastructure as code | CloudFormation | Change sets and updates with rollback. No nested stacks or custom resources yet. |
Tests & CI
No cloud credentials in CI, no bill, nothing left behind. HomeCloud's own end-to-end job runs on a stock GitHub Actions runner.
steps:
- uses: actions/checkout@v4
- uses: solinode/homecloud/integrations/github-action@main
with:
services-wait: s3 # wait for MinIO too
- run: |
aws s3 mb s3://artifacts
pytest # boto3 reads AWS_ENDPOINT_URL
Downloads a checksum-verified release, starts the server, and exports the endpoint and credentials. A post step prints the server log and removes every container it started.
from testcontainers_homecloud import HomeCloudContainer
@pytest.fixture(scope="session")
def homecloud():
with HomeCloudContainer() as hc:
yield hc
def test_upload(homecloud):
s3 = homecloud.get_client("s3")
s3.create_bucket(Bucket="test")
Starts the ghcr.io/solinode/homecloud image, waits for the API and S3, and cleans up on exit.
hc, err := homecloud.Run(ctx, homecloud.DefaultImage)
testcontainers.CleanupContainer(t, hc)
if err != nil {
t.Fatal(err)
}
s3c := s3.NewFromConfig(hc.AWSConfig(), func(o *s3.Options) {
o.UsePathStyle = true
})
Terminating the container also removes every container, network and volume HomeCloud created.
curl -fsSL https://homecloud.pages.dev/scripts/install.sh | sh
nohup homecloud serve > homecloud.log 2>&1 &
until curl -fs localhost:8080/api/v1/health; do sleep 2; done
eval "$(homecloud aws-env)"
terraform apply -auto-approve # or your test suite
Works on any runner with Docker. Run one HomeCloud per Docker host at a time.
Console
The web console is built into the binary and works offline. It is modeled on AWS's, so the layout will feel familiar. These are from the demo, which runs in your browser with sample data. Nothing to install.
Honest comparison
HomeCloud is one of several ways to run AWS without AWS, and it is not always the right one.
Self-hosting
For a team, a classroom or a homelab, not only for a test run.
linux · macos · windowsA Go binary for amd64 and arm64. Every service it offers runs as a container on the same Docker Engine.
homecloud service install2 vCPUs and 4 GB to try it; 4+ vCPUs and 8–16 GB to be comfortable. Sets up systemd or launchd.
127.0.0.1 → LAN, TailscaleIt binds to 127.0.0.1 by default. Bind it to a LAN or Tailscale address, with built-in TLS or behind a reverse proxy.
homecloud backupArchives the state and every HomeCloud volume: databases, S3 objects, images, EBS volumes. restore works on the same or a new server.
homecloud upgradeChecks the release's SHA-256 before replacing the binary; data migrates on the next start. homecloud doctor checks the host.
/var/run/docker.sockIt needs the Docker socket, which is root on the host, so HomeCloud admins are host admins. Audits are published.
Install on a server: Docker, TLS, firewall, DNS, backups and upgrades
Licensed under the GNU AGPL-3.0. If you run a modified HomeCloud as a service for others, share your changes. It is a young project, first released in September 2026: expect rough edges and please report them. A missing AWS operation is best reported as a compatibility gap.