【问题标题】:Remotely accessing mySQL through SSH in JavaJava中通过SSH远程访问mySQL
【发布时间】:2014-07-10 03:10:47
【问题描述】:

我正在尝试将我的本地 Java 应用程序连接到远程 mySQL 服务器。我对服务器及其 mySQL 具有 shell 访问权限,但没有 root 访问权限。

我试图实现一些我在网上找到的似乎可以实现这一目标的代码。首先我通过 SSH 连接到服务器,然后尝试访问 mySQL 数据库。但是,我收到以下错误:

Jul 09, 2014 2:20:06 PM [myClassName] connect
SEVERE: null,  message from server: "Host '[remoteHost]' is not allowed to connect to this MySQL server"

我知道默认情况下 mySQL 不允许远程客户端访问,但我不明白的是,在这种情况下,它似乎不允许自己访问自己的 mySQL 服务器。 (即错误消息中的 ["remoteHost"] 与托管我尝试访问的 mySQL 服务器的主机相同。)

我使用的代码模板如下。出于此问题的目的,我已将所有字段(用户、通行证、主机等)与模板上的相同。

我是否需要要求我的系统管理员授予我特殊权限?我通过终端访问 mySQL 服务器没有问题。先谢谢大家了

感谢 Kahimyang 项目 (http://kahimyang.info/kauswagan/code-blogs/1337/ssh-tunneling-with-java-a-database-connection-example)。

import java.util.logging.Logger;
import com.jcraft.jsch.*;
import java.util.logging.Level;

public class MysqlManager {

    // Logger
    private final static Logger LOGGER =
            Logger.getLogger(MysqlManager.class.getName());

    public static void main(String args[]) {
        MysqlManager mng = new MysqlManager ();
        mng.connect();
    }

    public void connect() {

        // 
        int assigned_port;   
        final int local_port=3309;

        // Remote host and port
        final int remote_port=3306;
        final String remote_host="kahimyang.info";

        try {
            JSch jsch = new JSch(); 

            // Create SSH session.  Port 22 is your SSH port which
            // is open in your firewall setup.
            Session session = jsch.getSession("user", remote_host, 22);
            session.setPassword("ssh_password");

            // Additional SSH options.  See your ssh_config manual for
            // more options.  Set options according to your requirements.
            java.util.Properties config = new java.util.Properties();
            config.put("StrictHostKeyChecking", "no");
            config.put("Compression", "yes");
            config.put("ConnectionAttempts","2");

            session.setConfig(config);

            // Connect
            session.connect();            

            // Create the tunnel through port forwarding.  
            // This is basically instructing jsch session to send 
            // data received from local_port in the local machine to 
            // remote_port of the remote_host
            // assigned_port is the port assigned by jsch for use,
            // it may not always be the same as
            // local_port.

            assigned_port = session.setPortForwardingL(local_port, 
                    remote_host, remote_port);

        } catch (JSchException e) {            
            LOGGER.log(Level.SEVERE, e.getMessage()); return;
        }

        if (assigned_port == 0) {
            LOGGER.log(Level.SEVERE, "Port forwarding failed !"); 
            return;
        }

        // Database access credintials.  Make sure this user has
        // "connect" access to this database;

        // these may be initialized somewhere else in your code.
        final String database_user="user";
        final String database_password="password";
        final String database = "database";

        // Build the  database connection URL.
        StringBuilder url =
                new StringBuilder("jdbc:mysql://localhost:");

        // use assigned_port to establish database connection
        url.append(assigned_port).append ("/").append(database).append ("?user=").
                append(database_user).append ("&password=").
                append (database_password);

        try {
            Class.forName(
                    "com.mysql.jdbc.Driver").newInstance();
            java.sql.Connection connection =
                    java.sql.DriverManager.getConnection(url.toString());

            java.sql.DatabaseMetaData metadata = connection.getMetaData();

             // Get all the tables and views
            String[] tableType = {"TABLE", "VIEW"};                       
            java.sql.ResultSet tables = metadata.getTables(null, null, "%", tableType);
            String tableName;
            while (tables.next()) {
                tableName = tables.getString(3);

                // Get the columns from this table
                java.sql.ResultSet columns = 
                        metadata.getColumns(null, tableName, null, null);

                String columnName;
                int dataType;
                while (columns.next()) {
                    columnName = columns.getString(4);
                    dataType = columns.getInt(5);

                    // Your actual task;
                }
            }

        } catch (ClassNotFoundException |
                IllegalAccessException |
                InstantiationException |
                java.sql.SQLException e) {
            LOGGER.log(Level.SEVERE, e.getMessage());
        }

    }
}

【问题讨论】:

    标签: java mysql ssh


    【解决方案1】:

    要确定您的问题是否与 Java 相关,您可以尝试telnet 到 SQL 服务器。

    $ telnet localhost 3306
    

    如果您不被允许连接,您将收到与您类似的错误消息。 要允许访问,您的系统管理员需要运行以下命令:

    $ mysql -u root -p
    Enter password:
    
    mysql> use mysql
    
    mysql> GRANT ALL ON *.* to root@'localhost' IDENTIFIED BY 'your-root-password'; 
    
    mysql> FLUSH PRIVILEGES;
    

    关于您的担忧(SQL 服务器不允许从 localhost 访问):只有在确实需要时才允许访问。因此,如果您只有远程 SQL 客户端,则无需允许来自主机 localhost 的访问。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-11-29
      • 2012-01-21
      • 1970-01-01
      • 2019-07-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多