This repository contains a container registry implementation in Workers that uses R2.
It supports all pushing and pulling workflows. It also supports Username/Password and public key JWT based authentication.
You have to install all the dependencies with pnpm (other package managers may work, but only pnpm is supported.)
$ pnpm install
After installation, there is a few steps to actually deploy the registry into production:
- Have your own
wrangler
file.
$ cp wrangler.toml.example wrangler.toml
- Setup the R2 Bucket for this registry
$ npx wrangler --env production r2 bucket create r2-registry
Add this to your wrangler.toml
r2_buckets = [
{ binding = "REGISTRY", bucket_name = "r2-registry"}
]
- Deploy your image registry
$ npx wrangler deploy --env production
Your registry should be up and running. It will refuse any requests if you don't setup credentials.
Set the USERNAME and PASSWORD as secrets with npx wrangler secret put USERNAME --env production
and npx wrangler secret put PASSWORD --env production
.
You can add a base64 encoded JWT public key to verify passwords (or token) that are signed by the private key.
npx wrangler secret put JWT_REGISTRY_TOKENS_PUBLIC_KEY --env production
You can use this registry with Docker to push and pull images.
Example using docker push
and docker pull
:
export REGISTRY_URL=your-url-here
# Replace $PASSWORD and $USERNAME with the actual credentials
echo $PASSWORD | docker login --username $USERNAME --password-stdin $REGISTRY_URL
docker pull ubuntu:latest
docker tag ubuntu:latest $REGISTRY_URL/ubuntu:latest
docker push $REGISTRY_URL/ubuntu:latest
# Check that pulls work
docker rmi ubuntu:latest $REGISTRY_URL/ubuntu:latest
docker pull $REGISTRY_URL/ubuntu:latest
You can configure the R2 registry to fallback to another registry if it doesn't exist in your R2 bucket. It will download from the registry and copy it into the R2 bucket. In the next pull it will be able to pull it directly from R2.
This is very useful for migrating from one registry to serverless-registry
.
It supports both Basic and Bearer authentications as explained in the registry spec.
In the wrangler.toml file:
[env.production.vars]
REGISTRIES_JSON = "[{ \"registry\": \"https://url-to-other-registry\", \"password_env\": \"REGISTRY_TOKEN\", \"username\": \"username-to-use\" }]"
Set as a secret the registry token of the registry you want to setup pull fallback in.
For example gcr:
cat ./registry-service-credentials.json | base64 | npx wrangler secret put REGISTRY_TOKEN --env production
Github for example uses a simple token that you can copy.
echo $GITHUB_TOKEN | npx wrangler secret put REGISTRY_TOKEN --env production
The trick is always looking for how you would login in Docker for the target registry and setup the credentials.
Never put a registry password/token inside the wrangler.toml, please always use wrangler secrets put
Right now there is some limitations with this container registry.
- Pushing with docker is limited to images that have layers of maximum size 500MB. Refer to maximum request body sizes in your Workers plan.
- To circumvent that limitation, you can either manually interact with the R2 bucket to upload the layer or take a
peek at the
./push
folder for some inspiration on how can you push big layers. - If you use
npx wrangler dev
and push to the R2 registry with docker, the R2 registry will have to buffer the request on the Worker.
The project is licensed under the Apache License.
See CONTRIBUTING.md
for contributing to the project.