java.lang.ClassNotFoundException:无法加载 class:com.microsoft.sqlserver.jdbc.SQLServerDriver 在新的 docker 容器上
java.lang.ClassNotFoundException: Unable to load class: com.microsoft.sqlserver.jdbc.SQLServerDriver on new docker container
我正在尝试使用 Sql 服务器 JDBC 驱动程序创建 docker 图像。
但是我收到这个错误:
Caused by: java.lang.ClassNotFoundException: Unable to load class: com.microsoft.sqlserver.jdbc.SQLServerDriver from ClassLoader:java.net.URLClassLoader@71423665;ClassLoader:java.net.URLClassLoader@71423665
at org.apache.tomcat.jdbc.pool.ClassLoaderUtil.loadClass(ClassLoaderUtil.java:56)
at org.apache.tomcat.jdbc.pool.PooledConnection.connectUsingDriver(PooledConnection.java:281)
... 41 more
Caused by: java.lang.ClassNotFoundException: com.microsoft.sqlserver.jdbc.SQLServerDriver
at java.base/java.net.URLClassLoader.findClass(URLClassLoader.java:471)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:588)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:521)
at java.base/java.lang.Class.forName0(Native Method)
at java.base/java.lang.Class.forName(Class.java:398)
at org.apache.tomcat.jdbc.pool.ClassLoaderUtil.loadClass(ClassLoaderUtil.java:38)
... 42 more
我的Docker文件是这样的:
FROM alpine:3.10 as builder
ARG VERSION=7.12.0
ARG DISTRO=tomcat
ARG SNAPSHOT=true
ARG EE=false
ARG USER
ARG PASSWORD
RUN apk add --no-cache \
ca-certificates \
maven \
tar \
wget \
xmlstarlet
COPY settings.xml download.sh camunda-tomcat.sh camunda-wildfly.sh /tmp/
RUN /tmp/download.sh
##### FINAL IMAGE #####
FROM alpine:3.10
ARG VERSION=7.12.0
#MSSQL SERVER JDBC DRIVER INSTALL
COPY sqljdbc_7.4.1.0_enu.tar.gz /tmp/
WORKDIR /tmp
RUN tar -xf sqljdbc_7.4.1.0_enu.tar.gz
RUN export CLASSPATH="$CLASSPATH:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar"
ENV CAMUNDA_VERSION=${VERSION}
ENV DB_DRIVER=com.microsoft.sqlserver.jdbc.SQLServerDriver
ENV DB_URL=jdbc:sqlserver://xx.database.windows.net:1433;database=camundadb;user=demo@xx;password=xxx.;encrypt=true;trustServerCertificate=false;hostNameInCertificate=*.database.windows.net;loginTimeout=30;
ENV DB_USERNAME=
ENV DB_PASSWORD=
ENV DB_CONN_MAXACTIVE=20
ENV DB_CONN_MINIDLE=5
ENV DB_CONN_MAXIDLE=20
ENV DB_VALIDATE_ON_BORROW=false
ENV DB_VALIDATION_QUERY="SELECT 1"
ENV SKIP_DB_CONFIG=
ENV WAIT_FOR=
ENV WAIT_FOR_TIMEOUT=120
ENV TZ=UTC
ENV DEBUG=TRUE
ENV JAVA_OPTS="-Xmx768m -XX:MaxMetaspaceSize=256m"
EXPOSE 8080 8000
# Downgrading wait-for-it is necessary until this PR is merged
# https://github.com/vishnubob/wait-for-it/pull/68
RUN apk add --no-cache \
bash \
ca-certificates \
openjdk11-jre-headless \
tzdata \
tini \
xmlstarlet \
&& wget -O /usr/local/bin/wait-for-it.sh \
"https://raw.githubusercontent.com/vishnubob/wait-for-it/a454892f3c2ebbc22bd15e446415b8fcb7c1cfa4/wait-for-it.sh" \
&& chmod +x /usr/local/bin/wait-for-it.sh
RUN addgroup -g 1000 -S camunda && \
adduser -u 1000 -S camunda -G camunda -h /camunda -s /bin/bash -D camunda
WORKDIR /camunda
USER camunda
ENTRYPOINT ["/sbin/tini", "--"]
CMD ["./camunda.sh"]
COPY --chown=camunda:camunda --from=builder /camunda .
更新 1:
我删除了导出行并添加了:
环境类路径 ${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
ARG CLASSPATH=${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
根据其他SO问题,我也试了jre11和jre12版本的驱动,还是一样的错误,无法加载class。
更新二:
根据此处的 Camunda 文档:https://github.com/camunda/docker-camunda-bpm-platform
Java 版本
我们的 docker 图像使用的是 Camunda BPM 支持的最新 LTS OpenJDK 版本。这目前意味着:
Camunda 7.12 将基于 OpenJDK 11
所有之前的版本都基于 OpenJDK 8
根据此处的 Microsoft 文档:
https://docs.microsoft.com/en-us/sql/connect/jdbc/system-requirements-for-the-jdbc-driver?view=sql-server-2017
Microsoft JDBC SQL 服务器的驱动程序 7.4:
JDBCDriver 7.4在每个安装包中包含三个JARclass库:mssql-jdbc-7.4.1.jre8.jar、mssql-jdbc-7.4.1.jre11.jar 和 mssql-jdbc-7.4.1.jre12.jar.
JDBC 驱动程序 7.4 旨在与所有主要 Java 虚拟机一起工作并受其支持,但仅在 OpenJDK 1.8、OpenJDK 11.0、OpenJDK 12.0、Azul Zulu JRE 1.8 上进行了测试、Azul Zulu JRE 11.0 和 Azul Zulu JRE 12.0。
OpenJDK 支持版本 7.4
RUN export CLASSPATH="$CLASSPATH:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar"
将对您的 dockerfile
无效:
相反,您需要对运行时使用 ENV
,对构建使用 ARG
:
ENV CLASSPATH ${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
ARG CLASSPATH=${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
我正在尝试使用 Sql 服务器 JDBC 驱动程序创建 docker 图像。
但是我收到这个错误:
Caused by: java.lang.ClassNotFoundException: Unable to load class: com.microsoft.sqlserver.jdbc.SQLServerDriver from ClassLoader:java.net.URLClassLoader@71423665;ClassLoader:java.net.URLClassLoader@71423665
at org.apache.tomcat.jdbc.pool.ClassLoaderUtil.loadClass(ClassLoaderUtil.java:56)
at org.apache.tomcat.jdbc.pool.PooledConnection.connectUsingDriver(PooledConnection.java:281)
... 41 more
Caused by: java.lang.ClassNotFoundException: com.microsoft.sqlserver.jdbc.SQLServerDriver
at java.base/java.net.URLClassLoader.findClass(URLClassLoader.java:471)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:588)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:521)
at java.base/java.lang.Class.forName0(Native Method)
at java.base/java.lang.Class.forName(Class.java:398)
at org.apache.tomcat.jdbc.pool.ClassLoaderUtil.loadClass(ClassLoaderUtil.java:38)
... 42 more
我的Docker文件是这样的:
FROM alpine:3.10 as builder
ARG VERSION=7.12.0
ARG DISTRO=tomcat
ARG SNAPSHOT=true
ARG EE=false
ARG USER
ARG PASSWORD
RUN apk add --no-cache \
ca-certificates \
maven \
tar \
wget \
xmlstarlet
COPY settings.xml download.sh camunda-tomcat.sh camunda-wildfly.sh /tmp/
RUN /tmp/download.sh
##### FINAL IMAGE #####
FROM alpine:3.10
ARG VERSION=7.12.0
#MSSQL SERVER JDBC DRIVER INSTALL
COPY sqljdbc_7.4.1.0_enu.tar.gz /tmp/
WORKDIR /tmp
RUN tar -xf sqljdbc_7.4.1.0_enu.tar.gz
RUN export CLASSPATH="$CLASSPATH:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar"
ENV CAMUNDA_VERSION=${VERSION}
ENV DB_DRIVER=com.microsoft.sqlserver.jdbc.SQLServerDriver
ENV DB_URL=jdbc:sqlserver://xx.database.windows.net:1433;database=camundadb;user=demo@xx;password=xxx.;encrypt=true;trustServerCertificate=false;hostNameInCertificate=*.database.windows.net;loginTimeout=30;
ENV DB_USERNAME=
ENV DB_PASSWORD=
ENV DB_CONN_MAXACTIVE=20
ENV DB_CONN_MINIDLE=5
ENV DB_CONN_MAXIDLE=20
ENV DB_VALIDATE_ON_BORROW=false
ENV DB_VALIDATION_QUERY="SELECT 1"
ENV SKIP_DB_CONFIG=
ENV WAIT_FOR=
ENV WAIT_FOR_TIMEOUT=120
ENV TZ=UTC
ENV DEBUG=TRUE
ENV JAVA_OPTS="-Xmx768m -XX:MaxMetaspaceSize=256m"
EXPOSE 8080 8000
# Downgrading wait-for-it is necessary until this PR is merged
# https://github.com/vishnubob/wait-for-it/pull/68
RUN apk add --no-cache \
bash \
ca-certificates \
openjdk11-jre-headless \
tzdata \
tini \
xmlstarlet \
&& wget -O /usr/local/bin/wait-for-it.sh \
"https://raw.githubusercontent.com/vishnubob/wait-for-it/a454892f3c2ebbc22bd15e446415b8fcb7c1cfa4/wait-for-it.sh" \
&& chmod +x /usr/local/bin/wait-for-it.sh
RUN addgroup -g 1000 -S camunda && \
adduser -u 1000 -S camunda -G camunda -h /camunda -s /bin/bash -D camunda
WORKDIR /camunda
USER camunda
ENTRYPOINT ["/sbin/tini", "--"]
CMD ["./camunda.sh"]
COPY --chown=camunda:camunda --from=builder /camunda .
更新 1:
我删除了导出行并添加了:
环境类路径 ${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar ARG CLASSPATH=${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
根据其他SO问题,我也试了jre11和jre12版本的驱动,还是一样的错误,无法加载class。
更新二:
根据此处的 Camunda 文档:https://github.com/camunda/docker-camunda-bpm-platform
Java 版本 我们的 docker 图像使用的是 Camunda BPM 支持的最新 LTS OpenJDK 版本。这目前意味着:
Camunda 7.12 将基于 OpenJDK 11 所有之前的版本都基于 OpenJDK 8
根据此处的 Microsoft 文档: https://docs.microsoft.com/en-us/sql/connect/jdbc/system-requirements-for-the-jdbc-driver?view=sql-server-2017
Microsoft JDBC SQL 服务器的驱动程序 7.4:
JDBCDriver 7.4在每个安装包中包含三个JARclass库:mssql-jdbc-7.4.1.jre8.jar、mssql-jdbc-7.4.1.jre11.jar 和 mssql-jdbc-7.4.1.jre12.jar.
JDBC 驱动程序 7.4 旨在与所有主要 Java 虚拟机一起工作并受其支持,但仅在 OpenJDK 1.8、OpenJDK 11.0、OpenJDK 12.0、Azul Zulu JRE 1.8 上进行了测试、Azul Zulu JRE 11.0 和 Azul Zulu JRE 12.0。
OpenJDK 支持版本 7.4
RUN export CLASSPATH="$CLASSPATH:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar"
将对您的 dockerfile
无效:
相反,您需要对运行时使用 ENV
,对构建使用 ARG
:
ENV CLASSPATH ${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar
ARG CLASSPATH=${CLASSPATH}:/tmp/sqljdbc_7.4/enu/mssql-jdbc-7.4.1.jre8.jar