A container registry can be defined as a repository or collection of repositories used to store and access container images. They can be used for container-based application development, saving developers valuable time to create and deliver cloud-native applications. They serve as intermediaries when sharing container images between systems.
Container images consist of libraries and system packages required to run an application. They provide several benefits to developers such as portability and agility. Container images can be created using tools like Buildah, kaniko, Img Image builder e.t.c. Once the container images have been developed, you need a place to save, share and access them later. A container registry provides storage for the images by uploading (pushing) and downloading them(pulling) to a remote system.
There are two main types of container registries:
- Public registries: these are used by individuals and small teams that want to spin and run registries as fast as possible. These are less secure and might cause problems such as patching, privacy, and access control for large organizations.
- Private registries: They offer advanced security features, providing the best way to incorporate security and privacy into enterprise container image storage. They can be hosted remotely or o-premise. The most popular Private Registries are Google Container Registry, Amazon Elastic Container Registry (ECR), and the Azure Container Registry.
Private container registries are preferred since they allow the organization to access the images internally in a more secure way. Multiple authentication systems put measures in place to verify the container images.
What is Harbor?
Harbor Container Image Registry is a free and open-source enterprise-class container registry used to store and distribute container images. It secures artifacts using policies and role-based access control. It also ensures that the images are scanned and free from vulnerabilities before signing them as trusted. Harbor was developed by VMware and later relinquished to the Cloud Native Computing Foundation(CNCF). Harbor evolved from Docker’s source code which was later enhanced to improve and eliminate security problems. Currently, it provides high performance and interoperability that helps users securely manage container images across cloud-native compute platforms such as Docker, Podman, Kubernetes e.t.c
The key features associated with Harbor are:
- Manage Helm Charts: It helps manage Helm charts isolated by projects and controlled by RBAC.
- Manage role by LDAP group: administrators can import an LDAP/AD group to Harbor and assign project roles to it.
- Replicate projects: It supports image replication. It is possible to replicate repositories from one Harbor instance to another.
- Role-Based Access Control: Users and repositories are organized into projects. Users can have different permissions for the images in different projects.
- Vulnerability Scanning: It makes use of Clair to scan images regularly and warn users of any vulnerabilities.
- Auditing: All the operations to the repositories are tracked.
- RESTful API: It has RESTful APIs for most administrative operations, easy to integrate with external systems.
- Graphical User Portal: where users can easily browse, search repositories, and manage projects.
Install Harbor Image Registry on Ubuntu 22.04|20.04
In this guide, we will comb through how to install Harbor Container Image Registry on Ubuntu 22.04|20.04
Harbor consists of 8 components that include:
- Redis: an in-memory database used for storing login information.
- PostgreSQL: the database used by the Harbor.
- Beego: an open-source web app framework on which the Harbor web service is built and developed.
- Chartmuseum: used to manage Helm Charts.
- Docker: used for pushing and pulling docker images.
- Helm: for managing Helm charts
- Swagger-ui: used to call and test the RESTful API.
Begin by updating the server and installing the required packages:
sudo apt update && sudo apt -y full-upgrade
sudo apt install apt-transport-https ca-certificates curl software-properties-common vim git
Check if a reboot is required after system upgrade:
[ -f /var/run/reboot-required ] && sudo reboot -f
Step 1 – Install Docker and Docker Compose
Harbor is deployed as a docker container and requires Docker installed. To install Docker on Ubuntu 22.04|20.04, use the aid provided in the guide below:
Once installed, ensure that Docker is started and enabled:
sudo systemctl start docker && sudo systemctl enable docker
Add your system use to the Docker Group.
sudo usermod -aG docker $USER
newgrp docker
Verify the installation:
$ docker version
Client: Docker Engine - Community
Version: 20.10.18
API version: 1.41
Go version: go1.18.6
Git commit: b40c2f6
Built: Thu Sep 8 23:11:43 2022
OS/Arch: linux/amd64
Context: default
Experimental: true
Server: Docker Engine - Community
Engine:
Version: 20.10.18
API version: 1.41 (minimum version 1.12)
Go version: go1.18.6
Git commit: e42327a
Built: Thu Sep 8 23:09:30 2022
OS/Arch: linux/amd64
Experimental: false
containerd:
Version: 1.6.8
GitCommit: 9cd3357b7fd7218e4aec3eae239db1f68a5a6ec6
runc:
Version: 1.1.4
GitCommit: v1.1.4-0-g5fd4c4d
docker-init:
Version: 0.19.0
GitCommit: de40ad0
You should also have Docker Compose installed:
$ docker compose version
Docker Compose version v2.10.2
If not, you can install Docker Compose, using the guide below:
Step 2 – Download Harbor installer on Ubuntu 22.04|20.04
Harbor installer required docker-compose let’s install it.
curl -s https://api.github.com/repos/docker/compose/releases/latest|grep browser_download_url|grep docker-compose-linux-x86_64 | cut -d '"' -f 4|wget -qi -
chmod +x docker-compose-linux-x86_64
sudo mv docker-compose-linux-x86_64 /usr/local/bin/docker-compose
rm docker-compose-linux-x86_64.sha256
Confirm it works:
$ docker-compose version
Docker Compose version v2.10.2
Download the Harbor package by visiting the GitHub release page. It is also possible to pull the latest package from the command line with the command:
curl -s https://api.github.com/repos/goharbor/harbor/releases/latest | grep browser_download_url | cut -d '"' -f 4 | grep '\.tgz$' | wget -i -
Once downloaded, extract the archive:
tar zxvf harbor-offline-installer-v*.tgz
Navigate into the directory:
cd harbor
Step 3 – Configure Harbor on Ubuntu 22.04|20.04
If you have a Fully Qualified Domain Name, you can generate SSL certificates for your domain name.
Using Let’s Encrypt SSL
Install certbot and request for Let’s Encrypt SSL:
sudo apt install certbot -y
sudo certbot certonly --standalone -d "harbor.geeksforgeeks.org" --preferred-challenges http --agree-tos -n -m "[email protected]" --keep-until-expiring
After this, you will have certificates at /etc/letsencrypt/live/harbor.yourdoain.com/
Using Self-signed certificates
- It is also possible to generate and use Self-signed certificates. But this might cause a problem with unknown CA certificate when trying to connect to Harbor from Docker/Podman client.
mkdir -p certs
openssl req \
-newkey rsa:4096 -nodes -sha256 -keyout certs/harbor.key \
-addext "subjectAltName = DNS:harbor.geeksforgeeks.org" \
-x509 -days 365 -out certs/harbor.crt
After this, copy the certificates to /etc/ssl/certs/;
sudo cp certs/harbor.* /etc/ssl/certs/
Once created, open the file for editing:
vim harbor.yml
In the file, make the desired configurations:
hostname: harbor.geeksforgeeks.org
http:
# port for http, default is 80. If https enabled, this port will redirect to https port
port: 80
# Remember Change the admin password from UI after launching Harbor.
harbor_admin_password: Harbor12345
If you intend to run Harbor over HTTP alone (you do not have an FQDN), you need to comment out the below HTTPS-related configs:
# https related config
#https:
# port: 443
# certificate: /your/certificate/path
# private_key: /your/private/key/path
Example https configurations for self-signed certificates:
https:
# https port for harbor, default is 443
port: 443
# The path of cert and key files for nginx
certificate: /etc/ssl/certs/harbor.crt
private_key: /etc/ssl/certs/harbor.key
You can also configure the database password, with the number of maximum connections:
# Harbor DB configuration
database:
# The password for the root user of Harbor DB. Change this before any production use.
password: root123
# The maximum number of connections in the idle connection pool. If it <=0, no idle connections are retained.
max_idle_conns: 100
# The maximum number of open connections to the database. If it <= 0, then there is no limit on the number of open connections.
# Note: the default number of connections is 1024 for postgres of harbor.
max_open_conns: 900
Configure the storage path for Harbor as shown:
# The default data volume
data_volume: /data
It is also possible to use external storage such as azure, GCS, S3, swift, and OSS by uncommenting and modifying the below lines.
# Uncomment storage_service setting If you want to using external storage
# storage_service:
# # ca_bundle is the path to the custom root ca certificate, which will be injected into the truststore
# # of registry's and chart repository's containers. This is usually needed when the user hosts a internal storage with self signed certificate.
# ca_bundle:
# # storage backend, default is filesystem, options include filesystem, azure, gcs, s3, swift and oss
# # for more info about this configuration please refer https://docs.docker.com/registry/configuration/
# filesystem:
# maxthreads: 100
# # set disable to true when you want to disable registry redirect
# redirect:
# disabled: false
Once the modifications have been made, save the file and proceed as shown below.
Step 4 – Install Harbor on Ubuntu 22.04|20.04
Now you can install the Harbor Container Image Registry on Ubuntu 22.04|20.04 by executing the installer script as shown:
sudo ./install.sh
Sample Output:
[Step 0]: checking if docker is installed ...
Note: docker version: 20.10.18
[Step 1]: checking docker-compose is installed ...
Note: Docker Compose version 2.11.2
[Step 2]: loading Harbor images ...
915f79eed965: Loading layer [==================================================>] 37.77MB/37.77MB
53e17aa1994a: Loading layer [==================================================>] 8.898MB/8.898MB
82205c155ee7: Loading layer [==================================================>] 3.584kB/3.584kB
7ffa6a408e36: Loading layer [==================================================>] 2.56kB/2.56kB
1a2ed94f447f: Loading layer [==================================================>] 97.91MB/97.91MB
e031eb4548cd: Loading layer [==================================================>] 98.7MB/98.7MB
Loaded image: goharbor/harbor-jobservice:v2.6.0
.....
Once complete, you should see this:
You can also view the running containers:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
6e6bda2f1a5f goharbor/harbor-jobservice:v1.10.14 "/harbor/harbor_jobs…" 21 seconds ago Up 16 seconds (health: starting) harbor-jobservice
be4ba338c24d goharbor/nginx-photon:v1.10.14 "nginx -g 'daemon of…" 21 seconds ago Up 16 seconds (health: starting) 0.0.0.0:80->8080/tcp, :::80->8080/tcp, 0.0.0.0:443->8443/tcp, :::443->8443/tcp nginx
05ce75a1f7dc goharbor/harbor-core:v1.10.14 "/harbor/harbor_core" 21 seconds ago Up 17 seconds (health: starting) harbor-core
baaeec02b7fb goharbor/harbor-portal:v1.10.14 "nginx -g 'daemon of…" 21 seconds ago Up 17 seconds (health: starting) 8080/tcp harbor-portal
27719428c542 goharbor/harbor-registryctl:v1.10.14 "/home/harbor/start.…" 21 seconds ago Up 18 seconds (health: starting) registryctl
d273aff2ee28 goharbor/redis-photon:v1.10.14 "redis-server /etc/r…" 21 seconds ago Up 17 seconds (health: starting) 6379/tcp redis
383433e6ec36 goharbor/registry-photon:v1.10.14 "/home/harbor/entryp…" 21 seconds ago Up 17 seconds (health: starting) 5000/tcp registry
e80e59840027 goharbor/harbor-db:v1.10.14 "/docker-entrypoint.…" 21 seconds ago Up 17 seconds (health: starting) 5432/tcp harbor-db
149ef8437374 goharbor/harbor-log:v1.10.14 "/bin/sh -c /usr/loc…" 21 seconds ago Up 19 seconds (health: starting) 127.0.0.1:1514->10514/tcp harbor-log
Step 5 – Access the Harbor Web UI on Ubuntu
Once installed, you can access the Harbor web interface using the URL http://domain_name or https://domain_name
Login using the credential defined on the Harbor config file. Once authenticated, you will see the below dashboard.
Create a User
From this dashboard, you can create a user by navigating to Administrator->Users then New user.
Provide the user details as shown.
Once created, the user will appear as shown and you can set them as admins by selecting the user and then click on Set as admin
Create New Harbor Registry
Navigate to the Administration menu and click on Registries-> NEW ENDPOINT
Harbor allows users to add other non-Harbor registries. The currently supported registries are Docker Hub, Docker registry, AWS Elastic Container Registry, Azure Container Registry, Huawei SWR, Gitlab, Quay.io, Jfrog Artifactory, Artifact Hub (Support added in v2.0.4), Ali Cloud Container Registry, and Google Container Registry.
For this guide, I will demonstrate how to add the DockerHub registry. You need to provide the provider, name, URL of the Endpoint, access ID(username), and Access secret(password).
To verify if everything is okay, click on Test connection.
If the connection goes through, click Ok to add the registry. Once added, the registry will appear as shown.
Now we need to create a Replication under Replications->New Replication Rule to synchronize artifacts with Harbor.
Here, you need to provide the:
- Name: lower case letters to specify the name
- Description: information regarding your replication
- Replication mode: This is the type of replication. It can be a Pull-based or push-based mode.
- Source registry: the repository configured to synchronize with Harbor
- Source filter: the repository you want to synchronize to your Harbor repository. For example nginx/latest on DockerHub
- tag: Tag of the images that you want to synchronize.
- Destination Namespace: Your project name
- Trigger Mode: synchronization can be manually triggered or Scheduled
For example:
Once the details have been filled click on save. The new replication will be added as shown.
Now to trigger the synchronization manually, select the Replication and click Replicate
Now on your project, you should see replication.
Click on it and see the available image that has been synchronized.
Step 6 – Use Harbor Container Image Registry
Now you can pull and use the images in the Harbor Container Image Registry. If you used HTTP, you need to make the below adjustments on your Docker client.
sudo vim /etc/docker/daemon.json
Add the below lines:
{
"insecure-registries" : ["harbor.geeksforgeeks.org", "0.0.0.0"]
}
Once the changes have been made, restart Docker:
sudo systemctl restart docker
You also need to ensure that Harbor DNS entry points to the Server IP:
$ sudo vim /etc/hosts
192.168.205.22 harbor.geeksforgeeks.org
Login to Harbor
Now login to Harbor using the command with the syntax;
##For Docker
docker login <harbor_address>
##For Podman with HTTPS
podman login <harbor_address>
##For Podman with HTTP
podman login <harbor_address> --tls-verify=false
For example:
docker login harbor.geeksforgeeks.org
You can also provide the username and password with the command:
$ docker login harbor.geeksforgeeks.org --username=admin --password=Harbor12345
WARNING! Using --password via the CLI is insecure. Use --password-stdin.
WARNING! Your password will be stored unencrypted in /home/rocky9/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store
Login Succeeded
Remember, you need to use –tls-verify=false for all Podman pull and push commands if you are using HTTP.
Pull a Container Image
To pull an image use the command with the syntax:
##For Docker
docker pull <harbor_address>/library/image:tag
##For Podman with HTTP
podman pull <harbor_address>/library/image:tag
##For Podman with HTTPs
podman pull <harbor_address>/library/image:tag --tls-verify=false
For example:
docker pull harbor.geeksforgeeks.org/library/keel-demo-image
Sample Output:
Build and Push a Container Image
It is also possible to build and push container images. First, create a Dockerfile.
$ vim Dockerfile
FROM ubuntu:20.04
RUN apt-get update -y
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get install -y gnupg apt-transport-https apt-utils wget
RUN echo "deb https://notesalexp.org/tesseract-ocr5/focal/ focal main" \
|tee /etc/apt/sources.list.d/notesalexp.list > /dev/null
RUN wget -O - https://notesalexp.org/debian/alexp_key.asc | apt-key add -
RUN apt-get update -y
RUN apt-get install tesseract-ocr -y
RUN apt install imagemagick -y
ENTRYPOINT ["tesseract"]
RUN tesseract -v
Create the container images using the Dockerfile
##For Docker
docker build . -t tesseract:5
##For Podman
podman build . -t tesseract:5
Now tag the image to be pushed:
docker tag tesseract:5 harbor.geeksforgeeks.org/library/tesseract:latest
Push an image:
docker push harbor.geeksforgeeks.org/library/tesseract:latest
Sample Output:
Verify if the image is available on Harbor.
This image can also be pulled and used to run containers.
Step 7 – Manage Harbor’s lifecycle
The Harbor containers can be stopped with the command:
$ docker compose stop
[+] Running 8/9
⠿ Container registryctl Stopped 10.3s
⠿ Container harbor-jobservice Stopped 0.5s
⠿ Container nginx Stopped 0.5s
⠿ Container harbor-core Stopped 0.4s
⠿ Container harbor-portal Stopped 0.4s
⠿ Container redis Stopped 0.6s
⠿ Container harbor-db Stopped 0.6s
⠿ Container registry Stopped 0.3s
⠋ Container harbor-log Stopping 10.0s
To start the containers, use the command:
$ docker compose start
[+] Running 9/9
⠿ Container harbor-log Started 0.6s
⠿ Container harbor-db Started 2.3s
⠿ Container redis Started 1.7s
⠿ Container registryctl Started 2.0s
⠿ Container harbor-portal Started 2.3s
⠿ Container registry Started 2.3s
⠿ Container harbor-core Started 0.6s
⠿ Container harbor-jobservice Started 1.5s
⠿ Container nginx Started 1.5s
To update the configurations, you need to stop the running Harbor instance:
$ docker compose down -v
[+] Running 7/8
⠇ Container registryctl Stopping 8.9s
⠿ Container harbor-jobservice Removed 0.4s
⠿ Container nginx Removed 0.7s
⠿ Container harbor-core Removed 3.3s
⠿ Container harbor-portal Removed 0.3s
⠿ Container redis Removed 0.6s
⠿ Container harbor-db Removed 0.7s
⠿ Container registry Removed 0.4s
Now make adjustments to your Harbor config:
vim harbor.yml
Once the desired adjustments have been made, run the below commands to start Harbor:
./prepare
docker-compose up -d
Conclusion
That marks the end of this guide on how to install Harbor Container Image Registry on Ubuntu 22.04|20.04. You can now store and distribute container images securely with Harbor Container Image Registry. I hope this was significant.
Related posts:
- Install Harbor Container Image Registry on CentOS / Debian / Ubuntu
- Setup Docker Container Registry with Podman & Let’s Encrypt SSL
- Publish Container Images to Docker Hub / Image registry with Podman
- Build container images from Dockerfile using kaniko in Kubernetes