使用Oracle数据库、Helidon和Coherence构建Kubernetes容器,轻松又实用 — 第6部分:构建容器,享受部署的乐趣
2025/1/3 21:04:13
本文主要是介绍使用Oracle数据库、Helidon和Coherence构建Kubernetes容器,轻松又实用 — 第6部分:构建容器,享受部署的乐趣,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
现在我们的应用已经跑起来了,我们最终希望把它部署到Kubernetes集群上。但是在那之前,我们得先构建镜像。
咱们开始吧。
构建容器图像 — Coherence 图像记得,这个待办事项应用包括三个部分:
前端和后端都是无状态的微服务,而Coherence则是有状态的。我们必须分别为它们构建容器镜像。我们先从构建Coherence的镜像开始。
但在构建镜像之前,我们必须改变配置Hibernate的模式。这是因为Hibernate配置文件包含了数据库的用户名称和密码,所以我们绝对不想将这些信息硬编码到镜像中。相反,在部署到Kubernetes时,我们最终希望使用Kubernetes Secret并将其挂载到pod的卷。至于钱包文件,我们希望使用Oracle Database Operator来为我们获取它,并将Hibernate配置文件的位置作为参数传递给程序。
首先,修改 coherence-cache-config.xml 并在 Hibernate CacheStore 的 init-param 中添加以下内容(除了 entityname 参数以外):
<cachestore-scheme> <class-scheme> <class-name> com.oracle.coherence.hibernate.cachestore.HibernateCacheStore </class-name> <init-params> <init-param> <param-type>java.lang.String</param-type> <param-value>{entityname}</param-value> </init-param> <init-param> <param-name>java.lang.String</param-name> <param-value>${coherence.hibernate.config hibernate.cfg.xml}</param-value> </init-param> </init-params> </class-scheme> </cachestore-scheme>
我们现在可以将 coherence.hibernate.config 作为系统属性来使用,以设置 Hibernate 配置文件的位置,不管是本地运行还是构建容器镜像时。
接下来,创建一个Dockerfile用于构建Coherence镜像。
# 第一阶段,构建应用程序 FROM container-registry.oracle.com/java/jdk-no-fee-term:21 as build # 安装 Maven WORKDIR /usr/share RUN set -x && \ curl -O https://archive.apache.org/dist/maven/maven-3/3.8.4/binaries/apache-maven-3.8.4-bin.tar.gz && \ tar -xvf apache-maven-*-bin.tar.gz && \ rm apache-maven-*-bin.tar.gz && \ mv apache-maven-* maven && \ ln -s /usr/share/maven/bin/mvn /bin/ WORKDIR /helidon # 创建一个缓存本地仓库中'Maven World'的初始层。 # 增量 Docker 构建在 pom.xml 更新之前会从这里开始。 ADD coherence/pom.xml . RUN mvn package -Dmaven.test.skip # 进行 Maven 构建! # 增量 Docker 构建在你修改源代码时会从这里继续。 ADD coherence coherence RUN mvn -f coherence/pom.xml clean package -DskipTests RUN echo "done!" # 第二阶段,构建运行时镜像 FROM container-registry.oracle.com/java/jdk-no-fee-term:21 WORKDIR /helidon # 复制第一阶段构建的二进制文件 COPY --from=build /helidon/coherence/target/coherence.jar ./ COPY --from=build /helidon/coherence/target/libs ./libs HEALTHCHECK --start-period=10s --interval=30s \ CMD ["java", \ "-cp", "/helidon/coherence.jar", \ "com.tangosol.util.HealthCheckClient", \ "http://127.0.0.1:6676/ready", \ "||", "exit", "1"] # 设置环境变量 # 默认使用 POF ENV COHERENCE_POF_ENABLED=true ENV COHERENCE_SERIALIZER=pof # 设置健康检查端口为固定值(与上面的命令相对应) ENV COHERENCE_HEALTH_HTTP_PORT=6676 # 启用 Coherence 指标 ENV COHERENCE_METRICS_HTTP_ENABLED=true # 将日志级别设置为调试 ENV COHERENCE_LOG_LEVEL=9 CMD ["java", "-Dcoherence.grpc.server.port=1408", "-Dcoherence.hibernate.config=/hibernate/hibernate.cfg.xml", "-jar", "coherence.jar"] EXPOSE 1408 EXPOSE 9612
我们现在可以动手构建和测试容器镜像了。
使用 `docker buildx build` 命令构建镜像,参数 `--no-cache` 表示不使用缓存,`--platform=linux/amd64` 表示目标平台为 Linux AMD64,`-t coherence` 指定镜像名称为 `coherence`,`-f docker/Dockerfile.coherence` 指定 Dockerfile 的路径。
我们现在就用刚才构建的容器来运行Coherence。
# 导出 HIBERNATE_CFG_XML 和 WALLET 环境变量 export HIBERNATE_CFG_XML=/path/to/hibernate.cfg.xml export WALLET=/path/to/extracted/wallet # 使用 Docker 运行容器,挂载所需文件路径并启动容器 docker run --rm -it -v $HIBERNATE_CFG_XML:/hibernate/hibernate.cfg.xml -v $WALLET:/wallets/task_db coherence
我们现在可以看到Coherence开始启动了。
构建后端容器镜像我们现在来构建后端容器镜像。回想一下,后端模块依赖于Coherence模块这一点。创建后端容器镜像的Dockerfile文件。
# 第一阶段,构建应用 FROM container-registry.oracle.com/java/jdk-no-fee-term:21 as build # 安装 Maven 模块构建工具 WORKDIR /usr/share RUN set -x && \ curl -O https://archive.apache.org/dist/maven/maven-3/3.8.4/binaries/apache-maven-3.8.4-bin.tar.gz && \ tar -xvf apache-maven-*-bin.tar.gz && \ rm apache-maven-*-bin.tar.gz && \ mv apache-maven-* maven && \ ln -s /usr/share/maven/bin/mvn /bin/ WORKDIR /helidon ADD coherence coherence RUN mvn -f coherence/pom.xml install -DskipTests ADD backend backend RUN mvn -f backend/pom.xml clean package -DskipTests RUN echo "完成!" # 第二阶段,构建运行时镜像环境 FROM container-registry.oracle.com/java/jdk-no-fee-term:21 WORKDIR /helidon # 从第一阶段复制编译后的二进制文件 COPY --from=build /helidon/backend/target/backend.jar ./ COPY --from=build /helidon/backend/target/libs ./libs 设置环境变量 COHERENCE_CLUSTER=todo CMD ["java", "-Dcoherence.pof.enabled=true", "-Dcoherence.hibernate.config=/hibernate/hibernate.cfg.xml", "-jar", "backend.jar"] EXPOSE 8080
我们现在可以按照同样的方法来构建和测试这个图像了。
使用 Docker 构建一个名为 coherence 的镜像: docker build -t coherence . 运行并挂载指定目录的 Docker 容器: docker run --rm -it -v $HIBERNATE_CFG_XML:/hibernate/hibernate.cfg.xml -v $WALLET:/wallets/task_db backend
请注意,我们使用了Hibernate配置文件和数据库凭证作为参数。这是因为我们希望在启动时将现有数据预载入缓存。
预加载数据(通过Coherence CacheLoader)处理数据库的一致性涉及两个概念,
- 一个 CacheStore,如我们上面提到的 HibernateCacheStore,它把数据写入数据库。
- 一个 CacheLoader 使 Coherence 集群能够从数据库加载现有数据到缓存。
import java.io.File; import java.util.Collection; 导入 com.oracle.coherence.hibernate.cachestore.HibernateCacheLoader; 导入 org.hibernate.Session; 导入 org.hibernate.query.Query;
public class CachePreloader extends HibernateCacheLoader { // 初始化缓存预加载器 public CachePreloader(String entity) { super(entity, new File(System.getProperty("coherence.hibernate.config"))); } public Collection<String> getAllKeys() { ensureInitialized(); // 确保初始化 Session session = openSession(); // 打开会话 try { Query<String> query = session.createQuery("SELECT e.id FROM " + getEntityName() + " e", String.class); // 创建查询 return query.list(); // 返回列表 } finally { closeSession(session); // 关闭会话 } } }
并且添加一个方便的 REST API 以便调用它
@GET @Path("/preload") @Produces(APPLICATION_JSON) public Response preload() { Collection<String> keys = new CachePreloader("todo.Task").getAllKeys(); String message = "预加载数据,找到键共=" + keys.size() + "."; LOG.log(INFO, message); svc.preloadTasks(keys);
返回 Response.ok(message + "\n").build();
你现在可以通过调用这个预加载方法来提前加载数据:
```preload()
运行此命令来预加载后端数据
curl http://localhost:8080/api/backend/preload
如果你的数据库里已经有数据,如下所示: 正在预加载数据,找到的键值为11。 ## 构建容器镜像文件 — 前端容器镜像 在开发的不同阶段,我们处于不同的时间点。有些开发者希望能够在本地进行开发和测试。最终我们希望能够测试整个系统。但在那之前,我们如何才能不用频繁修改代码和配置来进行测试呢?Helidon 提供了[配置文件](https://helidon.io/docs/v4/se/config/config-profiles),让你可以预设每个环境的配置。例如,在本地开发时,我们最初可能只想使用 jar 包和容器。创建一个名为 application-local 的文件,并设置如下配置:
services: # 后端服务的端点地址 backend.endpoint: "http://localhost:8080"
我们也可以为本地容器环境创建一个类似的。
services: backend.endpoint: "http://host.docker.internal:8080"
对于 Kubernetes 来说:
服务:
后端端点: "http://backend:8080"
我们现在可以挑选要运行的配置。比如说我们要用本地配置。
运行带有特定配置的Java命令
java -Dconfig.profile=local -Xmx512m -Xms512m -jar target/frontend.jar
如果我们想本地运行容器呢?别担心,我们已经搞定了。
docker run --rm -it -v -e CONFIG_PROFILE='docker' $HIBERNATE_CFG_XML:/hibernate/hibernate.cfg.xml -v $WALLET:/wallets/task_db frontend
这里使用了 `docker` 命令来运行一个容器。命令中的 `-rm` 参数表示容器在停止后会被自动删除,`-it` 参数则为容器提供了交互式的终端。`-v` 参数用来挂载宿主机的文件或目录到容器内部,而 `-e` 参数设置环境变量 `CONFIG_PROFILE` 的值为 `'docker'`。最后,`$HIBERNATE_CFG_XML` 和 `$WALLET` 分别指向了宿主机上的文件路径,这些路径会被映射到容器内的指定路径中。`frontend` 则指定了要运行的镜像名称。 在我们准备在 Kubernetes 集群中运行时,只需将配置设置成环境变量,比如: 比如可以设置为环境变量。
kind: Deployment apiVersion: apps/v1 metadata: name: 前端 namespace: todo spec: 副本数: 1 选择器: 匹配标签: app: 前端 模板: metadata: 标签: app: 前端 version: v1 spec: 容器: - 名称: 前端 image: ocir.<region>.oci.oraclecloud.com/<tenancy_namespace>/todo/frontend:v3 环境变量: - 名称: "CONFIG_PROFILE" 值: "k8s" 拉取策略: Always 端口: - 容器端口: 7001 镜像拉取密钥: - 名称: ocir-secret
一旦配置好基本设置,只需根据不同的环境调整这些设置的位置即可。 ## 概述 在这篇文章中,我们简要但必要地讨论了如何在 Kubernetes 集群中构建容器镜像。我们探讨了如何安全地在各个开发阶段中包含 Hibernate 配置,以及如何根据 Helidon 的配置文件来调整配置。 希望你喜欢这篇文章,敬请期待下一期。 我想感谢我的同事 Tim Middleton、Sherwood Zern 和(罗曼·格雷库尔)Romain Grecourt,他们帮助了这篇文章的完成。
这篇关于使用Oracle数据库、Helidon和Coherence构建Kubernetes容器,轻松又实用 — 第6部分:构建容器,享受部署的乐趣的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2025-01-07Kubernetes部署策略详解:滚动更新、固定更新、蓝绿部署和金丝雀发布
- 2025-01-03Django微服务与Docker和Kubernetes部署(系列第五篇:实战篇)
- 2025-01-02云原生Digest:Kubernetes v1.31版本中的移除功能和重大变更
- 2024-12-31Kubernetes工作节点的自动加入方法
- 2024-12-31Docker和Kubernetes面试速成指南 ??
- 2024-12-30玩乐案例:用开源技术从Hadoop迁移到Kubernetes的PB级数据平台之旅
- 2024-12-30在Kubernetes中用NVIDIA GPU运行自己的OLLMAMA服务
- 2024-12-30平台工程实战:用Score和Humanitec部署线上精品店示例应用
- 2024-12-26使用Goldilocks优化Kubernetes资源请求和限制配置指南
- 2024-12-26Canonical Kubernetes 1.32稳定版发布:无缝集群创建与管理