0%

Golang程序部署到k8s

前言

服务通过容器化部署后,容器增多,对于容器管理编排 主流是使用Kubernetes(K8S),本文主要是记录将一个go程序部署到k8s集群过程

环境:

Macbook Pro

Docker Desktop

Docker: (Docker version 27.4.0, build bde2b89)

K8s: 1.30.5

部署操作

Golang程序

此次主要是记录部署过程,golang程序为简单的web服务,参考代码,启动后 通过ip:8081/info 获取返回信息

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
func main() {

engine := gin.Default()
engine.GET("/info", func(context *gin.Context) {

hostname, _ := os.Hostname()
ip := getExternalIP()
context.String(http.StatusOK, "This is version: v1, running in pod %s, ip: %v", hostname, ip)

})
engine.Run(":8081")
}

func getExternalIP() string {
// 与外部服务器建立连接(这里连接到 Google 的 DNS)
conn, err := net.Dial("udp", "1:80")
if err != nil {
log.Fatal(err)
}
defer conn.Close()

// 获取本机的外部 IP 地址
localAddr := conn.LocalAddr().(*net.UDPAddr)
return localAddr.IP.String()
}

dockerfile

编译容器和业务容器分开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#依赖镜像
FROM golang:1.19-alpine3.18 as builder

#作者信息
MAINTAINER "zhangmengnan"

# 配置模块代理
ENV GO111MODULE=on
ENV GOPROXY=https://goproxy.cn,direct

#工作目录
WORKDIR /mnt/engine
ADD . .

#在Docker工作目录下执行命令, 编译
RUN go build -o server ./server.go

FROM golang:1.19-alpine3.18


RUN mkdir /mnt/engine/

WORKDIR /mnt/engine

# 从编译机器拷贝二进制和启动脚本
COPY --from=builder /mnt/engine/server .

#执行项目的命令
CMD ["./server"]

镜像推送到dockerhub

创建账号

镜像其实只要推送到镜像仓库就行,私有库公有库, 这里以dockerhub为例

1、需要注册dockerhub的账号

2、在repositories导航栏内选择创建一个容器仓库

3、创建仓库,如 username/repositoryName, 我的案例为 gitzmn/go-publish-k8s

4、效果如图

推送镜像

1、打包本地镜像

1
docker build -t gitzmn/go-publish-k8s:v1 . 

在dockerfile目录执行 docker build -t (username)/(repositoryName):(version) .

2、推送镜像

1
docker push gitzmn/go-publish-k8s:v1

推送时候需要保证是可以访问dockerhub的,如果不行需要登陆 docker login。

1
2
docker push gitzmn/go-publish-k8s:latest
The push refers to repository [docker.io/gitzmn/go-publish-k8s] denied: requested access to the resource is denied

如果还是出现访问被拒绝情况可以检查一下docker的版本,我本地推送时候经常失败,升级docker版本即可(Docker version 27.4.0, build bde2b89)

3、推送成功后界面查看

启动k8s

docker和k8s都是通过docker desktop启动的,在界面点击开启,等待后则k8s启动

启动后通过命令行测试,获取k8s结点信息。由于启动的是单机版本,只有一个结点

编写k8s文件

创建 deployment.yaml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: go-publish-k8s # 声明pod的名称
namespace: my-workspace # 声明工作空间,默认为default
spec:
replicas: 2 # 声明副本数
selector:
matchLabels:
name: go-publish-k8s
template:
metadata:
labels:
name: go-publish-k8s
spec:
containers:
- name: go-publish-k8s-container
image: gitzmn/go-publish-k8s:v1 # 指定镜像
imagePullPolicy: IfNotPresent
ports:
- containerPort: 8081 # containerPort是声明容器内部的port

---
apiVersion: v1
kind: Service
metadata:
name: go-publish-k8s-service # 声明创建的服务名称
namespace: my-workspace # 声明工作空间,默认为default
spec:
type: NodePort
ports:
- name: http
port: 18080 # Service暴露在cluster-ip上的端口,通过<cluster-ip>:port访问服务,通过此端口集群内的服务可以相互访问
targetPort: 8081 # Pod的外部访问端口,port和nodePort的数据通过这个端口进入到Pod内部,Pod里面的containers的端口映射到这个端口,提供服务
nodePort: 31080 # Node节点的端口,<nodeIP>:nodePort 是提供给集群外部客户访问service的入口
selector:
name: go-publish-k8s

部署服务到k8s

1、创建命名空间

1
kubectl create namespace my-workspace

2、在deployment.yaml文件目录下执行

1
kubectl create -f deployment.yaml

3、查看创建的pod

1
kubectl get po -n my-workspace

访问k8s服务

由于配置文件中指定的service访问是nodeport, 使用k8s结点 也就是本机ip:31080/info 即可访问

k8s界面管理

安装界面

对于k8s集群管理上,k8s本身提供了界面,但是我们选择了其他开源界面 Kuboard(https://kuboard.cn/v4/install/#%E8%87%B4-kuboard-v3-%E7%94%A8%E6%88%B7)

参考官方提供的手册启动Kuboard

1、创建mysql库表,使用了mac电脑自己安装的mysql

2、启动Kuboard docker容器, 启动时候需要连接mysql,由于我使用的是宿主机的mysql,所以ip使用了host.docker.internal,这是mac支持访问宿主机的方式

1
2
3
4
5
6
7
8
9
10
11
12
sudo docker run -d \
--restart=unless-stopped \
--name=kuboard \
-p 80:80/tcp \
-e TZ="Asia/Shanghai" \
-e DB_DRIVER=com.mysql.cj.jdbc.Driver \
-e DB_URL="jdbc:mysql://host.docker.internal:3306/kuboard?serverTimezone=Asia/Shanghai" \
-e DB_USERNAME=kuboard \
-e DB_PASSWORD=Kuboard123 \
swr.cn-east-2.myhuaweicloud.com/kuboard/kuboard:v4
# eipwork/kuboard:v4

登陆Kuboard

进入登陆页后,提供了默认的用户名和密码 admin/ Kuboard123

导入k8s集群

在首页选择集群导入后,填写集群名称,导入访问我选择的是Secret Token,在本机执行提供的命令,生成红色的token,拷贝到token处。 apiServer地址 通过 执行 kubectl config view –minify -o jsonpath=’{.clusters[0].cluster.server}’ 获取, 点击导入等待一会导入成功

查看启动的pod