文章轉載自:http://www.mydlq.club/article/66/
系統環境:
- kubernetes 版本:1.20.1
- Traefik Ingress 版本:2.4.3
- Harbor Chart 版本:1.5.2
- Harbor 版本:2.1.3
- Helm 版本:3.2.1
- 持久化存儲驅動:NFS
一、Harbor 簡介
1、簡介
Harbor 是一個開放源代碼容器鏡像注冊表,可通過基於角色權限的訪問控制來管理鏡像,還能掃描鏡像中的漏洞並將映像簽名為受信任。Harbor 是 CNCF 孵化項目,可提供合規性,性能和互操作性,以幫助跨 Kubernetes 和 Docker 等雲原生計算平台持續,安全地管理鏡像。
2、特性
管理:多租戶、可擴展
安全:安全和漏洞分析、內容簽名與驗證
二、准備環境
1、安裝 Helm
關於如何安裝 Helm 3,請查看之前的博文 安裝 Helm3 管理 Kubernetes 應用 進行安裝。
2、創建 Namespace
由於 Harbor 組件較多,一般我們會采取新建一個 Namespace 專用於部署 Harbor 相關組件,輸入下面命令創建名為 mydlq-hub 的命名空間。
$ kubectl create namespace mydlq-hub
3、掛載 NFS 與創建目錄
這里使用的是 NFS 存儲驅動,如果使用其他存儲驅動,請自行配置。
#掛載 NFS
$ mount -o vers=4.1 192.168.2.11:/nfs/ /nfs
#創建文件夾
mkdir -p /nfs/harbor/registry
mkdir -p /nfs/harbor/chartmuseum
mkdir -p /nfs/harbor/jobservice
mkdir -p /nfs/harbor/database
mkdir -p /nfs/harbor/redis
mkdir -p /nfs/harbor/trivy
4、創建 PV 與 PVC
(1)、創建 PV 部署文件 harbor-pv.yaml
harbor-pv.yaml
#registry-PV
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-registry
labels:
app: harbor-registry
spec:
capacity:
storage: 100Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/registry
server: 192.168.2.11
---
#harbor-chartmuseum-pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-chartmuseum
labels:
app: harbor-chartmuseum
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/chartmuseum
server: 192.168.2.11
---
#harbor-jobservice-pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-jobservice
labels:
app: harbor-jobservice
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/jobservice
server: 192.168.2.11
---
#harbor-database-pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-database
labels:
app: harbor-database
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/database
server: 192.168.2.11
---
#harbor-redis-pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-redis
labels:
app: harbor-redis
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/redis
server: 192.168.2.11
---
#harbor-trivy-pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: harbor-trivy
labels:
app: harbor-trivy
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: "hub"
mountOptions:
- hard
- nfsvers=4.1
nfs:
path: /nfs/harbor/trivy
server: 192.168.2.11
執行 Kuberctl 命令創建 PV 資源:
# -f:指定資源配置文件
# -n:指定創建資源的命名空間
$ kubectl apply -f harbor-pv.yaml
(2)、創建 PVC 部署文件 harbor-pvc.yaml
harbor-pvc.yaml
#harbor-registry-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-registry
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 100Gi
selector:
matchLabels:
app: harbor-registry
---
#harbor-chartmuseum-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-chartmuseum
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 5Gi
selector:
matchLabels:
app: harbor-chartmuseum
---
#harbor-jobservice-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-jobservice
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 5Gi
selector:
matchLabels:
app: harbor-jobservice
---
#harbor-database-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-database
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 5Gi
selector:
matchLabels:
app: harbor-database
---
#harbor-redis-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-redis
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 5Gi
selector:
matchLabels:
app: harbor-redis
---
#harbor-trivy-pvc
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: harbor-trivy
spec:
accessModes:
- ReadWriteOnce
storageClassName: "hub"
resources:
requests:
storage: 5Gi
selector:
matchLabels:
app: harbor-trivy
$ kubectl apply -f harbor-pvc.yaml -n mydlq-hub
三、創建自定義證書
安裝 Harbor 我們會默認使用 HTTPS 協議,需要 TLS 證書,如果我們沒用自己設定自定義證書文件,那么 Harbor 將自動創建證書文件,不過這個有效期只有一年時間,所以這里我們生成自簽名證書,為了避免頻繁修改證書,將證書有效期為 10 年,操作如下:
1、生成證書文件:
下面執行步驟時,需要輸入一些證書信息,其中 Common Name 必須要設置為和你要給 Harbor 的域名保持一致,如 Common Name (eg, your name or your server's hostname) []:hub.mydlq.club。
## 獲得證書
$ openssl req -newkey rsa:4096 -nodes -sha256 -keyout ca.key -x509 -days 3650 -out ca.crt
## 生成證書簽名請求
$ openssl req -newkey rsa:4096 -nodes -sha256 -keyout tls.key -out tls.csr
## 生成證書
$ openssl x509 -req -days 3650 -in tls.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out tls.crt
2、生成 Secret 資源
創建 Kubernetes 的 Secret 資源,且將證書文件導入:
- -n:指定創建資源的 Namespace
- --from-file:指定要導入的文件地址
$ kubectl create secret generic hub-mydlq-tls --from-file=tls.crt --from-file=tls.key --from-file=ca.crt -n mydlq-hub
查看是否創建成功:
$ kubectl get secret hub-mydlq-tls -n mydlq-hub
可以觀察到:
NAME TYPE DATA AGE
hub-mydlq-tls Opaque 3 52m
四、設置 Harbor 配置清單
由於我們需要通過 Helm 安裝 Harbor 倉庫,需要提前創建 Harbor Chart 的配置清單文件,里面是對要創建的應用 Harbor 進行一系列參數配置,由於參數過多,關於都有 Harbor Chart 都能夠配置哪些參數這里就不一一羅列,可以通過訪問 Harbor-helm 的 Github 地址 進行了解。
下面描述下,需要的一些配置參數:
values.yaml
#Ingress 網關入口配置
expose:
type: ingress
tls:
### 是否啟用 https 協議,如果不想啟用 HTTPS,則可以設置為 false
enabled: true
### 指定使用 sectet 掛載證書模式,且使用上面創建的 secret 資源
certSource: secret
secret:
secretName: "hub-mydlq-tls"
notarySecretName: "hub-mydlq-tls"
ingress:
hosts:
### 配置 Harbor 的訪問域名,需要注意的是配置 notary 域名要和 core 處第一個單詞外,其余保持一致
core: hub.mydlq.club
notary: notary.mydlq.club
controller: default
annotations:
ingress.kubernetes.io/ssl-redirect: "true"
ingress.kubernetes.io/proxy-body-size: "0"
#### 如果是 traefik ingress,則按下面配置:
kubernetes.io/ingress.class: "traefik"
traefik.ingress.kubernetes.io/router.tls: 'true'
traefik.ingress.kubernetes.io/router.entrypoints: websecure
#### 如果是 nginx ingress,則按下面配置:
#nginx.ingress.kubernetes.io/ssl-redirect: "true"
#nginx.ingress.kubernetes.io/proxy-body-size: "0"
## 如果不想使用 Ingress 方式,則可以配置下面參數,配置為 NodePort
#clusterIP:
# name: harbor
# ports:
# httpPort: 80
# httpsPort: 443
# notaryPort: 4443
#nodePort:
# name: harbor
# ports:
# http:
# port: 80
# nodePort: 30011
# https:
# port: 443
# nodePort: 30012
# notary:
# port: 4443
# nodePort: 30013
## 如果Harbor部署在代理后,將其設置為代理的URL,這個值一般要和上面的 Ingress 配置的地址保存一致
externalURL: https://hub.mydlq.club
### Harbor 各個組件的持久化配置,並設置各個組件 existingClaim 參數為上面創建的對應 PVC 名稱
persistence:
enabled: true
### 存儲保留策略,當PVC、PV刪除后,是否保留存儲數據
resourcePolicy: "keep"
persistentVolumeClaim:
registry:
existingClaim: "harbor-registry"
size: 100Gi
chartmuseum:
existingClaim: "harbor-chartmuseum"
size: 5Gi
jobservice:
existingClaim: "harbor-jobservice"
size: 5Gi
database:
existingClaim: "harbor-database"
size: 5Gi
redis:
existingClaim: "harbor-redis"
size: 5Gi
trivy:
existingClaim: "harbor-trivy"
size: 5Gi
### 默認用戶名 admin 的密碼配置,注意:密碼中一定要包含大小寫字母與數字
harborAdminPassword: "Mydlq123456"
### 設置日志級別
logLevel: info
#各個組件 CPU & Memory 資源相關配置
nginx:
resources:
requests:
memory: 256Mi
cpu: 500m
portal:
resources:
requests:
memory: 256Mi
cpu: 500m
core:
resources:
requests:
memory: 256Mi
cpu: 1000m
jobservice:
resources:
requests:
memory: 256Mi
cpu: 500m
registry:
registry:
resources:
requests:
memory: 256Mi
cpu: 500m
controller:
resources:
requests:
memory: 256Mi
cpu: 500m
clair:
clair:
resources:
requests:
memory: 256Mi
cpu: 500m
adapter:
resources:
requests:
memory: 256Mi
cpu: 500m
notary:
server:
resources:
requests:
memory: 256Mi
cpu: 500m
signer:
resources:
requests:
memory: 256Mi
cpu: 500m
database:
internal:
resources:
requests:
memory: 256Mi
cpu: 500m
redis:
internal:
resources:
requests:
memory: 256Mi
cpu: 500m
trivy:
enabled: true
resources:
requests:
cpu: 200m
memory: 512Mi
limits:
cpu: 1000m
memory: 1024Mi
#開啟 chartmuseum,使 Harbor 能夠存儲 Helm 的 chart
chartmuseum:
enabled: true
resources:
requests:
memory: 256Mi
cpu: 500m
五、安裝 Harbor
1、添加 Helm 倉庫
$ helm repo add harbor https://helm.goharbor.io
2、部署 Harbor
$ helm install harbor harbor/harbor --version 1.5.2 -f values.yaml -n mydlq-hub
3、查看應用是否部署完成
$ kubectl get deployment -n mydlq-hub
NAME READY UP-TO-DATE AVAILABLE AGE
harbor-harbor-chartmuseum 1/1 1 1 5m
harbor-harbor-clair 1/1 1 1 5m
harbor-harbor-core 1/1 1 1 5m
harbor-harbor-jobservice 1/1 1 1 5m
harbor-harbor-notary-server 1/1 1 1 5m
harbor-harbor-notary-signer 1/1 1 1 5m
harbor-harbor-portal 1/1 1 1 5m
harbor-harbor-registry 1/1 1 1 5m
4、Host 配置域名
接下來配置 Hosts,客戶端想通過域名訪問服務,必須要進行 DNS 解析,由於這里沒有 DNS 服務器進行域名解析,所以修改 hosts 文件將 Harbor 指定節點的 IP 和自定義 host 綁定。打開電腦的 Hosts 配置文件,往其加入下面配置:
192.168.2.11 hub.mydlq.club
5、訪問 Harbor
輸入地址 https://hub.mydlq.club 訪問 Harbor 倉庫。
- 用戶:admin
- 密碼:Mydlq123456 (在安裝配置中自定義的密碼)
進入后可以看到 Harbor 的管理后台:
六、服務器配置鏡像倉庫
1、查看 Harbor 證書
再上面部署 harbor 過程中創建了 https 證書 ca.crt。這里我們查看證書,內容如下:
-----BEGIN CERTIFICATE-----
MIIC9TCCAd2gAwIBAgIRALztT/b8wlhjw50UECEOTR8wDQYJKoZIhvcNAQELBQAw
FDESMBAGA1UEAxMJaGFyYm9yLWNhMB4XDTIwMDIxOTA3NTgwMFoXDTIxMDIxODA3
NTgwMFowFDESMBAGA1UEAxMJaGFyYm9yLWNhMIIBIjANBgkqhkiG9w0BAQEFAAOC
AQ8AMIIBCgKCAQEArYbsxYmNksU5eQhVIM3OKac4l6MV/5u5belAlWSdpbbQCwMF
G/gAliTSQMgqcmhQ3odYTKImvx+5zrhP5b1CWXCQCVOlOFSLrs3ZLv68ZpKoDLkg
6XhoQFVPLM0v5V+YzWCGAson81LfX3tDhltnOItSpe2KESABVH+5L/2vo25P7Mvw
4bWEWMyY4AS/3toiDZjhwNMrMb2lpICrlH9Sc3dAOzUteyVznA5/WF8IyPI64aKn
tl0gxLOZgUBTkBoxVhPj7dNNZu8lMnqAYXmhWt+oRr7t1HHp2lOtk2u/ndyV0kKL
xufx5FYVJQel2yRBGc/C1QLN18nC1y6u5pITaQIDAQABo0IwQDAOBgNVHQ8BAf8E
BAMCAqQwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMA8GA1UdEwEB/wQF
MAMBAf8wDQYJKoZIhvcNAQELBQADggEBACFT92PWBFeCT7By8y8+EkB2TD1QVMZm
NDpBS75q5s2yIumFwJrbY6YsHtRkN1Zx9jc4LiJFHC6r0ES3tbCDapsxocvzn7dW
XLNTtnSx0zPxNXZzgmTsamfunBd4gszdXMshJ+bKsEoTXhJEXVjZq/k0EZS8L4Mp
NZ7ciPqwAI1Tg+mFGp5UOvzxYLyW8nCLPykC73y3ob1tiO6xdyD/orTAbA6pIMc9
7ajTfwYj4Q6JPY/QAmu0S+4hJHs724IrC6hiXUlQNVVRW/d3k+nXbYttnnmPnQXC
RyK2ru7R8H43Zlwj26kQJo6naQoQ0+Xcjcyk5llPqJxCrk3uoHF0r4U=
-----END CERTIFICATE-----
2、服務器 Docker 中配置 Harbor 證書
然后進入服務器,在服務器上 /etc/docker 目錄下創建 certs.d 文件夾,然后在 certs.d 文件夾下創建 Harobr 域名文件夾,可以輸入下面命令創建對應文件夾:
$ mkdir -p /etc/docker/certs.d/hub.mydlq.club
然后再 /etc/docker/certs.d/hub.mydlq.club
目錄下創建上面的 ca 證書文件:
$ cat > /etc/docker/certs.d/hub.mydlq.club/ca.crt << EOF
-----BEGIN CERTIFICATE-----
MIIC9TCCAd2gAwIBAgIRALztT/b8wlhjw50UECEOTR8wDQYJKoZIhvcNAQELBQAw
FDESMBAGA1UEAxMJaGFyYm9yLWNhMB4XDTIwMDIxOTA3NTgwMFoXDTIxMDIxODA3
NTgwMFowFDESMBAGA1UEAxMJaGFyYm9yLWNhMIIBIjANBgkqhkiG9w0BAQEFAAOC
AQ8AMIIBCgKCAQEArYbsxYmNksU5eQhVIM3OKac4l6MV/5u5belAlWSdpbbQCwMF
G/gAliTSQMgqcmhQ3odYTKImvx+5zrhP5b1CWXCQCVOlOFSLrs3ZLv68ZpKoDLkg
6XhoQFVPLM0v5V+YzWCGAson81LfX3tDhltnOItSpe2KESABVH+5L/2vo25P7Mvw
4bWEWMyY4AS/3toiDZjhwNMrMb2lpICrlH9Sc3dAOzUteyVznA5/WF8IyPI64aKn
tl0gxLOZgUBTkBoxVhPj7dNNZu8lMnqAYXmhWt+oRr7t1HHp2lOtk2u/ndyV0kKL
xufx5FYVJQel2yRBGc/C1QLN18nC1y6u5pITaQIDAQABo0IwQDAOBgNVHQ8BAf8E
BAMCAqQwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMA8GA1UdEwEB/wQF
MAMBAf8wDQYJKoZIhvcNAQELBQADggEBACFT92PWBFeCT7By8y8+EkB2TD1QVMZm
NDpBS75q5s2yIumFwJrbY6YsHtRkN1Zx9jc4LiJFHC6r0ES3tbCDapsxocvzn7dW
XLNTtnSx0zPxNXZzgmTsamfunBd4gszdXMshJ+bKsEoTXhJEXVjZq/k0EZS8L4Mp
NZ7ciPqwAI1Tg+mFGp5UOvzxYLyW8nCLPykC73y3ob1tiO6xdyD/orTAbA6pIMc9
7ajTfwYj4Q6JPY/QAmu0S+4hJHs724IrC6hiXUlQNVVRW/d3k+nXbYttnnmPnQXC
RyK2ru7R8H43Zlwj26kQJo6naQoQ0+Xcjcyk5llPqJxCrk3uoHF0r4U=
-----END CERTIFICATE-----
EOF
3、登錄 Harbor 倉庫
只有登錄成功后才能將鏡像推送到鏡像倉庫,所以配置完證書后嘗試登錄,測試是否能夠登錄成功:
$ docker login -u admin -p Mydlq123456 hub.mydlq.club
如果提示 ca 證書錯誤,則重建檢測證書配置是否有誤。
七、服務器配置 Helm Chart 倉庫
1、配置 Helm 證書
跟配置 Docker 倉庫一樣,配置 Helm 倉庫也得提前配置證書,首先進入 ca 簽名目錄
如果下面執行的目錄不存在,請用 yum 安裝 ca-certificates 包。
$ cat > /etc/pki/ca-trust/source/anchors/ca.crt << EOF
-----BEGIN CERTIFICATE-----
MIIC9TCCAd2gAwIBAgIRALztT/b8wlhjw50UECEOTR8wDQYJKoZIhvcNAQELBQAw
FDESMBAGA1UEAxMJaGFyYm9yLWNhMB4XDTIwMDIxOTA3NTgwMFoXDTIxMDIxODA3
NTgwMFowFDESMBAGA1UEAxMJaGFyYm9yLWNhMIIBIjANBgkqhkiG9w0BAQEFAAOC
AQ8AMIIBCgKCAQEArYbsxYmNksU5eQhVIM3OKac4l6MV/5u5belAlWSdpbbQCwMF
G/gAliTSQMgqcmhQ3odYTKImvx+5zrhP5b1CWXCQCVOlOFSLrs3ZLv68ZpKoDLkg
6XhoQFVPLM0v5V+YzWCGAson81LfX3tDhltnOItSpe2KESABVH+5L/2vo25P7Mvw
4bWEWMyY4AS/3toiDZjhwNMrMb2lpICrlH9Sc3dAOzUteyVznA5/WF8IyPI64aKn
tl0gxLOZgUBTkBoxVhPj7dNNZu8lMnqAYXmhWt+oRr7t1HHp2lOtk2u/ndyV0kKL
xufx5FYVJQel2yRBGc/C1QLN18nC1y6u5pITaQIDAQABo0IwQDAOBgNVHQ8BAf8E
BAMCAqQwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMA8GA1UdEwEB/wQF
MAMBAf8wDQYJKoZIhvcNAQELBQADggEBACFT92PWBFeCT7By8y8+EkB2TD1QVMZm
NDpBS75q5s2yIumFwJrbY6YsHtRkN1Zx9jc4LiJFHC6r0ES3tbCDapsxocvzn7dW
XLNTtnSx0zPxNXZzgmTsamfunBd4gszdXMshJ+bKsEoTXhJEXVjZq/k0EZS8L4Mp
NZ7ciPqwAI1Tg+mFGp5UOvzxYLyW8nCLPykC73y3ob1tiO6xdyD/orTAbA6pIMc9
7ajTfwYj4Q6JPY/QAmu0S+4hJHs724IrC6hiXUlQNVVRW/d3k+nXbYttnnmPnQXC
RyK2ru7R8H43Zlwj26kQJo6naQoQ0+Xcjcyk5llPqJxCrk3uoHF0r4U=
-----END CERTIFICATE-----
EOF
執行更新命令,使證書生效:
$ update-ca-trust extract
2、添加 Helm 倉庫
添加 Helm 倉庫:
$ helm repo add myrepo --username=admin --password=Mydlq123456 https://hub.mydlq.club/chartrepo/library
- --username:harbor倉庫用戶名
- --password:harbor倉庫密碼
- --ca-file:指向ca.crt證書地址
- chartrepo:如果是chart倉庫地址,中間必須加chartrepo
- library:倉庫的項目名稱
查看倉庫列表:
$ helm repo list
NAME URL
stable https://kubernetes-charts.storage.googleapis.com
harbor https://helm.goharbor.io
myrepo https://hub.mydlq.club/chartrepo/library
八、測試功能
1、推送與拉取 Docker 鏡像
這里為了測試推送鏡像,先下載一個用於測試的 helloworld 小鏡像,然后推送到 hub.mydlq.club 倉庫:
### 拉取 Helloworld 鏡像
$ docker pull hello-world:latest
### 將下載的鏡像使用 tag 命令改變鏡像名
$ docker tag hello-world:latest hub.mydlq.club/library/hello-world:latest
### 推送鏡像到鏡像倉庫
$ docker push hub.mydlq.club/library/hello-world:latest
將之前的下載的鏡像刪除,然后測試從 hub.mydlq.club 下載鏡像進行測試:
### 刪除之前鏡像
$ docker rmi hello-world:latest
$ docker rmi hello-world:latest hub.mydlq.club/library/hello-world:latest
### 測試從 `hub.mydlq.club` 下載新鏡像
$ docker pull hub.mydlq.club/library/hello-world:latest
2、推送與拉取 Chart
Helm 要想推送 Chart 到 Helm 倉庫,需要提前安裝上傳插件:
$ helm plugin install https://github.com/chartmuseum/helm-push
然后創建一個測試的 Chart 進行推送測試:
### 創建一個測 試chart
$ helm create hello
### 打包chart,將chart打包成tgz格式
$ helm package hello
### 推送 chart 進行測試
$ helm push hello-0.1.0.tgz myrepo
Pushing hello-0.1.0.tgz to myrepo...
Done.