kubespray离线安装k8s

kubespray离线安装k8s

系统环境

OS:
Static hostname: test
Icon name: computer-vm
Chassis: vm
Machine ID: 22349ac6f9ba406293d0541bcba7c05d
Boot ID: 83bb7e5dbf27453c94ff9f1fe88d5f02
Virtualization: vmware
Operating System: Ubuntu 22.04.4 LTS
Kernel: Linux 5.15.0-105-generic
Architecture: x86-64
Hardware Vendor: VMware, Inc.
Hardware Model: VMware Virtual Platform

repo:
10.1.1.70

k8s_master:
10.1.1.71

kubespray version:
2.25.0

kubernetes version:
1.29.5

kubespray离线下载预配置

  1. 准备 kubespray 环境

    • 更新系统包列表:apt update
    • 安装 Git、Python3 和 pip:apt install git python3 python3-pip -y
    • 克隆 Kubespray 仓库:git clone https://github.com/kubernetes-incubator/kubespray.git
    • 进入 Kubespray 目录:cd kubespray
  2. 创建配置

    • 生成下载包和镜像列表:apt install ansible -y && cd contrib/offline && bash generate_list.sh

安装配置离线file repo

  1. 下载软件包到目录:wget -x -P temp/files -i temp/files.list

  2. 启动简单的http服务器:cd temp/files && python3 -m http.server 8000

安装配置harbor和离线镜像库

安装docker和docker-compose

apt install docker docker-compose -y

安装harbor

harbor安装配置官方文档

下载
wget https://github.com/goharbor/harbor/releases/download/v2.11.0-rc1/harbor-offline-installer-v2.11.0-rc1.tgz
tar xvf harbor-offline-installer-v2.11.0-rc1.tgz
生成私有证书

生成Harbor私有证书的证书和密钥通常涉及以下步骤:

  1. 创建一个文件夹:用于存放生成的证书和密钥。

    mkdir -p /data/certs && cd /data/certs
    
  2. 生成CA证书:首先,创建CA的私钥和证书。

    openssl genrsa -out ca.key 4096
    openssl req -x509 -new -nodes -sha512 -days 3650 -subj "/CN=harbor.sys.foobar.com" -key ca.key -out ca.crt
    

    harbor.sys.foobar.com替换为您的Harbor域名。

  3. 生成服务器证书:创建服务器的私钥和证书签名请求(CSR)。

    openssl genrsa -out server.key 4096
    openssl req -new -sha512 -subj "/CN=harbor.sys.foobar.com" -key server.key -out server.csr
    

    同样,将harbor.sys.foobar.com替换为您的Harbor域名。

  4. 创建v3.ext文件:为了生成服务器证书,需要一个v3.ext文件来定义证书的使用。

    cat > v3.ext <<-EOF
    authorityKeyIdentifier=keyid,issuer
    basicConstraints=CA:FALSE
    keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment
    extendedKeyUsage = serverAuth 
    subjectAltName = @alt_names
    
    [alt_names]
    DNS.1=harbor.sys.foobar.com
    EOF
    

    harbor.sys.foobar.com替换为您的Harbor域名。

  5. 生成服务器证书:使用CA证书和私钥对CSR进行签名。

    openssl x509 -req -sha512 -days 3650 -extfile v3.ext -CA ca.crt -CAkey ca.key -CAcreateserial -in server.csr -out server.crt
    
  6. 配置Harbor:将生成的server.crtserver.key文件复制到Harbor的配置目录中,并在harbor.yml文件中指定证书和私钥的路径。

配置安装

配置harbor.yml.tpl文件是Harbor安装和设置的关键步骤。这个文件包含了Harbor实例的所有配置信息。以下是配置harbor.yml.tpl的基本步骤:

  1. 复制模板文件:首先,您需要将harbor.yml.tpl模板文件复制为harbor.yml,这是Harbor将要使用的配置文件。

    cp harbor.yml.tmpl harbor.yml
    
  2. 编辑配置文件:使用文本编辑器打开harbor.yml文件进行编辑。

    vim harbor.yml
    
  3. 配置主要参数:在harbor.yml文件中,您需要配置以下主要参数:

    • hostname:设置Harbor服务器的主机名或IP地址(harbor.sys.foobar.com)。
    • port:设置HTTP和HTTPS的端口号,默认是80和443(默认)。
    • harbor_admin_password:设置Harbor管理员账户的初始密码(默认或修改)。
    • certificateprivate_key:如果启用HTTPS,指定SSL证书和私钥的路径(/root/harbor/server.crt, /root/harbor/server.key)。
  4. 保存并退出:完成配置后,保存文件并退出编辑器。

  5. 运行prepare脚本:在安装Harbor之前,运行prepare脚本来准备环境。

    # 注意镜像拉取错误可能是版本问题,修要修改脚本中goharbor/prepare:v2.11.0为goharbor/prepare:v2.11.0-rc1
    ./prepare
    
  6. 安装Harbor:运行install.sh脚本来安装Harbor。

    ./install.sh
    
下载镜像
  1. 创建k8s项目:新建项目

  2. 下载依赖镜像

    • 设置hosts解析,10.1.1.70 harbor.sys.foobar.com
    • 安装 skopeoapt install skopeo -y,将依赖镜像同步到自建私有镜像仓库。
    • 同步镜像:for image in $(cat temp/images.list); do skopeo copy --dest-creds=admin:Harbor12345 --src-tls-verify=false --dest-tls-verify=false docker://${image} docker://harbor.sys.foobar.com/k8s/${image#*/}; done,需要注意使用的域名和证书上的hostname以及harbor.yml中配置的hostname一致。
      在这里插入图片描述

master node配置kubespray

  1. 从repo服务器拷贝kubespray到本地

    • 更新系统包列表:apt update
    • 安装 Git、Python3 和 pip:apt install git python3 python3-pip -y
    • 从repo服务器克隆 Kubespray 仓库,git clone https://github.com/kubernetes-incubator/kubespray.git
    • 进入 Kubespray 目录:cd kubespray
    • 安装所需依赖:pip install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
    • 验证 Ansible 版本:ansible --version
    • 复制样本清单:cp -rfp inventory/sample inventory/mycluster
  2. 配置集群参数
    下载的file list和image list会根据配置文件生成

    • 编辑 k8s_cluster.yml 文件以设置 Kubernetes 版本和网络插件等参数:vim inventory/mycluster/group_vars/k8s_cluster/k8s-cluster.yml
    • 启用 Kubernetes 仪表板和入口控制器:vim inventory/mycluster/group_vars/k8s_cluster/addons.yml
    • 编辑vim roles/kubespray-defaults/defaults/main/download.yml,默认使用offline.yml中定义的地址。
  3. 配置kubespray

    • 编辑 offline.yml 文件,替换file和image镜像地址:vim /root/kubespray/inventory/mycluster/group_vars/all/offline.yml
    ---
    ## Global Offline settings
    ### Private Container Image Registry
    registry_host: "harbor.sys.foobar.com/k8s"
    files_repo: "http://10.1.1.70:8000"
    ### If using CentOS, RedHat, AlmaLinux or Fedora
    # yum_repo: "http://myinternalyumrepo"
    ### If using Debian
    # debian_repo: "http://myinternaldebianrepo"
    ### If using Ubuntu
    # ubuntu_repo: "http://myinternalubunturepo"
    
    ## Container Registry overrides
    kube_image_repo: "{{ registry_host }}"
    gcr_image_repo: "{{ registry_host }}"
    github_image_repo: "{{ registry_host }}"
    docker_image_repo: "{{ registry_host }}"
    quay_image_repo: "{{ registry_host }}"
    
    ## Kubernetes components
    kubeadm_download_url: "{{ files_repo }}/dl.k8s.io/release/{{ kubeadm_version }}/bin/linux/{{ image_arch }}/kubeadm"
    kubectl_download_url: "{{ files_repo }}/dl.k8s.io/release/{{ kube_version }}/bin/linux/{{ image_arch }}/kubectl"
    kubelet_download_url: "{{ files_repo }}/dl.k8s.io/release/{{ kube_version }}/bin/linux/{{ image_arch }}/kubelet"
    
    
    ## Two options - Override entire repository or override only a single binary.
    
    ## [Optional] 1 - Override entire binary repository
    # github_url: "https://my_github_proxy"
    # dl_k8s_io_url: "https://my_dl_k8s_io_proxy"
    # storage_googleapis_url: "https://my_storage_googleapi_proxy"
    # get_helm_url: "https://my_helm_sh_proxy"
    
    ## [Optional] 2 - Override a specific binary
    ## CNI Plugins
    cni_download_url: "{{ files_repo }}/github.com/containernetworking/plugins/releases/download/{{ cni_version }}/cni-plugins-linux-{{ image_arch }}-{{cni_version }}.tgz"
    
    ## cri-tools
    crictl_download_url: "{{ files_repo }}/github.com/kubernetes-sigs/cri-tools/releases/download/{{ crictl_version }}/crictl-{{ crictl_version }}-{{ansible_system | lower }}-{{ image_arch }}.tar.gz"
    
    ## [Optional] etcd: only if you use etcd_deployment=host
    etcd_download_url: "{{ files_repo }}/github.com/etcd-io/etcd/releases/download/{{ etcd_version }}/etcd-{{ etcd_version }}-linux-{{ image_arch }}.tar.gz"
    
    # [Optional] Calico: If using Calico network plugin
    calicoctl_download_url: "{{ files_repo }}/github.com/projectcalico/calico/releases/download/{{ calico_ctl_version }}/calicoctl-linux-{{ image_arch }}"
    # [Optional] Calico with kdd: If using Calico network plugin with kdd datastore
    calico_crds_download_url: "{{ files_repo }}/github.com/projectcalico/calico/archive/{{ calico_version }}.tar.gz"
    
    # [Optional] Cilium: If using Cilium network plugin
    ciliumcli_download_url: "{{ files_repo }}/github.com/cilium/cilium-cli/releases/download/{{ cilium_cli_version }}/cilium-linux-{{ image_arch }}.tar.gz"
    
    # [Optional] helm: only if you set helm_enabled: true
    helm_download_url: "{{ files_repo }}/get.helm.sh/helm-{{ helm_version }}-linux-{{ image_arch }}.tar.gz"
    
    # [Optional] crun: only if you set crun_enabled: true
    crun_download_url: "{{ files_repo }}/github.com/containers/crun/releases/download/{{ crun_version }}/crun-{{ crun_version }}-linux-{{ image_arch }}"
    
    # [Optional] kata: only if you set kata_containers_enabled: true
    kata_containers_download_url: "{{ files_repo }}/github.com/kata-containers/kata-containers/releases/download/{{ kata_containers_version }}kata-static-{{ kata_containers_version }}-{{ ansible_architecture }}.tar.xz"
    
    # [Optional] cri-dockerd: only if you set container_manager: docker
    cri_dockerd_download_url: "{{ files_repo }}/github.com/Mirantis/cri-dockerd/releases/download/v{{ cri_dockerd_version }}/cri-dockerd-{{cri_dockerd_version }}.{{ image_arch }}.tgz"
    
    # [Optional] runc: if you set container_manager to containerd or crio
    runc_download_url: "{{ files_repo }}/github.com/opencontainers/runc/releases/download/{{ runc_version }}/runc.{{ image_arch }}"
    
    # [Optional] cri-o: only if you set container_manager: crio
    # crio_download_base: "download.opensuse.org/repositories/devel:kubic:libcontainers:stable"
    # crio_download_crio: "http://{{ crio_download_base }}:/cri-o:/"
    crio_download_url: "{{ files_repo }}/storage.googleapis.com/cri-o/artifacts/cri-o.{{ image_arch }}.{{ crio_version }}.tar.gz"
    skopeo_download_url: "{{ files_repo }}/github.com/lework/skopeo-binary/releases/download/{{ skopeo_version }}/skopeo-linux-{{ image_arch }}"
    
    # [Optional] containerd: only if you set container_runtime: containerd
    containerd_download_url: "{{ files_repo }}/github.com/containerd/containerd/releases/download/v{{ containerd_version }}/containerd-{{containerd_version }}-linux-{{ image_arch }}.tar.gz"
    nerdctl_download_url: "{{ files_repo }}/github.com/containerd/nerdctl/releases/download/v{{ nerdctl_version }}/nerdctl-{{ nerdctl_version }}-{{ansible_system | lower }}-{{ image_arch }}.tar.gz"
    
    # [Optional] runsc,containerd-shim-runsc: only if you set gvisor_enabled: true
    gvisor_runsc_download_url: "{{ files_repo }}/storage.googleapis.com/gvisor/releases/release/{{ gvisor_version }}/{{ ansible_architecture }}/runsc"
    gvisor_containerd_shim_runsc_download_url: "{{ files_repo }}/storage.googleapis.com/gvisor/releases/release/{{ gvisor_version }}/{{ansible_architecture }}/containerd-shim-runsc-v1"
    
    # [Optional] Krew: only if you set krew_enabled: true
    krew_download_url: "{{ files_repo }}/github.com/kubernetes-sigs/krew/releases/download/{{ krew_version }}/krew-{{ host_os }}_{{ image_arch }}.tar.gz"
    
    ## CentOS/Redhat/AlmaLinux
    ### For EL7, base and extras repo must be available, for EL8, baseos and appstream
    ### By default we enable those repo automatically
    # rhel_enable_repos: false
    ### Docker / Containerd
    # docker_rh_repo_base_url: "{{ yum_repo }}/docker-ce/$releasever/$basearch"
    # docker_rh_repo_gpgkey: "{{ yum_repo }}/docker-ce/gpg"
    
    ## Fedora
    ### Docker
    # docker_fedora_repo_base_url: "{{ yum_repo }}/docker-ce/{{ ansible_distribution_major_version }}/{{ ansible_architecture }}"
    # docker_fedora_repo_gpgkey: "{{ yum_repo }}/docker-ce/gpg"
    ### Containerd
    # containerd_fedora_repo_base_url: "{{ yum_repo }}/containerd"
    # containerd_fedora_repo_gpgkey: "{{ yum_repo }}/docker-ce/gpg"
    
    ## Debian
    ### Docker
    # docker_debian_repo_base_url: "{{ debian_repo }}/docker-ce"
    # docker_debian_repo_gpgkey: "{{ debian_repo }}/docker-ce/gpg"
    ### Containerd
    # containerd_debian_repo_base_url: "{{ debian_repo }}/containerd"
    # containerd_debian_repo_gpgkey: "{{ debian_repo }}/containerd/gpg"
    # containerd_debian_repo_repokey: 'YOURREPOKEY'
    
    ## Ubuntu
    ### Docker
    # docker_ubuntu_repo_base_url: "{{ ubuntu_repo }}/docker-ce"
    # docker_ubuntu_repo_gpgkey: "{{ ubuntu_repo }}/docker-ce/gpg"
    ### Containerd
    # containerd_ubuntu_repo_base_url: "{{ ubuntu_repo }}/containerd"
    # containerd_ubuntu_repo_gpgkey: "{{ ubuntu_repo }}/containerd/gpg"
    # containerd_ubuntu_repo_repokey: 'YOURREPOKEY'
    
    • 配置hosts文件
    echo '10.1.1.70 harbor.sys.foobar.com' >>/etc/hosts
    
  4. 创建和配置主机清单

    • 声明 IP 地址数组并创建主机清单文件:

      # 当前只使用一个主节点
      declare -a IPS=(10.1.1.71)
      CONFIG_FILE=inventory/mycluster/hosts.yaml python3 contrib/inventory_builder/inventory.py ${IPS[@]}
      
    • 修改清单文件以设置控制节点和工作节点:vim inventory/mycluster/hosts.yaml

  5. 部署 Kubernetes 集群

    • 将 SSH 密钥从 Ansible 节点复制到所有其他节点:ssh-copy-id user@node_ip

    • 禁用防火墙并启用 IPv4 转发:

      ansible all -i inventory/mycluster/hosts.yaml -m shell -a "sudo systemctl stop firewalld && sudo systemctl disable firewalld"
      ansible all -i inventory/mycluster/hosts.yaml -m shell -a "echo 'net.ipv4.ip_forward=1' | sudo tee -a /etc/sysctl.conf"
      
  6. 拉取harbor镜像ssl报错时containerd证书配置
    crictl拉取镜像配置证书

    • k8s各个节点创建目录,mkdir -p /etc/containerd/certs
    • 从harbor节点拷贝证书,scp /root/harbor/server.crt node:/etc/containerd/certs/server.crt
    • 修改kubespray配置文件,相当于修改各个k8s节点containerd配置文件并重启,

    vim roles/container-engine/containerd/templates/config.toml.j2

    version = 2
    root = "{{ containerd_storage_dir }}"
    state = "{{ containerd_state_dir }}"
    oom_score = {{ containerd_oom_score }}
    
    {% if containerd_extra_args is defined %}
    {{ containerd_extra_args }}
    {% endif %}
    
    [grpc]
      max_recv_message_size = {{ containerd_grpc_max_recv_message_size }}
      max_send_message_size = {{ containerd_grpc_max_send_message_size }}
    
    [debug]
      level = "{{ containerd_debug_level }}"
    
    [metrics]
      address = "{{ containerd_metrics_address }}"
      grpc_histogram = {{ containerd_metrics_grpc_histogram | lower }}
    
    [plugins]
      [plugins."io.containerd.grpc.v1.cri"]
        sandbox_image = "{{ pod_infra_image_repo }}:{{ pod_infra_image_tag }}"
        max_container_log_line_size = {{ containerd_max_container_log_line_size }}
        enable_unprivileged_ports = {{ containerd_enable_unprivileged_ports | lower }}
        enable_unprivileged_icmp = {{ containerd_enable_unprivileged_icmp | lower }}
    {% if enable_cdi %}
        enable_cdi = true
        cdi_spec_dirs = ["/etc/cdi", "/var/run/cdi"]
    {% endif %}
        [plugins."io.containerd.grpc.v1.cri".containerd]
          default_runtime_name = "{{ containerd_default_runtime }}"
          snapshotter = "{{ containerd_snapshotter }}"
          discard_unpacked_layers = {{ containerd_discard_unpacked_layers | lower }}
          [plugins."io.containerd.grpc.v1.cri".containerd.runtimes]
    {% for runtime in [containerd_runc_runtime] + containerd_additional_runtimes %}
            [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.{{ runtime.name }}]
              runtime_type = "{{ runtime.type }}"
              runtime_engine = "{{ runtime.engine }}"
              runtime_root = "{{ runtime.root }}"
    {% if runtime.base_runtime_spec is defined %}
              base_runtime_spec = "{{ containerd_cfg_dir }}/{{ runtime.base_runtime_spec }}"
    {% endif %}
    
              [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.{{ runtime.name }}.options]
    {% for key, value in runtime.options.items() %}
    {% if value | string != "true" and value | string != "false" %}
                {{ key }} = "{{ value }}"
    {% else %}
                {{ key }} = {{ value }}
    {% endif %}
    {% endfor %}
    {% endfor %}
    {% if kata_containers_enabled %}
            [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.kata-qemu]
              runtime_type = "io.containerd.kata-qemu.v2"
    {% endif %}
    {% if gvisor_enabled %}
            [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runsc]
              runtime_type = "io.containerd.runsc.v1"
    {% endif %}
        [plugins."io.containerd.grpc.v1.cri".registry]
          # 以下行为添加内容
          [plugins."io.containerd.grpc.v1.cri".registry.configs."harbor.sys.foobar.com".tls]
               ca_file = "/etc/containerd/certs/server.crt"
               # 或者如下配置
               # insecure_skip_verify = true
          # harbor镜像拉取认证信息
          [plugins."io.containerd.grpc.v1.cri".registry.configs."harbor.sys.foobar.com".auth]
                username = "admin"
                password = "Harbor12345"
    {% if containerd_use_config_path is defined and containerd_use_config_path|bool %}
          config_path = "{{ containerd_cfg_dir }}/certs.d"
    {% else %}
          [plugins."io.containerd.grpc.v1.cri".registry.mirrors]
    {% set insecure_registries_addr = [] %}
    {% for registry in containerd_registries_mirrors %}
            [plugins."io.containerd.grpc.v1.cri".registry.mirrors."{{ registry.prefix }}"]
    {% set endpoint = [] %}
    {% for mirror in registry.mirrors %}
    {% if endpoint.append(mirror.host) %}{% endif %}
    {% if mirror.skip_verify is defined and mirror.skip_verify|bool %}{% if insecure_registries_addr.append(mirror.host | urlsplit('netloc')) %}{% endif %}{%    endif %}
    {% endfor %}
              endpoint = ["{{ ( endpoint | unique ) | join('","') }}"]
    {% endfor %}
    {% for addr in insecure_registries_addr | unique %}
            [plugins."io.containerd.grpc.v1.cri".registry.configs."{{ addr }}".tls]
              insecure_skip_verify = true
    {% endfor %}
    {% endif %}
    {% for registry in containerd_registry_auth if registry['registry'] is defined %}
    {% if (registry['username'] is defined and registry['password'] is defined) or registry['auth'] is defined %}
          [plugins."io.containerd.grpc.v1.cri".registry.configs."{{ registry['registry'] }}".auth]
    {% if registry['username'] is defined and registry['password'] is defined %}
            password = "{{ registry['password'] }}"
            username = "{{ registry['username'] }}"
    {% else %}
            auth = "{{ registry['auth'] }}"
    {% endif %}
    {% endif %}
    {% endfor %}
    
    {% if nri_enabled and containerd_version is version('1.7.0', '>=') %}
      [plugins."io.containerd.nri.v1.nri"]
        disable = false
    {% endif %}
    
    {% if containerd_tracing_enabled %}
      [plugins."io.containerd.tracing.processor.v1.otlp"]
        endpoint = "{{ containerd_tracing_endpoint }}"
        protocol = "{{ containerd_tracing_protocol }}"
        {% if containerd_tracing_protocol == "grpc" %}
        insecure = false
        {% endif %}
      [plugins."io.containerd.internal.v1.tracing"]
        sampling_ratio = {{ containerd_tracing_sampling_ratio }}
        service_name = "{{ containerd_tracing_service_name }}"
    {% endif %}
    

    相当于修改containerd配置文件,不过kubespray每次运行会覆盖,所以需要修改kubespray配置
    vim /etc/containerd/config.toml

    version = 2
    root = "/var/lib/containerd"
    state = "/run/containerd"
    oom_score = 0
    
    
    
    [grpc]
      max_recv_message_size = 16777216
      max_send_message_size = 16777216
    
    [debug]
      level = "info"
    
    [metrics]
      address = ""
      grpc_histogram = false
    
    [plugins]
      [plugins."io.containerd.grpc.v1.cri"]
        sandbox_image = "harbor.sys.foobar.com/pause:3.9"
        max_container_log_line_size = -1
        enable_unprivileged_ports = false
        enable_unprivileged_icmp = false
        [plugins."io.containerd.grpc.v1.cri".containerd]
          default_runtime_name = "runc"
          snapshotter = "overlayfs"
          discard_unpacked_layers = true
          [plugins."io.containerd.grpc.v1.cri".containerd.runtimes]
            [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc]
              runtime_type = "io.containerd.runc.v2"
              runtime_engine = ""
              runtime_root = ""
              base_runtime_spec = "/etc/containerd/cri-base.json"
    
              [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc.options]
                systemdCgroup = true
                binaryName = "/usr/local/bin/runc"
        [plugins."io.containerd.grpc.v1.cri".registry]
          # 以下两行为添加内容
          [plugins."io.containerd.grpc.v1.cri".registry.configs."harbor.sys.foobar.com".tls]
            ca_file = "/etc/containerd/certs/server.crt"
    
          [plugins."io.containerd.grpc.v1.cri".registry.mirrors]
            [plugins."io.containerd.grpc.v1.cri".registry.mirrors."docker.io"]
              endpoint = ["https://registry-1.docker.io"]
    
    

    重启containerd,systemctl restart containerd

    ctr拉取镜像配置证书,注意kubespray部署k8s镜像使用ctr命令,例如/usr/local/bin/ctr -n k8s.io images pull --hosts-dir /etc/containerd/certs.d harbor.sys.foobar.com/k8s/calico/pod2daemon-flexvol:v3.27.3

    mkdir -p /etc/containerd/certs.d/harbor.sys.foobar.com
    cat >/etc/containerd/certs.d/harbor.sys.foobar.com/hosts.toml<<EOF
    server = "https://harbor.sys.foobar.com"
    [host."https://harbor.sys.foobar.com"]
      capabilities = ["pull","resolve"]
      skip_verify = true
      override_path = false
    EOF
    
  7. kubespray报错E0527 19:22:56.946830 35606 remote_image.go:180] “PullImage from image service failed” err=“rpc error: code = Unknown desc = failed to pull and unpack image “harbor.sys.foobar.com/k8s/calico/node:v3.27.3”: failed to resolve reference “harbor.sys.foobar.com/k8s/calico/node:v3.27.3”: pull access denied, repository does not exist or may require authorization: authorization failed: no basic auth credentials” image=“harbor.sys.foobar.com/k8s/calico/node:v3.27.3”
    FATA[0000] pulling image: failed to pull and unpack image “harbor.sys.foobar.com/k8s/calico/node:v3.27.3”: failed to resolve reference “harbor.sys.foobar.com/k8s/calico/node:v3.27.3”: pull access denied, repository does not exist or may require authorization: authorization failed: no basic auth credentials

    • 将harbor仓库设为公开
    • 或者vim roles/kubespray-defaults/defaults/main/download.yml修改,添加--user {{ harbor_auth }}
    nerdctl_image_pull_command: "{{ bin_dir }}/ctr -n k8s.io images pull{% if containerd_registries_mirrors is defined %} --user {{ harbor_auth }} --hosts-dir {{ containerd_cfg_dir }}/certs.d{%- endif -%}"
    

    vim roles/container-engine/containerd/defaults/main.yml添加

    harbor_auth: admin:Harbor12345
    
  8. 启动kubespray部署

    • 启动 Kubernetes 部署:ansible-playbook -i inventory/mycluster/hosts.yaml --become --become-user=root cluster.yml

在这里插入图片描述

FAQ

如何在k8s上安装kubesphere

准备工作
  • 您的 Kubernetes 版本必须为:v1.20.x、v1.21.x、v1.22.x、v1.23.x、* v1.24.x、* v1.25.x 和 * v1.26.x。带星号的版本可能出现边缘节点部分功能不可用的情况。因此,如需使用边缘节点,推荐安装 v1.23.x。
  • 确保您的机器满足最低硬件要求:CPU > 1 核,内存 > 2 GB。
  • 在安装之前,需要配置 Kubernetes 集群中的默认存储类型。

备注

  • 当使用 --cluster-signing-cert-file--cluster-signing-key-file 参数启动时,在 kube-apiserver 中会激活 CSR 签名功能。请参见 RKE 安装问题
  • 有关在 Kubernetes 上安装 KubeSphere 的准备工作,请参见准备工作
部署 KubeSphere

确保您的机器满足安装的前提条件之后,可以按照以下步骤安装 KubeSphere。

  1. 执行以下命令开始安装:

    kubectl apply -f https://github.com/kubesphere/ks-installer/releases/download/v3.4.1/kubesphere-installer.yaml
    kubectl apply -f https://github.com/kubesphere/ks-installer/releases/download/v3.4.1/cluster-configuration.yaml
    
  2. 检查安装日志:

    kubectl logs -n kubesphere-system $(kubectl get pod -n kubesphere-system -l 'app in (ks-install, ks-installer)' -o jsonpath='{.items[0].metadata.name')  -f
    
  3. 使用 kubectl get pod --all-namespaces 查看所有 Pod 是否在 KubeSphere 的相关命名空间中正常运行。如果是,请通过以下命令检查控制台的端口(默认为 30880):

    kubectl get svc/ks-console -n kubesphere-system
    
  4. 确保在安全组中打开了端口 30880,并通过 NodePort (IP:30880) 使用默认帐户和密码 (admin/P@88w0rd) 访问 Web 控制台。

  5. 登录控制台后,您可以在系统组件中检查不同组件的状态。如果要使用相关服务,可能需要等待某些组件启动并运行。

kubespray如何部署kubernetes dashboard

在使用 Kubespray 部署 Kubernetes 集群之后,你可以通过以下步骤来部署 Kubernetes Dashboard

  1. 确认是否启用安装

    • 检查 kubespray/inventory/k8s/group_vars/k8s-cluster/addons.yml 文件中的 dashboard_enabled 设置是否为 true
    • 确认是否已成功安装 Kubernetes Dashboard。
  2. 修改 Kubernetes Dashboard Service 配置

    • 使用以下命令编辑 Kubernetes Dashboard 的 Service 配置:

      kubectl -n kube-system edit service kubernetes-dashboard
      
    • 将 Service 的类型从 ClusterIP 改为 NodePort

    • 保存并退出编辑。

  3. 查看 Kubernetes Dashboard 端口

    • 执行命令查看Kubernetes Dashboard端口:

      kubectl get service -A -o wide | grep kubernetes-dashboard
      
    • 访问https://kubesdashboardip:port

  4. 设置 Kubernetes Dashboard 登录信息

    • 在登录页面上,你可以使用 kubeconfigtoken 进行身份验证。

    • 以下是使用 token 登录的示例:

      • 创建 serviceaccount。

        kubectl create serviceaccount dashboard-admin -n kube-system
        
      • 创建 secret:

        kubectl create secret generic dashboard-admin --from-literal=token=k8sdashboard123 -n kube-system
        
      • 绑定 serviceaccount

        kubectl create clusterrolebinding dashboard-admin --clusterrole=cluster-admin --serviceaccount=kube-system:dashboard-admin
        
      • 获取 admin-token 的 secret 名称:

        kubectl -n kube-system get secret | grep dashboard-admin
        
      • 获取 token:

        kubectl -n kube-system get secret admin-token-h2dxb -o jsonpath={.data.token} | base64 -d
        
    • 成功登录后,你就可以使用 Kubernetes Dashboard 进行集群管理了。

总之,通过 Kubespray 安装 Kubernetes Dashboard 非常简单,只要 Kubernetes 安装成功,Dashboard 就会部署成功。

kubespray如何安装不同的k8s版本

Kubespray 是一个自由开源的工具,它提供了 Ansible 剧本 (playbook) 来部署和管理 Kubernetes 集群。它旨在简化跨多个节点的 Kubernetes 集群的安装过程,允许用户快速轻松地部署和管理生产就绪的 Kubernetes 集群。Kubespray 支持一系列操作系统,包括 Ubuntu、CentOS、Rocky Linux 和 Red Hat Enterprise Linux(RHEL),并可以在各种平台上部署 Kubernetes,包括裸机、公共云和私有云.

如果你想安装不同版本的 Kubernetes,你可以按照以下步骤进行操作:

  1. 修改配置文件:进入 Kubespray 目录后,我们需要修改 inventory/mycluster/group_vars/k8s-cluster/k8s-cluster.yml 配置文件,指定需要使用的 Kubernetes 版本。在该文件中,你可以找到以下配置项:

    • kube_version: 设置所需的 Kubernetes 版本。例如,如果你想使用 Kubernetes v1.18.0,可以将其设置为 v1.18.0
  2. 运行部署命令:运行以下命令来执行部署:

    ansible-playbook -i inventory/mycluster/inventory.ini cluster.yml -b
    

    这将使用你在配置文件中指定的 Kubernetes 版本来部署集群。

  3. 获取 kubeconfig:部署完成后,从 Master 节点上的 /root/.kube/config 路径获取到 kubeconfig 文件。你可以修改其中的 server 地址,将 https://127.0.0.1:6443 改为非 Master 节点可以访问的地址,例如直接替换成其中一台 Master 节点的 IP 地址。

kubespray的每个版本只支持部署特定的k8s版本吗

官方版本介绍

Kubespray 的版本与支持的 Kubernetes (K8s) 版本之间有一定的关联。不同版本的 Kubespray 默认支持不同的 K8s 版本。以下是一些关键信息:

  1. Kubespray 版本和默认支持的 K8s 版本

    • Kubespray 2.12 默认支持的最低 K8s 版本是 v1.15.0,最高支持的 K8s 版本是 v1.17.0
    • 具体的 Kubernetes 二进制文件版本如下:
      • kubelet: v1.15.0
      • kube-apiserver, kube-scheduler, kube-controller-manager: v1.15.0
      • kubectl: v1.15.0
    • 如果你使用的是 Kubespray 2.12,你可以部署 K8s 版本在 v1.15.0v1.17.0 之间。
  2. Kubespray 升级 K8s

    • Kubespray 使用 kubeadm 进行 K8s 的升级。目前,kubeadm 只支持跨越一个版本的升级,例如从 v1.13 升级到 v1.14,或从 v1.14 升级到 v1.15
    • 可以升级的组件包括:
      • Docker
      • Etcd
      • kubeletkube-proxy
      • 网络插件(如 Calico 或 Flannel)
      • kube-apiserver, kube-scheduler, and kube-controller-manager
      • 插件(如 KubeDNS)

总之,Kubespray 和 K8s 版本之间的关系是密切的,你需要根据你的需求选择合适的 Kubespray 版本来部署对应的 K8s 版本。

目前k8s依然迭代较快,没有LTS版本吗

截至目前,Kubernetes (K8s) 并没有官方的长期支持(LTS)版本。但是,从 Kubernetes 1.19 版本开始,每个次要版本都会获得大约 1年的补丁支持¹。这意味着,尽管没有正式的 LTS 版本,但是每个次要版本都会在一定时间内继续接收更新和安全修复,为用户提供了一定程度的稳定性。

Kubernetes 的版本号遵循语义版本控制,表示为 x.y.z,其中 x 是主要版本,y 是次要版本,z 是补丁版本。Kubernetes 项目维护最近三个次要版本的发布分支。例如,目前维护的版本包括 1.301.291.28¹。

此外,社区驱动的项目如 KLTS.io 提供对旧版本 Kubernetes 的额外支持,这可能对需要长期稳定环境的用户有帮助³。

因此,虽然没有官方的 LTS 版本,但 Kubernetes 的支持策略和社区的额外支持,为用户提供了足够的稳定性和安全性。

kubespray升级K8s会造成服务中断吗

使用 Kubespray 升级 Kubernetes (K8s) 集群时,是否会造成服务中断,主要取决于升级过程的管理和集群的配置。以下是一些关键点:

  1. 滚动升级:Kubespray 通常采用滚动升级的策略来更新集群节点。这意味着它会逐个升级节点,而不是同时升级所有节点。这样做的目的是为了最小化服务中断的可能性。

  2. 高可用性配置:如果你的 K8s 集群配置了高可用性,那么在升级过程中,即使某些节点暂时下线,服务也应该能够继续运行。

  3. 升级策略:在升级之前,应该制定详细的升级计划,并在非高峰时段进行升级,以减少对业务的影响。

  4. 测试升级:在生产环境中执行升级之前,在测试环境中进行彻底的升级测试是非常重要的,以确保升级过程不会影响服务的连续性。

  5. 备份和恢复计划:确保在升级前有完整的数据备份和恢复计划,以防升级过程中出现问题。

根据网络上的一些资源,虽然 Kubespray 设计了升级过程以尽量减少服务中断,但不能保证在升级过程中完全没有中断。因此,最佳实践是假设会有短暂的服务中断,并相应地进行计划。

总之,虽然 Kubespray 的设计目标是在不中断服务的情况下升级 K8s 集群,但在实际操作中,仍然需要谨慎规划和准备,以确保服务的平稳运行。

k8s集群网络插件比较

在 Kubernetes 中,选择适合的网络插件对于集群的性能、可靠性和管理效率至关重要。让我们比较一下目前最流行的几个 Kubernetes 网络插件:FlannelCalicoWeaveCanal

Flannel
  • Flannel 是由 CoreOS 开发的项目,可能是最直接且最受欢迎的 CNI 插件之一。
  • 它旨在实现更好的容器间和主机间网络连接。
  • Flannel 相对容易安装和配置,被打包为单个二进制文件 flanneld
  • 可以使用 Kubernetes 集群的现有 etcd 集群来存储其状态信息,无需专用的数据存储。
  • 配置第三层 IPv4 overlay 网络,创建一个大型内部网络跨越集群中的每个节点。
  • 使用 Docker 桥接接口为每个新容器分配地址,不同主机上的 Pod 通过 Flannel 将流量封装在 UDP 数据包中路由到适当的目标。
  • 推荐使用 VXLAN 后端,因为性能更好且需要的手动干预较少。
Calico
  • Calico 是出色的网络管理插件,具备复杂网络配置能力。
  • 提供强大的网络功能,支持网络策略、路由和安全性。
  • 使用 BGP 协议来管理边缘路由器之间的数据包路由。
  • 配置灵活,但相对复杂,适合需要高级网络功能的场景。
  • Calico 可以满足复杂网络需求,但需要更多的配置和管理。
Weave
  • Weave 是另一个流行的 CNI 插件,提供 Overlay 网络和网络策略。
  • 使用 VXLAN 或者 UDP 封装来创建 Overlay 网络。
  • 支持网络隔离、路由和安全性。
  • Weave 在易用性和功能之间取得了平衡,适合中等复杂度的网络需求。

总结:

  • 对于小而简单的集群,可以使用 Flannel。
  • 如果未来网络需要更多设备和复杂策略,Calico 是更好的选择。
  • Weave 则适合中等复杂度的网络需求。
  • 根据实际需求选择最适合自己集群的网络插件。🚀

terway是什么插件,为什么阿里云ack不用calico

Terway 是阿里云开源的基于专有网络 VPC 的容器网络接口(CNI)插件,支持基于 Kubernetes 标准的网络策略来定义容器间的访问策略。它将原生的弹性网卡分配给 Pod 实现 Pod 网络,支持高性能、高可扩展性和安全性的容器通信。

Calico 是另一个强大的开源容器网络和网络安全解决方案,广泛应用于 Kubernetes 集群和其他容器编排平台。它使用 BGP 协议来实现容器间的路由,支持灵活的网络策略和安全规则,适用于大规模部署。

为什么阿里云 ACK 不使用 Calico 呢?主要原因如下:

  1. Terway 是阿里云自研的网络插件,专门为 ACK 优化,支持高性能、高可扩展性和安全性的容器网络。
  2. Calico 在某些场景下可能较复杂,而 Terway 提供了更灵活的 IPAM 策略,避免了地址浪费。
  3. Terway 支持网络策略,可以实现容器间的隔离和安全通信,同时支持对单个容器做带宽的限流。

总之,根据实际需求选择最适合自己集群的网络插件即可。🚀

容器的缺点是什么

容器技术,尽管在开发和运维领域带来了许多优势,但也存在一些缺点。以下是容器技术的一些常见缺点:

  1. 构建和部署的挑战
    尽管容器化可以简化部署过程,但对于某些应用来说,容器化并不总是最佳选择。例如,传统的构建和部署工具如Jenkins,提供了成熟的功能和高度的定制化能力,而容器平台可能需要额外的工作来达到相同的自动化程度。

  2. 自动扩容和缩容的限制
    虽然容器支持无状态服务的自动扩容和缩容,但对于需要固定IP或有状态的服务来说,这可能不是理想的解决方案。此外,对于中小型企业来说,自动扩缩容的需求可能并不频繁。

  3. 隔离性较差
    相比基于hypervisor的虚拟机,容器的隔离性较差。虚拟机提供了更完善的隔离特性,因为它们的系统硬件资源是完全虚拟的,由hypervisor分配,这意味着bug、病毒或入侵可能影响一台虚拟机,但不会蔓延到其他虚拟机上。

  4. 安全性问题
    由于容器共享宿主机的内核,因此如果宿主机的内核存在漏洞,则所有容器都可能受到影响。这与虚拟机不同,后者为每个实例提供了独立的内核。

  5. 工具和生态系统的成熟度
    容器技术相对较新,其监控和管理工具的种类和成熟度仍在发展中。这可能导致在某些情况下,开发者需要花费额外的时间来解决问题。

  6. 数据持久化和存储问题
    容器天生适合无状态应用,但对于需要持久存储的应用,如数据库,容器可能不是最佳选择。数据持久化通常需要额外的存储解决方案和配置。

  7. 网络配置复杂性
    容器可能需要复杂的网络配置来确保通信和服务发现。这可能包括对网络策略、负载均衡和服务网格的配置,这些都可能增加系统的复杂性。

  8. 资源利用率的误解
    虽然容器可以提高资源利用率,但这并不意味着它们总是比虚拟机更节省资源。资源利用率取决于多种因素,包括应用的性质和部署的规模。

  9. 操作系统的选择
    容器通常使用最小化操作系统,这可能限制了某些应用的运行,特别是那些需要完整操作系统功能的应用。

  10. 应用兼容性
    并非所有应用都适合容器化。一些复杂的或者紧密耦合的应用可能难以拆分为容器化服务。

这些缺点并不意味着容器技术不值得使用,而是在考虑采用容器技术时,需要权衡这些因素以确定是否适合您的特定用例和环境。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值