Docker Compose配置Zipkin连接MySQL时认证插件异常求助
我正在通过Docker Compose配置Zipkin服务,现有MySQL实例可与其他服务正常连接,但启用调试模式连接Zipkin时,出现如下错误:
DEBUG [/] 1 --- [ng-tasks-1-1019] z.s.i.h.ComponentHealth : ServiceConfigurationError: org.mariadb.jdbc.plugin.AuthenticationPlugin: Provider org.mariadb.jdbc.plugin.authentication.addon.SendGssApiAuthPacket could not be instantiated
向Zipkin发送数据时会抛出完整栈跟踪错误:
java.util.ServiceConfigurationError: org.mariadb.jdbc.plugin.AuthenticationPlugin: Provider org.mariadb.jdbc.plugin.authentication.addon.SendGssApiAuthPacket could not be instantiated
at java.base/java.util.ServiceLoader.fail(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$ProviderImpl.newInstance(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$ProviderImpl.get(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$3.next(Unknown Source) ~[?:?]
at org.mariadb.jdbc.plugin.authentication.AuthenticationPluginLoader.get(AuthenticationPluginLoader.java:32) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.client.impl.StandardClient.authenticationHandler(StandardClient.java:282) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.client.impl.StandardClient.(StandardClient.java:226) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:68) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:92) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:26) ~[mariadb-java-client-3.4.1.jar:?]
at com.zaxxer.hikari.util.DriverDataSource.getConnection(DriverDataSource.java:137) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.PoolBase.newConnection(PoolBase.java:360) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.PoolBase.newPoolEntry(PoolBase.java:202) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.createPoolEntry(HikariPool.java:461) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.checkFailFast(HikariPool.java:550) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.(HikariPool.java:98) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:111) ~[HikariCP-5.1.0.jar:?]
at zipkin2.storage.mysql.v1.HasTraceIdHigh.test(HasTraceIdHigh.java:33) ~[zipkin-storage-mysql-v1-3.4.3.jar:?]
at zipkin2.storage.mysql.v1.Schema.(Schema.java:41) ~[zipkin-storage-mysql-v1-3.4.3.jar:?]
at zipkin2.storage.mysql.v1.MySQLStorage.schema(MySQLStorage.java:122) ~[zipkin-storage-mysql-v1-3.4.3.jar:?]
at zipkin2.storage.mysql.v1.MySQLStorage.spanConsumer(MySQLStorage.java:146) ~[zipkin-storage-mysql-v1-3.4.3.jar:?]
at zipkin2.collector.Collector.store(Collector.java:190) ~[zipkin-collector-3.4.3.jar:?]
at zipkin2.collector.Collector$StoreSpans.run(Collector.java:219) ~[zipkin-collector-3.4.3.jar:?]
at com.linecorp.armeria.common.DefaultContextAwareRunnable.run(DefaultContextAwareRunnable.java:45) ~[armeria-1.31.0.jar:?]
at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Unknown Source) ~[?:?]
at java.base/java.util.concurrent.FutureTask.run(Unknown Source) ~[?:?]
at java.base/java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(Unknown Source) ~[?:?]
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source) ~[?:?]
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source) ~[?:?]
at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30) ~[netty-common-4.1.115.Final.jar:4.1.115.Final]
at java.base/java.lang.Thread.run(Unknown Source) [?:?]
Caused by: java.lang.NoClassDefFoundError: Could not initialize class org.mariadb.jdbc.plugin.authentication.addon.SendGssApiAuthPacket
at java.base/jdk.internal.misc.Unsafe.ensureClassInitialized0(Native Method) ~[?:?]
at java.base/jdk.internal.misc.Unsafe.ensureClassInitialized(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.MethodHandleAccessorFactory.ensureClassInitialized(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.MethodHandleAccessorFactory.newConstructorAccessor(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.ReflectionFactory.newConstructorAccessor(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.acquireConstructorAccessor(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.newInstance(Unknown Source) ~[?:?]
... 30 more
Caused by: java.lang.ExceptionInInitializerError: Exception java.lang.NoClassDefFoundError: org/ietf/jgss/GSSException [in thread "armeria-common-blocking-tasks-1-1"]
at org.mariadb.jdbc.plugin.authentication.addon.SendGssApiAuthPacket.(SendGssApiAuthPacket.java:30) ~[mariadb-java-client-3.4.1.jar:?]
at java.base/jdk.internal.misc.Unsafe.ensureClassInitialized0(Native Method) ~[?:?]
at java.base/jdk.internal.misc.Unsafe.ensureClassInitialized(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.MethodHandleAccessorFactory.ensureClassInitialized(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.MethodHandleAccessorFactory.newConstructorAccessor(Unknown Source) ~[?:?]
at java.base/jdk.internal.reflect.ReflectionFactory.newConstructorAccessor(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.acquireConstructorAccessor(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Unknown Source) ~[?:?]
at java.base/java.lang.reflect.Constructor.newInstance(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$ProviderImpl.newInstance(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$ProviderImpl.get(Unknown Source) ~[?:?]
at java.base/java.util.ServiceLoader$3.next(Unknown Source) ~[?:?]
at org.mariadb.jdbc.plugin.authentication.AuthenticationPluginLoader.get(AuthenticationPluginLoader.java:32) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.client.impl.StandardClient.authenticationHandler(StandardClient.java:282) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.client.impl.StandardClient.(StandardClient.java:226) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:68) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:92) ~[mariadb-java-client-3.4.1.jar:?]
at org.mariadb.jdbc.Driver.connect(Driver.java:26) ~[mariadb-java-client-3.4.1.jar:?]
at com.zaxxer.hikari.util.DriverDataSource.getConnection(DriverDataSource.java:137) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.PoolBase.newConnection(PoolBase.java:360) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.PoolBase.newPoolEntry(PoolBase.java:202) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.createPoolEntry(HikariPool.java:461) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.checkFailFast(HikariPool.java:550) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.pool.HikariPool.(HikariPool.java:98) ~[HikariCP-5.1.0.jar:?]
at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:111) ~[HikariCP-5.1.0.jar:?]
at zipkin2.storage.mysql.v1.MySQLStorage.check(MySQLStorage.java:150) ~[zipkin-storage-mysql-v1-3.4.3.jar:?]
at zipkin2.server.internal.health.ComponentHealth.ofComponent(ComponentHealth.java:22) ~[classes/:?]
at zipkin2.server.internal.health.ZipkinHealthController.lambda$health$1(ZipkinHealthController.java:62) ~[classes/:?]
at java.base/java.util.concurrent.CompletableFuture$AsyncSupply.run(Unknown Source) ~[?:?]
... 8 more
我已尝试以下方案但均无效:
- 切换到Cassandra存储
- 切换到Postgres存储
- 更换数据库与Zipkin版本
- 咨询Copilot、GPT及Claude
目前仅内存模式下Zipkin可正常运行,请问问题出在哪里?
我的YAML配置片段如下:
networks: env_prod: driver: bridge #activate ipv6 driver_opts: com.docker.network.enable_ipv6: "true" #IP Adress Manager ipam: driver: default config: - subnet: 172.16.232.0/24 gateway: 172.16.232.1 - subnet: "2001:3974:3979::/64" gateway: "2001:3974:3979::1" services: mysql: container_name: mysql image: mysql:8 restart: always networks: - env_prod expose: - 3306 zipkin: container_name: zipkin image: openzipkin/zipkin:latest restart: always networks: - env_prod ports: - 9411:9411 environment: - JAVA_OPTS=-Dlogging.level.zipkin2=DEBUG -Dlogging.level.org.springframework=DEBUG - STORAGE_TYPE=mysql - MYSQL_HOST=mysql - MYSQL_DB=zipkin - MYSQL_USER=zipkin - MYSQL_PASS=zipkinpass - MYSQL_USE_SSL=false
问题分析与解决方案
问题根源
从栈跟踪信息可以定位到核心错误:java.lang.NoClassDefFoundError: org/ietf/jgss/GSSException。这是因为Zipkin默认使用的Mariadb JDBC客户端会自动扫描所有可用的认证插件,其中GSSAPI认证插件依赖JDK的GSS模块,但官方Zipkin镜像使用的精简版JRE缺少该模块,导致插件初始化失败,进而阻断数据库连接流程。
解决方案
方案1:强制使用MySQL官方JDBC驱动
Zipkin默认使用Mariadb驱动,可通过环境变量指定使用MySQL官方驱动,绕过Mariadb客户端的插件扫描逻辑:
在Zipkin的environment中添加以下配置:
- MYSQL_JDBC_URL=jdbc:mysql://mysql:3306/zipkin?useSSL=false&allowPublicKeyRetrieval=true - MYSQL_DRIVER_CLASS=com.mysql.cj.jdbc.Driver
修改后的Zipkin服务配置:
zipkin: container_name: zipkin image: openzipkin/zipkin:latest restart: always networks: - env_prod ports: - 9411:9411 environment: - JAVA_OPTS=-Dlogging.level.zipkin2=DEBUG -Dlogging.level.org.springframework=DEBUG - STORAGE_TYPE=mysql - MYSQL_HOST=mysql - MYSQL_DB=zipkin - MYSQL_USER=zipkin - MYSQL_PASS=zipkinpass - MYSQL_USE_SSL=false - MYSQL_JDBC_URL=jdbc:mysql://mysql:3306/zipkin?useSSL=false&allowPublicKeyRetrieval=true - MYSQL_DRIVER_CLASS=com.mysql.cj.jdbc.Driver
方案2:禁用Mariadb客户端的GSSAPI插件
通过JDBC URL参数指定仅加载常用的认证插件,跳过GSSAPI插件:
修改Zipkin的环境变量,添加自定义JDBC URL:
- MYSQL_JDBC_URL=jdbc:mariadb://mysql:3306/zipkin?useSSL=false&allowPublicKeyRetrieval=true&authenticationPlugins=mysql_native_password,caching_sha2_password
方案3:使用完整JDK环境
如果上述方案无效,可自定义Zipkin镜像,使用包含GSS模块的完整JDK:
创建Dockerfile:
FROM openzipkin/zipkin:latest RUN jlink --add-modules sun.security.jgss --output /opt/jdk-custom ENV JAVA_HOME=/opt/jdk-custom
然后构建镜像并替换docker-compose.yml中的openzipkin/zipkin:latest为自定义镜像。
内容的提问来源于stack exchange,提问作者Yape

