在ubuntu 安装时,手动配置 ipv4,name servers 和 searchdomains 是什么

  1. Name Servers(DNS 服务器) 用于解析域名。例如: • 8.8.8.8, 8.8.4.4(Google DNS) • 或者你网络提供商的 DNS,如 114.114.114.114

填写多个时用 逗号分隔。

  1. Search Domains(搜索域) 这个选项是为了方便局域网域名解析。举个例子: • 如果你填写了 example.com,当你在终端中访问 server1,系统会自动尝试解析为 server1.example.com。 • 多个域名可以用空格分隔:example.com local.lan

这主要用于企业或学校内的内网环境,不填也可以。

我使用虚拟机和 NAT 网络,如何配置代理?我的宿主机上使用 Clash

确认 Clash 开放了公网访问(监听 0.0.0.0)

编辑 Clash 的配置文件 ~/.config/clash/config.yaml 或 clash.meta.yaml,确保监听地址改为:

mixed-port: 7890
allow-lan: true   # ✅ 允许局域网设备访问 Clash
bind-address: 0.0.0.0  # ✅ 不要写 127.0.0.1

在虚拟机中设置代理 在 Ubuntu 虚拟机里,可以这样设置环境变量方式配置代理:

export http_proxy="http://192.168.79.1:7890"
export https_proxy="http://192.168.79.1:7890"
export all_proxy="socks5://192.168.79.1:7891"

K8s 安装软件仓库地址

关于 https://github.com/kubernetes/kubernetes/issues/123673 , Kubernetes 更改了其软件包仓库(repository)的地址。旧的仓库地址(通常是 apt.kubernetes.io)已弃用,并迁移到了新的地址 pkgs.k8s.io

首先我们要删除原来的/etc/apt/sources.list.d/kubernetes.list或者是中央sources.list中的k8s相关 然后

echo "deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://pkgs.k8s.io/core:/stable:/v1.28/deb/ /" | sudo tee /etc/apt/sources.list.d/kubernetes.list
$ curl -fsSL https://pkgs.k8s.io/core:/stable:/v1.28/deb/Release.key | sudo gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg

/etc/apt/keyrings/这个文件夹可能需要自己创建 然后

sudo apt update

sudo apt install -y kubelet kubeadm kubectl

K8s初始化

The connection to the server localhost:8080 was refused - did you specify the right host or port?

mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config

`kubectl get nodes

删除pods

只需要删除对应的配置文件即可,比如

kubectl delete -f kube-flannel.yml

安装网络组件

在安装前,需要运行

sudo kubeadm init --pod-network-cidr=10.244.0.0/16

安装MySQL Pod

注意一定要有PV和PVC,否则PVC无法正确创建。不是所有的环境都能够自动配置StorageLCass

安装Nacos

https://github.com/nacos-group/nacos-k8s/blob/master/README-CN.md

彻底恢复 PV

kubectl get pv mysql-data-pv

删除整个claimRef块

NodePort 与 ClusterIP

准确来说设置 NodePort 没什么影响,只是会扩大暴露范围,并且它是有范围的

apiVersion: v1
kind: Service
metadata:
  name: mysql
  labels:
    name: mysql
spec:
  type: NodePort                   # <— makes it reachable on the node’s IP
  selector:
    name: mysql
  ports:
    - port:     33066              # <— the “internal” ClusterIP port (clients in-cluster)
      targetPort: 3306             # <— the container’s actual listening port
      nodePort:   33066            # <— the port on each node’s IP

范围可调

Nacos pod has unbound immediate PersistentVolumeClaims

$ kubectl get pvc data-nacos-0

NAME           STATUS    VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS          AGE

data-nacos-0   Pending                                      managed-nfs-storage   3d19h

查看它的情况

kubectl describe pvc data-nacos-0

...Waiting for a volume to be created either by the external provisioner 'fuseim.pri/ifs' or manually by the system administrator

此处显示,也就是我们的nfs-storageclass的设置

provisioner: fuseim.pri/ifs

但在我们的nfs-development中

env:
  - name: PROVISIONER_NAME
    value: k8s-sigs.io/nfs-subdir-external-provisioner

所以需要修改nfs-storageclass

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: managed-nfs-storage
provisioner: k8s-sigs.io/nfs-subdir-external-provisioner    # ← must match PROVISIONER_NAME
parameters:
  server: "192.168.79.143"           # your NFS server
  share:  "/nfs/data/nfs-share"      # the same NFS_PATH you gave the pod
  archiveOnDelete: "false"
reclaimPolicy: Delete
volumeBindingMode: Immediate

这时候删除data-nacos-0

kubectl delete pvc data-nacos-0 会卡住

先看看是否有阻碍它的finalizers

kubectl get pvc data-nacos-0 -o jsonpath='{.metadata.finalizers}'
# e.g. ["kubernetes.io/pvc-protection"]

然后清除

kubectl patch pvc data-nacos-0 \
  -p '{"metadata":{"finalizers":[]}}' \
  --type=merge

然后删除其绑定的 pv

kubectl get pv

kubectl delete pv <pv-name>

pv大概率也会卡住,所以也要清除

kubectl patch pv mysql-data-pv \
  -p '{"metadata":{"finalizers":[]}}' \
  --type=merge

删除 pvc 和 pv 后,nacos-0 还没有重新创建

kubectl get sts nacos

如果看到 nacos 仍然存在,说明控制器还在,只是还没机会重建 Pod

kubectl delete pod nacos-0

删除掉旧 pod

kubectl get pods -l app=nacos

安装nacos镜像无法访问

使用这个

docker pull nacos-registry.cn-hangzhou.cr.aliyuncs.com/nacos/nacos-server:v${nacos.version}

安装ingress-controller

kubectl apply \
  -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.8.1/deploy/static/provider/cloud/deploy.yaml

nacos-ingress.yaml

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nacos-ingress
spec:
  rules:
    - host: nacos-web.nacos-demo.com
      http:
        paths:
          - path: /nacos
            pathType: Prefix
            backend:
              service:
                name: nacos-headless
                port:
                  name: server

检查服务

kubectl get svc -n ingress-nginx

输出,说明绑定在 32530

NAME                                 TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                      AGE
ingress-nginx-controller             NodePort    10.108.58.154   <none>        80:32530/TCP,443:31811/TCP   11h
ingress-nginx-controller-admission   ClusterIP   10.96.204.241   <none>        443/TCP                      11h

Ingress的NodePort访问不到

在 DNS 中添加解析后,还是无法访问

# root @ sc-master in ~ [13:01:37] 
$ sudo vi /etc/hosts

# root @ sc-master in ~ [13:33:23] 
$ ping nacos-web.nacos-demo.com
PING nacos-web.nacos-demo.com (192.168.79.144) 56(84) bytes of data.
64 bytes from sc-node1 (192.168.79.144): icmp_seq=1 ttl=64 time=1.41 ms
64 bytes from sc-node1 (192.168.79.144): icmp_seq=2 ttl=64 time=0.308 ms
64 bytes from sc-node1 (192.168.79.144): icmp_seq=3 ttl=64 time=0.300 ms
64 bytes from sc-node1 (192.168.79.144): icmp_seq=4 ttl=64 time=0.401 ms
64 bytes from sc-node1 (192.168.79.144): icmp_seq=5 ttl=64 time=0.333 ms
64 bytes from sc-node1 (192.168.79.144): icmp_seq=6 ttl=64 time=0.279 ms
^C
--- nacos-web.nacos-demo.com ping statistics ---
6 packets transmitted, 6 received, 0% packet loss, time 5078ms
rtt min/avg/max/mdev = 0.279/0.505/1.409/0.406 ms

# root @ sc-master in ~ [13:33:46] 
$ nc nacos-web.nacos-demo.com 32530
^C

# root @ sc-master in ~ [13:37:14] C:130
$ kubectl get ingress nacos-ingress -n default
NAME            CLASS    HOSTS                      ADDRESS   PORTS   AGE
nacos-ingress   <none>   nacos-web.nacos-demo.com             80      12h

可以看到 Class 是空的,查看日志

kubectl logs -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx --tail 20 -f
# log 中包含
W0501 17:18:40.042396       6 controller.go:328] ignoring ingress default/nacos-ingress in default based on annotation : ingress does not contain a valid IngressClass

所以要给 Ingress 指定 IngressClass

spec:
  ingressClassName: nginx
  rules:
  - host: nacos-web.nacos-demo.com
    http:
      paths:
      - path: /nacos
        pathType: Prefix
        backend:
          service:
            name: nacos-headless
            port:
              name: server

然后 apply,可以看到

I0502 06:48:38.590512 … “creating ingress” ingress="default/nacos-ingress" ingressclass="nginx"
I0502 06:48:38.645059 … “Backend successfully reloaded”
I0502 06:49:02.167770 … “updating Ingress status” … newValue=[{"ip":"10.108.58.154"}]

再验证

kubectl get ingress nacos-ingress -n default

NAME            CLASS   HOSTS                          ADDRESS         PORTS   AGE
nacos-ingress   nginx   nacos-web.nacos-demo.com       10.108.58.154   80      10m

集群内部HTTP 请求可以得到回复

$ curl -H "Host: nacos-web.nacos-demo.com" \
     http://10.108.58.154/nacos/index.html -v
*   Trying 10.108.58.154:80...
* TCP_NODELAY set
* Connected to 10.108.58.154 (10.108.58.154) port 80 (#0)
> GET /nacos/index.html HTTP/1.1
> Host: nacos-web.nacos-demo.com
> User-Agent: curl/7.68.0
> Accept: */*
> 
* Mark bundle as not supporting multiuse
< HTTP/1.1 200 

集群外部还是请求不到32530端口

这是因为我们 DNS 设置为

vim /etc/hosts
...
192.168.79.144   nacos-web.nacos-demo.com

但是官方的 nginx-ingress.yaml中

spec:
  type: NodePort
  externalTrafficPolicy: Local
  ports:
    - name: http
      port: 80
      nodePort: 32530
    

我们验证一下是不是这样配置

kubectl get svc ingress-nginx-controller -n ingress-nginx -o yaml | grep externalTrafficPolicy

# 如果显示
externalTrafficPolicy: Local

就说明只有本地一个 IP 能访问,而不是 VPC 中的每个 Pod 都能访问。我们必须修改 DNS

192.168.79.145   nacos-web.nacos-demo.com

或者我们修改官方 yaml 的策略,这样任意 Node 上 NodePort 都能生效

kubectl patch svc ingress-nginx-controller -n ingress-nginx \
  -p '{"spec":{"externalTrafficPolicy":"Cluster"}}'

Helm 安装Jenkins

$ helm repo add jenkinsci https://charts.jenkins.io
helm repo update

helm install jenkins jenkinsci/jenkins \
  --namespace cicd --create-namespace \
  --set controller.serviceType=ClusterIP \
  --set controller.ingress.enabled=true \
  --set controller.ingress.hostName=jenkins.example.com \
  --set persistence.size=10Gi
  --set persistence.storageClass=managed-nfs-storage
  --set 'controller.env[0].name=TZ' \
  --set 'controller.env[0].value=Asia/Shanghai'
  --set controller.ingress.ingressClassName=nginx \
  --set controller.ingress.annotations."kubernetes\.io/ingress\.class"=nginx

查看初始密码

kubectl exec -n cicd -it jenkins-0 -c jenkins -- cat /run/secrets/additional/chart-admin-password && echo

error: unknown command “port‑forward” for “kubectl”

复制下面这个,-是 ASCII 字符

kubectl port-forward -n cicd svc/jenkins 8080:8080

Jenkins登录后报错

我们查看日志

$ kubectl logs -n cicd jenkins-0 -c jenkins \
  | grep -C5 <此处填写logging ID>

# 看到以下内容
java.nio.file.NoSuchFileException: /var/jenkins_home/secrets/org.springframework.security.web.authentication.rememberme.TokenBasedRememberMeServices.mac
        at java.base/sun.nio.fs.UnixException.translateToIOException(Unknown Source)
        at java.base/sun.nio.fs.UnixException.rethrowAsIOException(Unknown Source)
        at java.base/sun.nio.fs.UnixException.rethrowAsIOException(Unknown Source)
        at java.base/sun.nio.fs.UnixFileSystemProvider.newByteChannel(Unknown Source)

文件不存在。这个错误是由于创建文件到以下路径: $JENKINS_HOME/secrets/…mac. 但是在我们的步骤中,我们使用 nfs-subdir-external-provisioner,正常来说是自动创建了 pvc

查看 nfs-share/下,确实存在 pvc。那么就是权限问题 Jenkins 默认不用 root 用户允许,不像 nacos。所以不具有权限,而是使用UID/GID 1000:1000 所以我们可以手工 chown,但太麻烦

helm upgrade jenkins jenkinsci/jenkins \
  --namespace cicd \
  --reuse-values \
  --set 'controller.securityContext.fsGroup=1000'

设置fsGroup 这样就 ok 了

Jenkins K8S中无法配置 maven 和 jdk

原因很简单。如果我们直接在全局 tool 中配置环境变量,是行不通的。因为实际上他对应的是Jenkins所在机器,而这个机器是k8s的一个 pod。我们把maven和jdk安装进去是十分费力的。

而且如果采用自动安装的方式,我遇到了JDK有一个脚本只符合bash的重定位语法,而ubuntu默认是dash。这个也很难解决

最后采取了配置静态节点的方法,不使用k8s插件了。配置到一台节点上进行构建

Ubuntu虚拟机创建 20G 但只有 10G

需要进行 LVM 扩容

Jenkins构建后节点磁盘空间问题

du -sh * | sort -h   # 查看各文件夹大小排序

最后发现是 docker 里面镜像太多使用了很多空间。containerd 占用也多,不过我没清

cd /var/lib/docker
# 删除所有未运行容器、悬空镜像、网络、构建缓存、未挂载卷
docker system prune -a --volumes --force

然后在 Jenkinsfile 中添加

post {
    always {
        sh 'docker system prune -af --volumes'
    }
}

DockerHub 限速问题

# 1. 删除旧的 secret
kubectl delete secret dockerhub-auth -n cicd

# 2. 重新创建(把下面的 <用户名>、<PAT>、<email> 换成正确的)
kubectl create secret docker-registry dockerhub-auth \
  --docker-server=https://index.docker.io/v1/ \
  --docker-username=<DockerID> \
  --docker-password=<新的PAT_or_密码> \
  --docker-email=<邮箱地址> \
  -n cicd
# 3. 应用到 Jenkins Chart 默认 SA 叫 "jenkins"(你也可以 helm get values 看真实名字)
# 这边我用helm部署自带了sa
kubectl patch serviceaccount jenkins -n cicd \
  -p='{"imagePullSecrets":[{"name":"dockerhub-auth"}]}'

不过最好还是推到阿里云私有仓库,懒得搞了,实验先这样

不过在这个过程中还发现可能是我的代理服务器问题。

$ kubectl describe pod jenkins -n cicd

...
failed to fetch anonymous token: Get "https://auth.docker.io/token?scope=repository%3Ajenkins%2Fjenkins%3Apull&service=registry.docker.io": EOF

中间换过一次全局代理,可能是clash 有 bug。可以重启一下

Springboot bootstrap问题

需要引入 maven 依赖,才能使用

dashboard token

sudo kubectl -n kubernetes-dashboard create token dashboard-admin --duration=24h

k8s驱逐问题

在原有的/var/lib/kubelet/config.yaml中添加一条。注意是顶级的,不需要 tab

evictionHard:
	imagefs.available: "15%" # 镜像文件系统可用空间低于15%时触发驱逐 (如果您的镜像存储和节点根文件系统是分开的)
	imagefs.inodesFree: "5%" # 镜像文件系统可用inode低于5%时触发驱逐
	memory.available: "100Mi" # 节点可用内存低于100Mi时触发驱逐
	nodefs.available: "10%" # 节点根文件系统可用空间低于10%时触发驱逐 (这是您主要关注的)
	nodefs.inodesFree: "5%" # 节点根文件系统可用inode低于5%时触发驱逐

Sentinel识别不到服务

需要增加一个暴露的port用于与sentinel连接

helm部署RabbitMQ

    echo "Username      : user"
    echo "Password      : $(kubectl get secret --namespace default rabbitmq -o jsonpath="{.data.rabbitmq-password}" | base64 -d)"
    echo "ErLang Cookie : $(kubectl get secret --namespace default rabbitmq -o jsonpath="{.data.rabbitmq-erlang-cookie}" | base64 -d)"