使用 Java 透過 SSH 連接到遠端 MySQL 資料庫
1. 概述
Secure Shell (SSH) 讓我們可以安全地存取和管理遠端系統,包括執行命令、傳輸檔案和隧道服務。
我們可以透過 SSH 會話建立到遠端 MySQL 資料庫的連線。 Java 中存在多種 SSH 用戶端,最常見的一種是 Java 安全通道 (JSch)。
在本教程中,我們將探討如何透過 SSH 會話連接到遠端伺服器的localhost
上執行的 MySQL 資料庫。
2.了解SSH埠轉發
連接埠轉送允許透過 SSH 連接將流量從本地端口定向到遠端伺服器上的端口,從而在客戶端系統和遠端伺服器之間傳輸資料。
當防火牆或其他限制阻止直接連接到遠端伺服器的 IP 和連接埠時,這尤其有用。
在我們的例子中,MySQL 伺服器在遠端電腦的localhost
上運行,通常使用端口 3306。相反,我們可以使用 SSH 上的本機連接埠轉送來建立與資料庫的安全連線。
在本地端口轉發中,我們在本地機器上分配一個可用端口,並將其與遠端運行的MySQL伺服器的端口綁定,以允許我們的程式和遠端伺服器之間進行資料通信。
3.Maven依賴
首先,我們將JSch和MySQL 連接器相依性加入pom.xml
中:
<dependency>
<groupId>com.github.mwiede</groupId>
<artifactId>jsch</artifactId>
<version>0.2.20</version>
</dependency>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<version>9.0.0</version>
</dependency>
JSch 依賴項提供了Session
等類,這些類別對於建立到遠端伺服器的 SSH 連線至關重要。此外,MySQL 連接器允許我們建立與正在運行的 MySQL 伺服器的連線。
4. 連接詳情
此外,讓我們定義遠端伺服器的連接詳細資訊:
private static final String HOST = "HOST";
private static final String USER = "USERNAME";
private static final String PRIVATE_KEY = "PATH_TO_PRIVATEKEY";
private static final int PORT = 22;
在上面的程式碼中,我們定義了建立 SSH 會話所需的憑證。接下來,讓我們定義遠端資料庫的連線詳細資訊:
private static final String DATABASE_HOST = "localhost";
private static final int DATABASE_PORT = 3306;
private static final String DATABASE_USERNAME = "DATABASE_USERNAME";
private static final String DATABASE_PASSWORD = "DATABASE_PASSWORD";
MySQL 資料庫運行在遠端電腦的localhost
上,使用連接埠 3306。
5. 建立 SSH 會話
定義連線詳細資料後,讓我們建立一個JSch
實例來引導與遠端伺服器的連線:
JSch jsch = new JSch();
jsch.addIdentity(PRIVATE_KEY);
在這裡,我們使用私鑰來驗證我們的身分。但是,我們也可以使用基於密碼的身份驗證。
接下來,讓我們建立一個新的 SSH 會話:
Session session = jsch.getSession(USER, HOST, PORT);
session.setConfig("StrictHostKeyChecking", "no");
session.connect();
在上面的程式碼中,我們使用連接詳細資訊建立一個新Session
,並為簡單起見禁用關鍵主機檢查。停用主機金鑰檢查對於測試來說很方便,但出於安全目的應在生產中避免。
最後,我們呼叫Session
物件上的connect()
方法來開啟一個新的 SSH 會話。
6.透過連接埠轉送連接MySQL
接下來,讓我們使用 SSH 連接埠轉送來隧道 MySQL 連接埠:
int port = session.setPortForwardingL(0, DATABASE_HOST, DATABASE_PORT);
在上面的程式碼中,我們呼叫Session
物件上的setPortForwardingL()
方法來設定本地埠轉送。透過傳遞0
作為本地端口,程式動態選擇一個可用的本地端口,將流量轉送到遠端 MySQL 伺服器的端口 3306 。
連接埠轉送(隧道)允許傳送到本機連接埠的流量透過 SSH 連線轉送至遠端電腦上的 MySQL 伺服器。
此外,讓我們使用轉送連接埠連接到 MySQL 伺服器:
String databaseUrl = "jdbc:mysql://" + DATABASE_HOST + ":" + port + "/baeldung";
Connection connection = DriverManager.getConnection(databaseUrl, DATABASE_USERNAME, DATABASE_PASSWORD);
在上面的程式碼中,我們使用 JDBC Connection
類別建立與資料庫的連線。在我們的資料庫 URL 中,我們使用轉送的本機連接埠而不是遠端 MySQL 伺服器的預設連接埠 (3306)。
此外,讓我們驗證連線是否存在:
assertNotNull(connection);
在上面的程式碼中,我們斷言與資料庫的連接不為null
。
7. 簡單查詢
此外,讓我們對已建立的連線執行一些資料庫操作。首先,我們建立一個表:
String createTableSQL = "CREATE TABLE test_table (id INT, data VARCHAR(255))";
try (Statement statement = connection.createStatement()) {
statement.execute(createTableSQL);
}
在這裡,我們在baeldung
資料庫中建立一個test_table
。接下來,我們將一筆記錄插入到已建立的表中:
String insertDataSQL = "INSERT INTO test_table (id, data) VALUES (1, 'test data')";
try (Statement statement = connection.createStatement()) {
statement.execute(insertDataSQL);
}
最後,我們斷言創建的表存在於資料庫中:
try (Statement statement = connection.createStatement()) {
ResultSet resultSet = statement.executeQuery("SHOW TABLES LIKE 'test_table'");
return resultSet.next();
}
在上面的程式碼中,我們驗證建立的表是否存在於資料庫中。
8. 關閉連接
本質上,我們需要在操作後關閉 SSH 會話和資料庫連線:
session.disconnect();
connection.close();
在上面的程式碼中,我們分別呼叫Session
和Connection
物件的disconnect()
和close()
方法來釋放資源。它還可以防止潛在的記憶體洩漏。
9. 結論
在本文中,我們學習如何透過 SSH 會話連接到遠端資料庫。此外,我們學習了本機連接埠轉發,並將其應用於透過已建立的 SSH 會話連接到遠端 MySQL 資料庫。
與往常一樣,範例的完整原始程式碼可在 GitHub 上取得。