共计 3703 个字符,预计需要花费 10 分钟才能阅读完成。
引言
继续部署 (CD) 是在继续集成的根底上,把集成代码或构建产物自动化部署到测试或生产环境。这就是咱们所说的“流动软件”。齐全自动化能够使您的部署无缝、更少的出错几率、更快,并且能够缩短反馈循环,因为您当初能够在每次更改之后进行部署。
实现继续部署须要以下因素:
继续集成 (CI),如 Jenkins 或 JFrog Pipeline,用于构建 / 验证新版本。
制品管理器,如 JFrog Artifactory,用于存储制品,并提供新版本的部署指标 (服务器、智能设施)。
一个部署代理,管制新版本制品的相干运维操作 (进行以后服务器、下载二进制文件、启动服务器)。代理有两种类型:
拉取形式: 在指标上运行的代理
推形式: 在任意集中服务器上运行的代理,近程更新指标服务
两种形式的比照:
拉和推部署模型各有优缺点,您也能够同时应用这两种模型。拉模型最显著的毛病是代理不晓得二进制存储中的更改,因而它不晓得何时触发更新。推送模型的一个毛病是安全性,因为指标须要确保部署代理通过身份验证,并且只能执行受权执行的操作。
在本次分享中,咱们会分享如何创立一个推 / 拉的解决方案。咱们将一步一步实现从构建推送 Docker 镜像到注册核心进行验证,并将其降级生产环境,最初应用 JFrog Artifactory webhook 来触发将其部署到咱们的生产服务器。
1. 搭建制品库 Artifactory
首先,您须要一个运行的 Artifactory 服务器。如果您还没有云实例,您能够收费创立一个云实例。https://jfrog.com/artifactory…
首先创立两个 Docker 仓库:Docker-local-staging 和 Docker-local-prod。
在 new repository 窗口中:
- 抉择 Docker
- 输出“docker-local-staging”作为 key
- 点击“保留并实现”
- 反复上述步骤创立“docker-local-prod”
当初你有了两个空的存储库,持续设置 webhook。导航到治理菜单 Admin |General| Webhooks,点击“新建 webhook“像这样填写:
留神: 在这个例子中,URL 设置为 ” http://host.docker.internal:7979/ “。这是因为 webhook 处理程序将运行在本地主机和端口 7979 上。这里的 host.docker.internal 主机名是用来从 Docker 容器达到主机的。在生产环境中,您可能须要将其更改为您的生产服务器 URL 和您抉择的端口, Artifactory 当文件有变更会被动告诉该地址所执行的服务。
在 secret 字段中,您能够输出任何您想要的字符串,它将以 HTTP header“X-jfrog-event-auth”模式发送到指标服务,这样您就能够验证查问是否来自可信的源。
抉择“Docker tag was promoted”事件。在 Artifactory 中,Docker 镜像能够被降级(升级,代表测试验证通过,将该镜像降级为更高成熟度状态),这须要在不批改内容的状况下将 Docker 镜像从一个仓库挪动到另一个仓库。这能够确保在筹备阶段测试的镜像是将验证通过并是行将投产的镜像。
点击“Select Repositories”,而后抉择要从中晋升镜像的仓库。你也能够在“Include Patterns”局部增加一个过滤器来匹配你的 Docker 镜像清单。
2 创立 Webhook 处理程序
webhook 处理程序将在生产服务器上运行,并将接管一个蕴含变更事件信息的 HTTP 申请。在上述镜像降级的状况下,它的申请数据将看起来像这样:
webhook 处理程序须要做到以下操作:
- 读取并解析 HTTP 音讯体。
- 验证 Docker 镜像和仓库。即便你在 Artifactory 的 webhook 设置中增加了过滤器,服务器也应该总是验证申请输出。
- 拉去最新的 Docker 镜像。
- 进行正在运行的容器 (如果存在的话)。
- 启动新版本。
上面是处理程序的外围逻辑。残缺的代码示例能够在 Github 中找到。
https://github.com/jfrog/project-examples/tree/master/webhook-example
func main() {
http.HandleFunc(“/”, func (w http.ResponseWriter, r *http.Request) {
ctx := context.Background()
p, err := readPayload(r)
if err != nil {
http.Error(w, err.Error(), http.StatusBadRequest)
log.Printf(“Payload reading error: %+v”, err)
return
}
if !isMyServerEvent(p) {
http.Error(w, “Bad event”, http.StatusBadRequest)
log.Printf(“Unexpected event %+v”, p)
return
}
cli, err := client.NewClientWithOpts(client.FromEnv, client.WithAPIVersionNegotiation())
if err != nil {
log.Printf(“New client error: %+v”, err)
return
}
err = pullLatestVersion(cli, ctx)
if err != nil {
log.Printf(“Pull error: %+v”, err)
return
}
err = stopRunningContainer(cli, ctx)
if err != nil {
if client.IsErrNotFound(err){
log.Printf(“Container does not exists”)
} else {
log.Printf(“Stop error: %+v”, err)
return
}
}
err = startContainer(cli, ctx)
if err != nil {
log.Printf(“Start error: %+v”, err)
} else {
log.Printf(“Container updated “)
}
})
http.ListenAndServe(“:8081”, nil)
}
它应用多个开源库:
- golang 内置的 http server
- docker golang SDK
其余局部代码请查看 github 源码,蕴含输出信息查看,拉取最新镜像,更新启动新的容器等
2 构建并推送 docker images(demo 利用)
应用以下简略的 golang web 服务器进行测试: server.go
测试启动:go run serve.go
一个很简略测试服务,当你在浏览器中加载“http://localhost:8080”时打印出“Hello world”。
以下是这个应用程序的 Dockerfile (大部分来自 VSCode 的 golang Dockerfile 模板):
用以下命令构建 dockerfile。这在 CI 继续集成过程中应该是自动化的(基于 JFrog CLI)。
docker build . -t localhost:8082/docker-local-staging/helloworld
jfrog rt docker-push localhost:8082/docker-local-staging/helloworld docker-local-staging –url http://localhost:8082/artifactory –user admin –password password
jfrog rt docker-promote helloworld docker-local-staging docker-local-prod –copy –user admin –password password –url http://localhost:8082/artifactory
jfrog rt docker-promote 该命令将触发以下流程:
- Artifactory 将 Docker 镜像复制到 Docker-local-prod 存储库中。
- Artifactory 通过 HTTP 申请调用 Webhook。
- Webhook 坐在服务器获取最新版本。
- 它会杀死正在运行的服务器 (如果存在的话)。
- 用最新的更改并启动新的服务。
如果你实现到这里,祝贺您,您曾经实现了一个自动化部署计划!!!
4. 一些倡议
心愿下面的指南能帮忙你开始实现继续部署和应用 webhook。还有许多附加的性能能够增加。以下是一些倡议:
- 在 CI 环境中执行所有 Docker / Jfrog CLI 命令。例如,应用蕴含“#prod”的提交音讯,使开发人员可能进行部署。
- 应用容器编排。进行构建公布 Docker 命令,比方应用 Kubernetes、Docker swarm 或者一些云提供商 SDK。
- 进步安全性。您能够向来自 Artifactory 的 HTTP 查问增加一个自定义头,以确保该查问不会由发现您的凋谢端口并意外触发部署动作。
- 尝试通过为“docker push”事件创立 webhook,自动化分段部署。