date
related_level
slug
type
relate_date
summary
status
tags
category
last_updated
Nov 10, 2025 10:03 PM
是否已更新
orginal_page
是否推荐
- 使用 PostgreSQL, redis, garage s3 存储等外部服务,TLS 由 step-ca 外部服务提供
设置外部 redis 有一堆限制和坑
- 不支持 redis clustering
- sentinel 不能设置 ACL 和 requirepass
protected-mode no
- redis 设置,可以开 acl 但不能禁用 default 用户,且 default 用户密码需要与 harbor 用户密码一致
- https://github.com/goharbor/harbor/wiki/Harbor-FAQs#external-redis-username-password-usage
protected-mode yesrequirepass harborpass
- redis ACL 设置参考
user default on >harborpass ~* +@read +@write +publish +subscribe +select +ping +eval +evalsha +multi +exec
helm 安装 Harbor 配置
参考资料
添加 harbor 官方仓库
helm repo add harbor https://helm.goharbor.io
创建密码 Secret
创建 postgres 密码 Secret
echo -n "postgres passwd: " && read -s HARBOR_PSQL_PASSWORD; echo
kubectl create secret generic ext-psql-passwd-secret \ --namespace=registry \ --from-literal=password="$HARBOR_PSQL_PASSWORD"
kubectl get secret -n registry ext-psql-passwd-secret -o yaml
kubectl get secret -n registry ext-psql-passwd-secret -o jsonpath='{.data.password}' | base64 --decode- 查看解码后的情况
unset HARBOR_PSQL_PASSWORD
创建 redis 密码 Secret
- 另外,4 年了还没有支持 sentinel 密码
echo -n "redis passwd: " && read -s HARBOR_REDIS_PASSWORD; echo
kubectl create secret generic ext-redis-passwd-secret \ --namespace=registry \ --from-literal=REDIS_USERNAME=harbor\ --from-literal=REDIS_PASSWORD="$HARBOR_REDIS_PASSWORD"- 文档没写清楚,还需要提供
REDIS_USERNAME不然用户名为空
kubectl get secret -n registry ext-redis-passwd-secret -o yaml
kubectl get secret -n registry ext-redis-passwd-secret -o jsonpath='{.data.REDIS_PASSWORD}' | base64 --decode- 查看解码后的情况
unset HARBOR_REDIS_PASSWORD
创建 s3 密码 Secret
- 官方配置没有说明, 参考模板自行配置
echo -n "s3 passwd: " && read -s HARBOR_S3_PASSWORD; echo
kubectl create secret generic ext-s3-cred-secret \ --namespace=registry \ --from-literal=REGISTRY_STORAGE_S3_ACCESSKEY=<s3-key-id> \ --from-literal=REGISTRY_STORAGE_S3_SECRETKEY="$HARBOR_S3_PASSWORD"
kubectl get secret -n registry ext-s3-cred-secret -o yaml
kubectl get secret -n registry ext-s3-cred-secret -o jsonpath='{.data.REGISTRY_STORAGE_S3_SECRETKEY}' | base64 --decode- 查看解码后的情况
unset HARBOR_S3_PASSWORD
创建管理密码 Secret
echo -n "admin passwd: " && read -s HARBOR_ADMIN_PASSWORD; echo
kubectl create secret generic harbor-passwd-secret \ --namespace=registry \ --from-literal=HARBOR_ADMIN_PASSWORD="$HARBOR_ADMIN_PASSWORD"
kubectl get secret -n registry harbor-passwd-secret -o yaml
kubectl get secret -n registry harbor-passwd-secret -o jsonpath='{.data.HARBOR_ADMIN_PASSWORD}' | base64 --decode- 查看解码后的情况
unset HARBOR_ADMIN_PASSWORD
创建 registry htpasswd Secret
- 内部 core 访问 registry 实例会使用 htpasswd 用户认证
which htpasswd || sudo apt install apache2-utils
echo -n "registry passwd: " && read -s HARBOR_REGISTRY_PASSWORD; echo
kubectl create secret generic harbor-htpasswd \ --namespace=registry \ --from-literal=REGISTRY_HTPASSWD=$(htpasswd -nbBC 10 harbor_registry_user "$HARBOR_REGISTRY_PASSWORD") \ --from-literal=REGISTRY_PASSWD="$HARBOR_REGISTRY_PASSWORD"- 用户名必须是
harbor_registry_user,文档也没说
kubectl get secret -n registry harbor-htpasswd -o yaml
kubectl get secret -n registry harbor-htpasswd -o jsonpath='{.data.REGISTRY_PASSWD}' | base64 --decode- 查看解码后的情况
unset HARBOR_REGISTRY_PASSWORD && rm /tmp/.htpasswd
创建证书 Secret
- 使用 step-issuer+certmanager 向外部 step-ca 申请证书
- 具体部署参考 step-issuer 相关文章
vim ~/.step/cert.harbor.k8s.yaml
kubectl apply -f ~/.step/cert.harbor.k8s.yaml
kubectl get -n registry secret | grep harbor | grep kubernetes.io/tls
kubectl get -n registry secret/harbor-tls-secret -o yaml
- 查看证书签发情况
- data 下的三个文件符合 harbor 相关要求
- ca.crt
- tls.crt
- tls.key
创建 nfs 存储 pvc 存放 registry 镜像
vim ~/.config/k3s/pvc.harbor.registry.yaml
kubectl apply -f ~/.config/k3s/pvc.harbor.registry.yaml
kubectl get -n registry pvc pvc-harbor-registry
vim ~/.config/helm/value/harbor.yaml
- ingress 后续通过 k3s traefik ingreeroute 来实现,所以只需要 cluster ip 即可
- externalURL 根据 expose 类型而定,具体参考文档
- https://github.com/goharbor/harbor-helm?tab=readme-ov-file#configure-the-external-url
- 设置不当会影响 portal webui 登录,可以使用 traefik ingreeroute 来绕过
- registry 仅当 imageChartStorage 为 filesystem 才需要 PVC
- 通过 s3 外部存储来提供 registry 持久化
- 禁用了 trivy 组件来限制资源消耗
- affinity 和 nodeselector 说明
- NFS 存储需要主机支持所以限制了 VM 节点
- 集群存在多架构且 harbor chart 不支持,所以限制了 node
helm upgrade --install harbor harbor/harbor \ -n registry --create-namespace \ -f ~/.config/helm/value/harbor.yaml
查看运行情况
kubectl get deployment -n registry | grep harbor
kubectl get pod -n registry -l app.kubernetes.io/name=harbor
kubectl get cm -n registry harbor-core -o yaml | grep REDIS
kubectl describe -n registry -l app.kubernetes.io/name=harbor,app.kubernetes.io/component=core
kubectl logs --since 1h -n registry $(kubectl get pod -n registry -o jsonpath='{.items[0].metadata.name}' -l app.kubernetes.io/name=harbor,app.kubernetes.io/component=core)- 查看对应组件日志,这里是 core
kubectl logs --since 1h -n registry $(kubectl get pod -n registry -o jsonpath='{.items[0].metadata.name}' -l app.kubernetes.io/name=harbor,app.kubernetes.io/component=jobservice)- 查看对应组件日志,这里是 jobservice
- nginx 和 portal 没准备好时会报错
创建到 core 和 portal 的 traefik 路由
- 另外 externalURL https 也会影响认证,报错 405 Method not allowed
kubectl describe -n kube-system deploy/traefik | grep namespace- 先检查 traefik 是否已经为 registry 命名空间提供路由
vim ~/.config/k3s/IngressRoute.harbor.yaml
- 需要区分 core 和 portal 两个不同路由
/c/login应该发至 core 而非 portal
kubectl apply -f ~/.config/k3s/IngressRoute.harbor.yaml
kubectl get IngressRoute -n registry ingress-harbor -o yaml
检查日志
kubectl logs --since 1h -n kube-system deploy/traefik- 检查 traefik 日志
kubectl logs --since 1h -n registry deploy/harbor-core | grep login
kubectl logs --since 1h -n registry deploy/harbor-portal | grep login
外部 openssl 测试
添加 DNS 记录到 /etc/hosts
- 获取 traefik 的 external-ip
kubectl get svc -n kube-system traefik -o wide
openssl s_client -connect harbor.cluster.local:443 -servername harbor.cluster.local | grep "subject="
curl 测试
curl -vk https://harbor.cluster.local- 访问 portal 首页
- 默认管理员账户名为 admin,密码就是创建
harbor-passwd-secret时的值
HARBOR_ADMIN_PASS=$(kubectl get secret -n registry harbor-passwd-secret -o jsonpath='{.data.HARBOR_ADMIN_PASSWORD}' | base64 --decode)
curl -u admin:$HARBOR_ADMIN_PASS -H "Content-Type: application/json" https://harbor.cluster.local/api/v2.0/systeminfo- 查看系统信息,api 测试非 webui 登录
使用命令行管理 harbor 配置
- 直接查看可用 api
https://harbor.cluster.local/devcenter-api-2.0
helm 添加 harbor 作为存储并推送本地 chart
创建 myapp chart
mkdir -p ~/project && cd ~/project
helm create myapp && cd ./myapp
helm package ~/project/myapp
helm 登录 harbor 作为存储
HARBOR_ADMIN_PASS=$(kubectl get secret -n registry harbor-passwd-secret -o jsonpath='{.data.HARBOR_ADMIN_PASSWORD}' | base64 --decode)
helm registry login https://harbor.cluster.local -u admin -p $HARBOR_ADMIN_PASS- login succeeded 则为成功
查看可用 project 并推送 myapp chart
curl -u admin:$HARBOR_ADMIN_PASS -H "Content-Type: application/json" https://harbor.cluster.local/api/v2.0/projects- 查看所有可用的项目
helm push ~/project/myapp/myapp-0.1.0.tgz oci://harbor.cluster.local/library- 推送 chart 至默认项目 library
查看推送是否成功
helm show all oci://harbor.cluster.local/library/myapp
curl -u admin:$HARBOR_ADMIN_PASS -H "Content-Type: application/json" https://harbor.cluster.local/api/v2.0/repositories- 查看项目下所有已授权的 repo
curl -u admin:$HARBOR_ADMIN_PASS -H "Content-Type: application/json" https://harbor.cluster.local/api/v2.0/projects/library/repositories/myapp- 查看具体某个 repo
nerdctl 添加 harbor 作为存储并推送本地 oci 镜像
- 假设有本地镜像文件
~/project/hellobuild/hellobuild_v1.0.0.oci.tar - 构筑测试
hellobuild项目详见文章 k8s 部署 buildkit 容器镜像构建服务
nerdctl 加载生成的 oci 文件
nerdctl --namespace default load --all-platforms -i ~/project/hellobuild/hellobuild_v1.0.0.oci.tar
nerdctl --namespace default image ls | grep hellobuild
- nerdctl 登录 harbor 作为 oci 存储
nerdctl login harbor.cluster.local -u admin -p=$HARBOR_ADMIN_PASS
为镜像添加标签 harbor.cluster.local/library 并推送
nerdctl --namespace default tag hellobuild:v1.0.0 \ harbor.cluster.local/library/hellobuild:v1.0.0- 仍旧推送到默认项目 library
nerdctl --namespace default image ls | grep hellobuild- 会多了一个引用
nerdctl --namespace default push harbor.cluster.local/hellobuild:v1.0.0
查看推送是否成功
curl -u admin:$HARBOR_ADMIN_PASS -H "Content-Type: application/json" https://harbor.cluster.local/api/v2.0/projects/library/repositories/hellobuild- 查看具体某个 repo
清理本地镜像并测试重新拉取
nerdctl --namespace default rmi -f $(nerdctl --namespace default images --filter "reference=hellobuild:v1.0.0" --format "{{.Digest}}" | sort -u)
nerdctl --namespace default image ls | grep hellobuild
nerdctl --namespace default pull harbor.cluster.local/library/hellobuild:v1.0.0
nerdctl --namespace default image ls | grep hellobuild
- Author:白鸟3
- URL:https://blog.kun2peng.top/operation/k8s_harbor
- Copyright:All articles in this blog, except for special statements, adopt BY-NC-SA agreement. Please indicate the source!
