yelao

  因为换新的电脑设备,为其安装一些开发需要的应用及环境,下载了新版的Mysql8.0.13,在Eclipse中测试连接时遇到一些新的问题,遂记录。

 

1. Mysql 5.*  版本JDBC连接

  a. 常规导入 5.* jar 包

  

  b. 编写测试程序

package wqz.mysql.test;

import java.sql.DriverManager;

public class Test {
    private static String url = "jdbc:mysql://localhost:3306/你的库名";//数据库服务地址
    private static String driver = "com.mysql.jdbc.Driver";//驱动路径
    private static String username = "root";
    private static String passworld = "你的密码";
    
    public static void main(String[] args) throws Exception {
        Class.forName(driver).newInstance();

        //如果能连接成功,则打印连接
        System.out.println(DriverManager.getConnection(url, username, passworld));
        
    }
}

  c. 运行程序

  如果数据库是Mysql 5.* 版本 ,在没有出现输入错误的连接信息情况下,会成功输出数据库连接对象。


 

2. 测试 Mysql 8.* 的连接

使用和上述驱动和程序 连接 Mysql 8.*,没有输出连接对象,异常信息如下 :

Tue Oct 30 10:20:06 CST 2018 WARN: Establishing SSL connection without server\'s identity verification is not recommended. According to MySQL 5.5.45+, 5.6.26+ and 5.7.6+ requirements SSL connection must be established by default if explicit option isn\'t set. For compliance with existing applications not using SSL the verifyServerCertificate property is set to \'false\'. You need either to explicitly disable SSL by setting useSSL=false, or set useSSL=true and provide truststore for server certificate verification.
Exception in thread "main" com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Could not create connection to database server.
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.jdbc.Util.handleNewInstance(Util.java:404)
    at com.mysql.jdbc.Util.getInstance(Util.java:387)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:917)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:896)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:885)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:860)
    at com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2330)
    at com.mysql.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:2083)
    at com.mysql.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:806)
    at com.mysql.jdbc.JDBC4Connection.<init>(JDBC4Connection.java:47)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.jdbc.Util.handleNewInstance(Util.java:404)
    at com.mysql.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:410)
    at com.mysql.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:328)
    at java.sql.DriverManager.getConnection(DriverManager.java:664)
    at java.sql.DriverManager.getConnection(DriverManager.java:247)
    at wqz.mysql.test.Test.main(Test.java:14)
Caused by: java.lang.NullPointerException
    at com.mysql.jdbc.ConnectionImpl.getServerCharset(ConnectionImpl.java:2997)
    at com.mysql.jdbc.MysqlIO.sendConnectionAttributes(MysqlIO.java:1936)
    at com.mysql.jdbc.MysqlIO.proceedHandshakeWithPluggableAuthentication(MysqlIO.java:1865)
    at com.mysql.jdbc.MysqlIO.doHandshake(MysqlIO.java:1228)
    at com.mysql.jdbc.ConnectionImpl.coreConnect(ConnectionImpl.java:2253)
    at com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2284)
    ... 13 more

  1. 首先看第一个信息:...WARN: Establishing SSL connection without ...

  在较高版本的 Mysql 中,引入了 SSL 安全认证,需要拥有一定的安全证书去连接数据库,而我们没有证书,所以出现此警告。

  解决方式:在原数据库 url 后加上禁用 SSL 的信息

//private static String url = "jdbc:mysql://localhost:3306/你的库名";//数据库服务地址
private static String url = "jdbc:mysql://localhost:3306/你的库名?useSSL=false";//数据库服务地址

  运行程序:

Exception in thread "main" com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Could not create connection to database server.
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.jdbc.Util.handleNewInstance(Util.java:404)
    at com.mysql.jdbc.Util.getInstance(Util.java:387)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:917)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:896)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:885)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:860)
    at com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2330)
    at com.mysql.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:2083)
    at com.mysql.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:806)
    at com.mysql.jdbc.JDBC4Connection.<init>(JDBC4Connection.java:47)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.jdbc.Util.handleNewInstance(Util.java:404)
    at com.mysql.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:410)
    at com.mysql.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:328)
    at java.sql.DriverManager.getConnection(DriverManager.java:664)
    at java.sql.DriverManager.getConnection(DriverManager.java:247)
    at wqz.mysql.test.Test.main(Test.java:14)
Caused by: java.lang.NullPointerException
    at com.mysql.jdbc.ConnectionImpl.getServerCharset(ConnectionImpl.java:2997)
    at com.mysql.jdbc.MysqlIO.sendConnectionAttributes(MysqlIO.java:1936)
    at com.mysql.jdbc.MysqlIO.proceedHandshakeWithPluggableAuthentication(MysqlIO.java:1865)
    at com.mysql.jdbc.MysqlIO.doHandshake(MysqlIO.java:1228)
    at com.mysql.jdbc.ConnectionImpl.coreConnect(ConnectionImpl.java:2253)
    at com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2284)
    ... 13 more

  可见,上述警告已经不再出现,但仍无法连接成功。

  2. 解决驱动问题 

  在安装Mysql过程中会提示安装Connector/j,其中包含适应Mysql版本的JDBC连接驱动

  将其导入到项目中(如果没有此驱动,可去mysql官网下载),并删除之前的驱动:

  对比之前的驱动,由5.*  变成了  8.*,此时的程序没有变化:

package wqz.mysql.test;

import java.sql.DriverManager;

public class Test {
    private static String url = "jdbc:mysql://localhost:3306/你的库?useSSL=false";
    private static String driver = "com.mysql.jdbc.Driver";
    private static String username = "root";
    private static String passworld = "你的密码";
    
    public static void main(String[] args) throws Exception {
        Class.forName(driver).newInstance();
        //如果能连接成功,则打印连接
        System.out.println(DriverManager.getConnection(url, username, passworld));
        
    }
}

  运行程序:

Loading class `com.mysql.jdbc.Driver\'. This is deprecated. The new driver class is `com.mysql.cj.jdbc.Driver\'. The driver is automatically registered via the SPI and manual loading of the driver class is generally unnecessary.
Exception in thread "main" java.sql.SQLException: The server time zone value \'???ú±ê×??±??\' is unrecognized or represents more than one time zone. You must configure either the server or JDBC driver (via the serverTimezone configuration property) to use a more specifc time zone value if you want to utilize time zone support.
    at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:129)
    at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:97)
    at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:89)
    at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:63)
    at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:73)
    at com.mysql.cj.jdbc.exceptions.SQLExceptionsMapping.translateException(SQLExceptionsMapping.java:76)
    at com.mysql.cj.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:835)
    at com.mysql.cj.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:455)
    at com.mysql.cj.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:240)
    at com.mysql.cj.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:207)
    at java.sql.DriverManager.getConnection(DriverManager.java:664)
    at java.sql.DriverManager.getConnection(DriverManager.java:247)
    at wqz.mysql.test.Test.main(Test.java:14)
Caused by: com.mysql.cj.exceptions.InvalidConnectionAttributeException: The server time zone value \'???ú±ê×??±??\' is unrecognized or represents more than one time zone. You must configure either the server or JDBC driver (via the serverTimezone configuration property) to use a more specifc time zone value if you want to utilize time zone support.
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.cj.exceptions.ExceptionFactory.createException(ExceptionFactory.java:61)
    at com.mysql.cj.exceptions.ExceptionFactory.createException(ExceptionFactory.java:85)
    at com.mysql.cj.util.TimeUtil.getCanonicalTimezone(TimeUtil.java:132)
    at com.mysql.cj.protocol.a.NativeProtocol.configureTimezone(NativeProtocol.java:2234)
    at com.mysql.cj.protocol.a.NativeProtocol.initServerSession(NativeProtocol.java:2258)
    at com.mysql.cj.jdbc.ConnectionImpl.initializePropsFromServer(ConnectionImpl.java:1319)
    at com.mysql.cj.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:966)
    at com.mysql.cj.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:825)
    ... 6 more

  程序仍然运行失败,根据异常信息(主要是上面红色加大部分信息)

  解决问题:

  1. 解决驱动类路径问题

  之前版本的驱动类的 全限定名为 com.mysql.jdbc.Driver, 较新版本的驱动类的包结构发生了改变,全限定名变为 com.mysql.cj.jdbc.Driver , 更改即可

//com.mysql.jdbc.Driver
com.mysql.cj.jdbc.Driver

  2. 解决时区问题 ...The server time zone value \'???ú±ê×??±??\'...

  解决此问题只需要在原 url 后附加 serverTimezone=UTC

//private static String url = "jdbc:mysql://localhost:3306/你的库?useSSL=false";

private static String url = "jdbc:mysql://localhost:3306/你的库?useSSL=false&serverTimezone=UTC";

  此时的程序变为:

package wqz.mysql.test;

import java.sql.DriverManager;

public class Test {
    private static String url = "jdbc:mysql://localhost:3306/你的库?useSSL=false&serverTimezone=UTC";
    private static String driver = "com.mysql.cj.jdbc.Driver";
    private static String username = "root";
    private static String passworld = "你的密码";
    
    public static void main(String[] args) throws Exception {
        Class.forName(driver).newInstance();
        //如果能连接成功,则打印连接
        System.out.println(DriverManager.getConnection(url, username, passworld));
        
    }
}

 

  运行程序:成功输出连接对象


 本文结束。

 

分类:

技术点:

相关文章: