1. 程式人生 > >如何讓Docker映象飛起來

如何讓Docker映象飛起來

前言

Docker用起來非常爽,尤其是用於DevOps實踐時。但是,當你在國內或者本地拉取映象時,經常會碰到各種“便祕”——要麼映象拉取緩慢,要麼時斷時連,要麼連線超時!

當我們的映象又比較大時(比如某人在程式碼裡面丟了個魔獸爭霸的包),這簡直是一個噩夢!那麼如何解決這個問題?接下來我們就主要從以下幾個方面來解決這個問題:

  • 使用映象加速器
  • 換源
  • 自己做映象推送到國內倉庫
  • 自己搭建就近映象倉庫
  • 最後的絕招(保密)

映象加速器

玩網遊卡都可以祭出加速器,映象拉取通用有相關的加速器。國內的雲廠商基本上都提供了映象加速器:

Docker Hub 映象加速器列表

映象加速器映象加速器地址專屬加速器其它加速
Docker 中國官方映象 https://registry.docker-cn.com   Docker Hub
DaoCloud 映象站 http://f1361db2.m.daocloud.io 可登入,系統分配 Docker Hub
Azure 中國映象 https://dockerhub.azk8s.cn   Docker Hub、GCR、Quay
科大映象站 https://docker.mirrors.ustc.edu.cn   Docker Hub、GCR、Quay
阿里雲 https://.mirror.aliyuncs.com
需登入,系統分配 Docker Hub
七牛雲 https://reg-mirror.qiniu.com   Docker Hub、GCR、Quay
網易雲 https://hub-mirror.c.163.com   Docker Hub
騰訊雲 https://mirror.ccs.tencentyun.com   Docker Hub

如何使用映象加速器呢?

Docker Hub 映象加速器配置

Linux系統可以執行以下Shell:

配置了之後,可以通過“docker info”命令來檢視是否生效:

如果是Windows 10呢?可以在如下圖所示的介面處配置:

換源

加速器用起來非常爽,但是很多時候某些映象就算是配置了加速器也不好使(可能和加速器的國際頻寬有關係),這個時候就必須換源了。畢竟加速器不是萬能的,尤其是當你的映象比較大的時候。這時候你就要找合適的源了。

比如.NET Core 的SDK映象,我們可以統一使用Azure中國的映象源,如下表所示,我們看到“mcr.microsoft.com”在國內對應的代理為“mcr.azk8s.cn”:

globalproxy in Chinaformatexample
dockerhub (docker.io) dockerhub.azk8s.cn dockerhub.azk8s.cn//: dockerhub.azk8s.cn/microsoft/azure-cli:2.0.61 dockerhub.azk8s.cn/library/nginx:1.15
gcr.io gcr.azk8s.cn gcr.azk8s.cn//: gcr.azk8s.cn/google_containers/hyperkube-amd64:v1.13.5
quay.io quay.azk8s.cn quay.azk8s.cn//: quay.azk8s.cn/deis/go-dev:v1.10.0
mcr.microsoft.com mcr.azk8s.cn mcr.azk8s.cn//: mcr.azk8s.cn/oss/kubernetes/hyperkube:v1.15.7

因此,我們可以使用“mcr.azk8s.cn”來替代官方提供的“mcr.microsoft.com”源:

# docker pull  mcr.microsoft.com/dotnet/core/sdk:2.2-stretch
docker pull mcr.azk8s.cn/dotnet/core/sdk:2.2-stretch

如上述程式碼所示,我們將Azure國際的源換成了Azure中國的源,拉包速度就會飛快。換源了,意味著我們也需要將Dockerfile的命令也進行修改:

#FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
#修改為Azure中國映象
FROM mcr.azk8s.cn/dotnet/core/sdk:2.2-stretch AS build

自己做映象推送到國內倉庫

有源的還還說,要是沒源怎麼辦?那總不能涼拌吧?那就自己做吧。可以基於GitHub託管,Azure DevOps和Docker hub進行海外構建,然後將映象推送到國內的映象倉庫之中。如下面這個開源庫,用於構建專案中使用的aspnetcore的執行時公共基礎映象,同時提供了騰訊雲公共映象和Docker Hub公共映象以供國內外使用:
https://github.com/xin-lai/aspnetcore-docker

相關映象標籤說明

標籤名稱說明
latest 最新映象,當前為3.1
2.2 Asp.Net Core Runtime 2.2
2.2withfonts Asp.Net Core Runtime 2.2 (包含字型)
3.0 Asp.Net Core Runtime 3.0
3.1 Asp.Net Core Runtime 3.1

然後,僅需在Dockerfile中替換為自己的源即可,即可享受快的飛起:

#說明見:https://github.com/xin-lai/aspnetcore-docker
FROM ccr.ccs.tencentyun.com/magicodes/aspnetcore-runtime:2.2withfonts AS base

這裡分享一個技巧:Linux下使用apt裝包很多時候非常緩慢而且不靠譜,有時候換成國內的代理也很不靠譜,這時候可以考慮使用海外構建,做成映象。

自己搭建就近映象倉庫

伺服器頻寬不行,本地網路不佳,怎麼辦?還能怎麼辦,自己搭建倉庫吧。這裡推薦使用nexus,nexus可以託管各種包,包括Docker、Nuget、Jar、npm、Bower等等包,簡直不要太犀利了。如何搭建?Yaml常考如下:

apiVersion: apps/v1beta2
kind: Deployment
metadata:
  labels:
    k8s-app: nexus
  name: nexus
  namespace: default
spec:
  progressDeadlineSeconds: 600
  replicas: 1
  revisionHistoryLimit: 10
  selector:
    matchLabels:
      k8s-app: nexus
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        k8s-app: nexus
    spec:
      containers:
      - image: sonatype/nexus3
        imagePullPolicy: IfNotPresent
        name: nexus
        resources:
          limits:
            cpu: "2"
            memory: 5024Mi
          requests:
            cpu: 10m
            memory: 256Mi
        volumeMounts:
        - mountPath: /nexus-data
          name: data
      restartPolicy: Always
      nodeName: k8s-node1 #強制約束將Pod排程到指定的Node節點上
      terminationGracePeriodSeconds: 30 #Pod結束時等待時長(單位為秒)
      volumes:
        - name: data
          hostPath:   #使用主機目錄
            path: /var/nexus
      hostNetwork: true
---
apiVersion: v1
kind: Service
metadata:
  name: nexus
  namespace: default
spec:
  ports:
  - name: tcp-8081-8081
    nodePort: 30081
    port: 8081
    protocol: TCP
    targetPort: 8081
  - name: tcp-8082-8082
    nodePort: 30082
    port: 8082
    protocol: TCP
    targetPort: 8082
  - name: tcp-8083-8083
    nodePort: 30083
    port: 8083
    protocol: TCP
    targetPort: 8083
  - name: tcp-8084-8084
    nodePort: 30084
    port: 8084
    protocol: TCP
    targetPort: 8084
  - name: tcp-8085-8085
    nodePort: 30085
    port: 8085
    protocol: TCP
    targetPort: 8085
  - name: tcp-8086-8086
    nodePort: 30086
    port: 8086
    protocol: TCP
    targetPort: 8086
  selector:
    k8s-app: nexus
  sessionAffinity: None
  type: NodePort

最後的絕招

還不行,用U盤複製吧。別說認識我。你不信可以通過U盤複製?可以去了解下以下兩個命令:

  • docker save
  • docker load