Skip to content
Deployments

Deploy a private container registry with OpenTofu

Deployment

Coming from another cloud?

▸AWS·ECR

This Quake AI feature maps to AWS’s ECR.

▸Google Cloud·Artifact Registry

This Quake AI feature maps to Google Cloud’s Artifact Registry.

Deploy a private container registry with OpenTofu

Stand up Harbor, an open-source container registry, on a single Quake AI instance using the validated OpenTofu template harbor-registry. You run it yourself; this is a self-hosted registry you operate, with projects, role-based access control, and Trivy vulnerability scanning by default.

Monthly cost estimate

Pricing calculator ↗

Sized as a custom package on shared vCPU.

Starting template$72.20/mo

Monthly total for the required template above. Use the configurator below to add optional pieces and see the total update.

What each resource is for

Harbor

s1a.large · 8 shared vCPU, 8 GiB RAM, 0.5 Gbps

$66.00/mo

Compute shown per role at custom-package rates ($29/dedicated vCPU, $7.25/shared vCPU, $1/GiB RAM). The headline above is the billed total: the cheaper of a named plan and the custom package, plus add-ons.

Included in baseline

s1a.large

8 shared vCPU, 8 GiB RAM, 0.5 Gbps

$66.00

Compute + RAM rate basis

8 vCPU + 8 GiB RAM at $29/dedicated vCPU, $7.25/shared vCPU, $1/GiB RAM (regular). Totals apply the flat −$5/mo package promotion.

—

Block storage (140 GiB)

140 GiB at $0.08/GiB/mo

$11.20

Public IP (included)

1 included with the custom package

$0.00

Package promotional discount

Flat −$5.00/mo on the custom package (same promotion as named plans).

$-5.00

Included at no charge

These line items are zero on Quake AI. Many other providers meter them separately.

Data transfer (inbound and outbound)

Unlimited data transfer on every plan; Quake AI does not meter per-GB egress.

AWS, GCP, and Azure meter outbound transfer per GB. DigitalOcean and Hetzner include an allowance on compute plans, then charge overage.

Learn more
$0.00

Private networking

Private networks, subnets, Neutron routers, and security groups are included with the plan.

VPC objects are usually free to create elsewhere, but NAT gateways bill hourly plus per-GB processed. Quake AI uses router SNAT with no separate NAT line item.

$0.00

Control-plane API requests

OpenStack API calls for provisioning and management are included.

Some managed services on other clouds meter API calls or charge for premium control-plane features.

$0.00

Pricing data last validated: . For current rates, check quake.ai/pricing.

Docker clientQuake AIdocker pushdocker pullFloating IPHTTPS :443Private network10.50.0.0/24Routerto PublicStaticHarbor stackportal + registryTrivy scannerData volume/data scan on pushimage layers
Click to zoom
Harbor registry topology: private subnet, Harbor stack with data volume, one floating IP on HTTPS, Trivy scanner on push

Prerequisites#

You need:

  • A Quake AI account with application credentials
  • OpenTofu 1.6.0 or later (installation guide)
  • OpenStack credentials sourced into the shell (source openrc.sh). See the OpenStack CLI guide.
  • An existing SSH key pair in your project. See Add an SSH key.
  • Docker installed on the client you push from, with permission to edit /etc/docker/certs.d
  • A copy of the harbor-registry template from the template reference page
  • Enough project quota for one s1a.large instance, a 40 GB boot volume, a 100 GB data volume, one router, one private network, and one floating IP

Step 1: Configure variables and apply#

Copy terraform.tfvars.example to terraform.tfvars and set:

HCL
key_name = "YOUR_KEY_NAME"

Leave domain commented out for a self-signed certificate on the floating IP. Defaults for flavor, Harbor version, and volume size are documented on the Harbor registry reference page.

From the template directory, run:

bash
tofu init
tofu plan
tofu apply

Type yes when prompted. Provisioning takes several minutes while cloud-init installs Docker, generates the certificate and admin password, and starts the Harbor stack.

When the run finishes, record the outputs:

bash
REGISTRY_URL=$(tofu output -raw registry_url)
HARBOR_HOST=$(tofu output -raw floating_ip)

Step 2: Retrieve the admin password and trust the certificate#

cloud-init takes several minutes after apply returns. Wait for it to finish and read the admin password:

bash
ssh -i ~/.ssh/YOUR_KEY -o StrictHostKeyChecking=accept-new ubuntu@"$HARBOR_HOST" 'cloud-init status --wait'
ssh -i ~/.ssh/YOUR_KEY ubuntu@"$HARBOR_HOST" sudo cat /root/harbor-credentials

Harbor serves HTTPS with a self-signed certificate on first boot. Copy the certificate into Docker's per-registry trust directory on your client:

bash
sudo mkdir -p /etc/docker/certs.d/"$HARBOR_HOST"
ssh -i ~/.ssh/YOUR_KEY ubuntu@"$HARBOR_HOST" sudo cat /data/certs/harbor.crt | \
  sudo tee /etc/docker/certs.d/"$HARBOR_HOST"/ca.crt > /dev/null

Step 3: Sign in and push an image#

Open registry_url in your browser and sign in as admin with the generated password. Create a private project named demo.

Sign the Docker client in to the registry:

bash
docker login "$HARBOR_HOST"

Tag and push a test image:

bash
docker pull hello-world:latest
docker tag hello-world:latest "$HARBOR_HOST"/demo/hello-world:latest
docker push "$HARBOR_HOST"/demo/hello-world:latest

Confirm the registry serves the image back:

bash
docker rmi "$HARBOR_HOST"/demo/hello-world:latest hello-world:latest
docker pull "$HARBOR_HOST"/demo/hello-world:latest

With Trivy enabled, Harbor scans the pushed image and reports vulnerabilities on the artifact detail page in the portal.

Next steps#

Clean up#

Run tofu destroy from the project directory when finished. Type yes to confirm. Remove the certificate you added on the client if you no longer need it:

bash
sudo rm -rf /etc/docker/certs.d/"$HARBOR_HOST"
Was this page helpful?