学习如何从头开始设置 CI/CD 管道
在本教程中,我们将以 Go 应用程序为例并设置 CI/CD 管道。
Go因其能够简化和保障现代应用程序的构建,在开发者中越来越受欢迎。该语言由 Google 创建,因其开源特性和使用 Go 语言编写程序的能力而备受青睐。Go 还允许用户自由构建自己的前端网站和应用程序,并且易于开发、维护和使用。企业可以依靠 Go 来构建和扩展云计算系统,同时享受其强大的并发功能。此外,Go 还能在不占用过多资源的情况下提供高性能。
今天,我们将创建一个简单的 Go 应用程序,并为其设置 CI/CD 流水线。开始吧!
先决条件
-
创建一个免费的 SingleStore 帐户。在本教程中,我们将使用 SingleStore 作为数据库解决方案。SingleStore 是一个高性能内存数据库,支持 SQL 和 NoSQL 数据模型。
-
创建免费的Harness 云帐户来设置 CI/CD
-
从这里快速下载并安装 Go
-
从任何云提供商访问 Kubernetes 集群来部署我们的应用程序(您也可以使用Minikube或Kind来创建单节点集群)。
-
Docker,最好是Docker Desktop
教程
示例代码库可在此处访问;您可以随意 fork 它或直接照着做。我不会详细介绍应用程序代码本身。它是一个示例“Hello World”应用,会在本地主机 8080 端口打印文本“Hello World”。
以下是该文件的代码main.go
:
package main
import (
"fmt"
"log"
"net/http"
)
func homePage(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Home Page")
}
func wsEndpoint(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hello World")
}
func setupRoutes() {
http.HandleFunc("/", homePage)
http.HandleFunc("/ws", wsEndpoint)
}
func main() {
fmt.Println("Hello World")
setupRoutes()
log.Fatal(http.ListenAndServe(":8080", nil))
}
该应用程序还有一个带有main_test.go
简单测试用例的测试文件。
package main
import (
"net/http"
"net/http/httptest"
"testing"
)
func TestHomePage(t *testing.T) {
req, err := http.NewRequest("GET", "/", nil)
if err != nil {
t.Fatal(err)
}
rr := httptest.NewRecorder()
handler := http.HandlerFunc(homePage)
handler.ServeHTTP(rr, req)
if status := rr.Code; status != http.StatusOK {
t.Errorf("handler returned wrong status code: got %v want %v",
status, http.StatusOK)
}
if rr.Body.String() != "Home Page" {
t.Errorf("handler returned unexpected body: got %v want %v",
rr.Body.String(), "Home Page")
}
}
func TestWsEndpoint(t *testing.T) {
req, err := http.NewRequest("GET", "/ws", nil)
if err != nil {
t.Fatal(err)
}
rr := httptest.NewRecorder()
handler := http.HandlerFunc(wsEndpoint)
handler.ServeHTTP(rr, req)
if status := rr.Code; status != http.StatusOK {
t.Errorf("handler returned wrong status code: got %v want %v",
status, http.StatusOK)
}
if rr.Body.String() != "Hello World" {
t.Errorf("handler returned unexpected body: got %v want %v",
rr.Body.String(), "Hello World")
}
}
您在 repo 中看到的 Dockerfile 将用于构建我们的应用程序并将其作为映像推送到 Docker Hub。
FROM golang:1.16.4-buster AS builder
ARG VERSION=dev
WORKDIR /go/src/app
COPY main.go .
RUN go build -o main -ldflags=-X=main.version=${VERSION} main.go
FROM debian:buster-slim
COPY --from=builder /go/src/app/main /go/bin/main
ENV PATH="/go/bin:${PATH}"
CMD ["main"]
接下来我们将使用以下命令构建镜像并将其推送到 Docker Hub,
docker buildx build --platform=linux/arm64 --platform=linux/amd64 -t docker.io/<docker hub username>/<image name>:<tag> --push -f ./Dockerfile .
一旦构建和推送成功,您可以通过访问您的 Docker Hub 帐户进行确认。
我们将在 Kubernetes 集群上部署我们的应用程序。您可以在forked 的仓库
中 看到deployment.yaml
和文件,它们定义了部署和服务,以帮助我们部署和公开应用程序。此时,请确保您的 Kubernetes 集群已启动并正在运行。service.yaml
我们的deployment.yaml文件如下所示
apiVersion: apps/v1
kind: Deployment
metadata:
name: go-app-deployment
spec:
replicas: 1
selector:
matchLabels:
app: go-app
template:
metadata:
labels:
app: go-app
spec:
containers:
- name: go-app
image: pavansa/golang-hello-world:latest
ports:
- containerPort: 8080
env:
- name: PORT
value: "8080"
service.yaml 文件如下所示,
apiVersion: v1
kind: Service
metadata:
name: go-app-service
spec:
selector:
app: go-app
ports:
- name: http
protocol: TCP
port: 80
targetPort: 8080
type: LoadBalancer
现在是时候设置一个 Harness 帐户来执行 CI/CD 了。Harness 是一个具有 AI/ML 功能的现代 CI/CD 平台。
创建一个免费的 Harness 帐户并开始您的第一个项目。注册 Harness 后,您将获得全新的 CI/CD 体验和功能。
添加所需的连接器,例如Harness Delegate、您的 GitHub 仓库、Docker Hub 帐户和密钥。Harness 中的 Delegate 是您需要在目标集群(在本例中为 Kubernetes 集群)上安装/运行的服务/软件,用于将您的构件、基础设施、协作、验证和其他提供程序与 Harness Manager 连接起来。首次设置 Harness 时,您需要安装 Harness Delegate。
持续集成
登录 Harness 后,它首先会要求您创建一个项目。
连接到您的源代码控制管理(如 GitHub),其中包含应用程序代码。
当您点击执行下的“Go Build App”时,您将看到以下设置详细信息。
让我们修改上一步/上面的步骤,将其命名为“Test Go App”,在命令选项卡中添加以下代码,然后保存并运行管道。
我们成功为应用程序创建了一条 CI 流水线,用于代码的构建和测试。接下来,让我们将这个想法扩展到我们的目标环境,也就是 Kubernetes,来部署这段无错误的应用程序代码。
持续交付和部署
为您的阶段添加一个名称,选择部署类型为“Kubernetes”,然后单击“设置阶段”。
我们需要创建一个服务。因此,点击“添加服务”。下一步,我们需要为服务添加名称和清单详细信息。
指定 K8S 清单存储。我们知道清单文件位于 GitHub 中。因此选择 GitHub。
现在,从你的 GitHub 仓库添加清单详细信息。 保存所有内容并继续。 你应该会看到包含清单详细信息的服务。
同样,添加新的基础设施。选择“Kubernetes”作为基础设施类型,并添加集群详细信息。
保存并继续。
下一步,您需要选择部署策略类型。我们选择“滚动”作为部署策略。
您应该看到管道从 CI 开始逐步执行,然后 CD 成功执行。
自动化 CI/CD
最后一步是通过创建触发器来实现 CI/CD 流水线的自动化。我们开始吧。
添加 GitHub 触发器,每当有人将新代码推送到主分支时,管道就会自动触发。
保存所有内容并创建触发器。
您应该在“触发器”选项卡下看到已创建的触发器。
现在,让我们确认一下我们的 CI/CD 是否自动化并正常运行。将一个 readme 文件添加到我们的 GitHub 仓库,看看它是否触发了我们的流水线。
我们已经成功地使用 Harness 实现了 Go 应用程序的 CI/CD 流程自动化。
另外,请查看我关于持续集成和部署的其他文章。