目前,一个 Java 应用程序环境已在 Java21 环境下的[email protected]上运行。该应用程序已经过广泛测试,在测试堆栈中运行稳定。现在,它将被部署到 Openshift 集群中。
构建了由 wildfly-33.0.2.Final-jdk21.tar 组成的几个容器。
sh-5.1$ cat /etc/system-release
Red Hat Enterprise Linux release 9.5 (Plow)
sh-5.1$ java --version
openjdk 21.0.4 2024-07-16 LTS
OpenJDK Runtime Environment Temurin-21.0.4+7 (build 21.0.4+7-LTS)
OpenJDK 64-Bit Server VM Temurin-21.0.4+7 (build 21.0.4+7-LTS, mixed mode, sharing)
sh-5.1$ /opt/jboss/wildfly/bin/jboss-cli.sh --connect --controller=localhost:9990 --command="version”
JBoss Admin Command-line Interface
JBOSS_HOME: /opt/jboss/wildfly
Release: 25.0.2.Final
Product: WildFly 33.0.2.Final
JAVA_HOME: /opt/java/openjdk
java.version: 21.0.4
java.vm.vendor: Eclipse Adoptium
java.vm.version: 21.0.4+7-LTS
os.name: Linux
os.version: 5.14.0-427.49.1.el9_4.x86_64
应用程序在 Docker 构建期间被复制到容器中
FROM dxc.com/basys3-base:v1 AS builder
USER jboss
ENV JBOSS_ROOT=/opt/jboss
ENV JBOSS_HOME=/opt/jboss/wildfly
ENV DEPLOY_DIR=$JBOSS_HOME/standalone/deployments/
COPY benutzungsdienst.war $DEPLOY_DIR/benutzungsdienst.war
RUN touch $DEPLOY_DIR/benutzungsdienst.war.dodeploy
WORKDIR $JBOSS_HOME
EXPOSE 8080 9990
CMD [“/opt/jboss/wildfly/bin/standalone.sh”, “-b”, “0.0.0.0”, “-bmanagement”, “0.0.0.0”]
然后在 openshift 集群中
oc version
Client version: 4.17.10
Kustomize version: v5.0.4-0.20230601165947-6ce0bf390ce3
Kubernetes version: v1.30.7
有了这样的部署,YAML 就部署了
apiVersion: apps/v1
kind: Deployment
metadata:
name: xxx-deployment
spec:
replicas: 1
selector:
matchLabels:
app: basys3film
template:
metadata:
labels:
app: basys3film
spec:
containers:
- name: basys3film-container
image: xxx.xxx.xxx.xxx:5000/xxx:v1
imagePullPolicy: Always
ports:
- containerPort: 8080
- containerPort: 9990
securityContext:
runAsUser: 1000650000
allowPrivilegeEscalation: false
runAsNonRoot: true
capabilities:
drop: [“ALL”]
seccompProfile:
type: RuntimeDefault
env:
- name: TZ
value: “Europe/Berlin”
- name: WILDFLY_LOG_FILE_NAME
value: “server.film.log”
volumeMounts:
- name: wildfly-dat
mountPath: /opt/jboss/wildfly/standalone/data
- name: wildfly-tmp
mountPath: /opt/jboss/wildfly/standalone/tmp
- name: wildfly-log
mountPath: /opt/jboss/wildfly/standalone/log
volumes:
- name: wildfly-dat
persistentVolumeClaim:
claimName: pvc-dat
- name: wildfly-log
persistentVolumeClaim:
claimName: pvc-log
- name: wildfly-tmp
persistentVolumeClaim:
claimName: pvc-tmp
三个持久卷声明安装在容器中,如下所示
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: pvc-tmp
spec:
storageClassName: crc-csi-hostpath-provisioner
accessModes:
- ReadWriteMany
resources:
requests:
storage: “1Gi”
Wildflys 启动正常,应用程序部署也没有任何错误。问题在于,在测试用例中,错误可能偶尔发生,然后更频繁地发生:
Caused by: java.lang.ClassNotFoundException: com.xxx.yyy.benutzung.dao.datatable.DateUtils from [Module “deployment.benutzungsdienst.war” from Service Module Loader]
Caused by: java.lang.ClassNotFoundException: com.xxx.yyyy.benutzung.utils.Utils from [Module “deployment.benutzungsdienst.war” from Service Module Loader]
Caused by: java.lang.ClassNotFoundException: com.xxx.yyyy.zzz.controller.mag.mag0102.MAG010202Bean from [Module \“deployment.film.war\” from Service Module Loader]"}}
Caused by: org.jboss.as.server.deployment.DeploymentUnitProcessingException: java.lang.ClassNotFoundException: com.xxx.yyyy.zzz.controller.mag.mag0102.MAG010202Bean from [Module \“deployment.basys3film.war\” from Service Module Loader]
如果 Wildfly 找不到这样的 Java 类,它仍然存在于文件系统中,可以使用 find -name 进行追踪。
我觉得这个错误图像似乎只有在我创建了 PVC 挂载点后才会出现。如果我移除挂载点并再次部署,就无法重现这个错误模式了。
我了解到使用符号链接时可能会出现此类错误,并且也尝试过 Java 开关 -Djboss.vfs.forceCanonical=true,但这也无济于事。
您对如何防止此类行为有什么想法吗?
非常感谢,并致以亲切的问候,Juergen
该问题可能是由于将 WildFly 内容存储库 (
$JBOSS_HOME/standalone/data
) 存储在持久卷中引起的。正如WildFly 文档中所述,当在 WildFly 中部署时(您在执行
Dockerfile
时COPY benutzungsdienst.war
),实际的二进制文件(及其类)存储在内容存储库中。我不知道您的测试在做什么,但最终可能会得到来自持久卷中的内容存储库的二进制文件,这些二进制文件不再与部署的类匹配(因为 PV 优先于容器文件系统)。
尝试移除 PV 以
wildfly-dat
避免这些随机错误。日志和 tmp 目录的其他 PV 则没有问题。