持续集成 Jenkins 做 docker 集群架构的持续集成,怎样控制镜像的构建?

土豆炖洋芋 · 2022年01月14日 · 最后由 土豆炖洋芋 回复于 2022年01月17日 · 2787 次阅读

请问下各位大佬,后端为 docker 集群架构,后端所有代码都在一个工程里。如果用 Jenkins 做持续集成的话,怎样控制镜像的准确构建呢(比如说只有登录服务做了修改,就只构建登录服务)?
现在因能力有限,只能做到有代码更新时,所有镜像全部重新构建,但这样做的话太耗时间了。

共收到 13 条回复 时间 点赞
土豆炖洋芋 关闭了讨论 01月17日 19:43

感谢各位大佬的回复,看了下大家的讨论,还是决定先手动处理把,等后面业务达到了一定高度在评估是否自动化吧。😁

南风 回复

内部公共包/二方库这些,需要使用 nexus 之类的内部 maven 仓库来管理,基础模块预先发布好,业务模块才可以编译、发布

TO 楼主:不要妄图自动化一切,除非你们的 cmdb 做到了高度实时有效,即便是这样,也要花费很多精力:维护组件目录映射关系,通过变更文件清单找到所属组件,从 cmdb 查找、解析所涉组件所有的依赖组件……并且递归查找到 root,然后自上而下去发布基础组件,最后再发布你当前变更所涉及到的组件~

这种不太好处理,而且有些共用的包修改了,很多包都要重新打包的,也解决不了,最好拆分成独立的库

其实呢,主要还是看你的需求是什么。如果是开发环境,每次都重构一次也不是什么大问题,容器化的构建时间基本上都是秒级的,又不是不可以接受。如果是测试环境,为了保障测试环境的稳定性,手动触发可能会更稳妥些。

因为这里面还会涉及到一个问题,就是你那些服务代码的提交频率是什么样的。如果说几个服务的提交频率都差不多,你做这个 Diff 就没什么意义。如果提交频率差异很大,人为判断下,不是更快么。

以解决问题为目标。不一定非得用技术手段去解决

额,前面说的这个思路可以么?可以的话,写脚本实现然后供 jenkins 调用是否可以?

这个属于项目强相关的逻辑,自行写脚本去实现是最合适的。

陈恒捷 回复

那么你通过 git diff 看下改动的代码文件路径包含哪些 service 的文件夹,然后就只运行这个 service 对应的 docker build 命令,是否可以?

这个是可以的,单独的建 job 就行。
但现在的问题点是,Jenkins 怎样才能实现自动分辨 “代码变动的 service“ 并执行对应的 docker build 命令,而不是每次人工判断执行。

墨妖 回复

是由不同的 module 区分的

控制准确构建,核心是要识别到变更涉及的 service 是什么。

如上面槽神说的,既然区分了 service ,那这几个 service 大部分情况下应该是放在不同文件夹的,然后通过 module 或者 git submodule 之类的形式组合成这个大仓库。那么你通过 git diff 看下改动的代码文件路径包含哪些 service 的文件夹,然后就只运行这个 service 对应的 docker build 命令,是否可以?

那 build 的三个 service 怎么区分的代码呢

槽神 回复

不好意思,可能我没表达清楚😥 。我的意思是,怎样才能从开发提交的代码里,决定哪些 service 需要重新 build?
例如,总共 3 个 service,开发第一次提交 “修改 serviceA 的代码”,第二次提交 “修改 serviceB 和 serviceC 的代码”。现状是这两次提交,Jenkins 每次都需要 build3 个 service。有没有一种办法让 Jenkins 只 build 发生修改的 service。

CKL的思考 回复

有个问题是,开发都是对一个工程提交代码,那么怎样从开发提交的代码判断需要执行的 JOB 呢?

首先你的登录服务必须是一个独立的仓库,或者是一个大 project 里面的一个独立的 module,以 spring 为例,可以参考https://www.cnblogs.com/toutou/p/project_module.html
maven build 的时候可以这样做:https://www.cnblogs.com/wenbozhou123/p/7885905.html

都是一个百度就能解决的问题

拆成不同的任务去构建就好了呀。在不同的 Dockerfile 里配置不同服务的打包命令。例如一个 Dockerfile 只负责构建一个服务,然后对应不同的 Jenkins 的 JOB 就好了。如果需要全局构建,那就再建一个 JOB 统一调用一次就好。

需要 登录 后方可回复, 如果你还没有账号请点击这里 注册