在使用全密態MySQL時,目前只支援使用MySQL的Text Protocol。全密態MySQL在MySQL服務端返回的ResultSet上,對目標敏感性資料進行加密。為了正確拿到密文,您必須首先對MySQL的Text Protocol進行正確解析。為了讓用戶端需要能夠正確處理密文的ResultSet,阿里雲推出了全密態用戶端Java SDK模組(即EncDB SDK)。EncDB SDK提供了可信密鑰管理、資料加解密、端到端安全通訊功能。本文檔介紹如何使用EncDB SDK訪問資料庫。
準備工作
擷取加密資料庫串連資訊。您首先需要擷取加密資料庫的串連資訊,如網域名稱(host)、連接埠(port)、資料庫執行個體名(dbname)、使用者名稱(username)、密碼(password)等。
配置加密規則。具體操作請參見建立加密規則。
配置Java SDK(EncDB SDK)
在您的Maven專案裡添加依賴:
<dependencies>
...
<!-- 任意版本mysql conenctor都行 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.32</version>
</dependency>
<dependency>
<groupId>com.alibaba.encdb</groupId>
<artifactId>libencdb</artifactId>
<version>1.2.11-SNAPSHOT</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk15on -->
<dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcprov-jdk15on</artifactId>
<version>1.62</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.bouncycastle/bcpkix-jdk15on -->
<dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcpkix-jdk15on</artifactId>
<version>1.62</version>
</dependency>
<dependency>
<groupId>com.alibaba.fastjson2</groupId>
<artifactId>fastjson2</artifactId>
<version>2.0.2</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.postgresql/postgresql -->
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.2.23</version>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>24.1.1-jre</version>
</dependency>
...
</dependencies>
配置樣本
您可以使用任何形式的MySQL用戶端(只要能正確解析MySQL Text Protocol),並在此基礎上使用EncDB SDK對密文進行處理。以下樣本是基於社區版MySQL JDBC和EncDB SDK構建的DEMO(需要在pom裡額外引入MySQL JDBC),請用一個全密態PolarDB MySQL版的叢集串連資訊來完成下面的Demo,並且對enc_int
列配置加密規則。
// 請填入全密態PolarDB MySQL的叢集串連資訊(注意不要是主地址)
String hostname = "asodijasdoijaisd.rwlb.rds.aliyuncs.com";
String port = "3306";
String dbname = "test_db";
String username = "ruanbu";
String password = "123456Abc!";
Class.forName("com.mysql.cj.jdbc.Driver");
String dbUrl = String.format("jdbc:mysql://%s:%s/%s", hostname, port, dbname);
java.sql.Connection conn = java.sql.DriverManager.getConnection(dbUrl, username, password);
// 使用者密鑰,demo內手寫一個32位的16進位串即可
String mek = "00112233445566778899aabbccddeeff";
com.alibaba.encdb.EncdbSDK sdk =
com.alibaba.encdb.crypto.EncdbSDKBuilder.newInstance()
.setKeyMgmtType(com.alibaba.encdb.common.Constants.KeyMgmtType.MYSQL_PROXY)
.setDbConnection(conn)
.setMek(mek)
.build();
com.alibaba.encdb.Cryptor cryptor = sdk.getCryptor();
// 建表測試
conn.createStatement().executeUpdate("drop table if exists test");
conn.createStatement().executeUpdate("create table test (enc_int int)");
conn.createStatement().executeUpdate("insert into test values (1)");
java.sql.ResultSet rs = conn.createStatement().executeQuery("select * from test");
rs.next();
// 擷取密文位元組流
byte[] cipher = rs.getBytes(1);
// 調用Cryptor.decrypt方法擷取明文位元組流
byte[] plaintext = cryptor.decrypt(cipher);
// 輸出,對比明密文
System.out.println("明文:" + new String(plaintext) + " 密文:" + new String(cipher));
輸出:
明文:1 密文:QmEA/4d0ROXfA3QeUZFiu7EdlvZy4Yaa+uDnyFHvFOnVK4dtgVIzjrYI54I=
Java SDK(EncDB SDK)API介紹
EncdbSDKBuilder
即com.alibaba.encdb.crypto.EncdbSDKBuilder
,它是一個EncdbSDK
類的構造類,使用中您需要以下API:// 擷取一個新的EncdbSDKBuilder執行個體。您總是應該用這個方法來構造EncdbSDKBuilder。 EncdbSDKBuilder newInstance(); // (必選)設定一個資料庫連接,用於EncDB SDK相關的密鑰管理動作。這個資料庫連接可以獨立於業務中實際用到的資料庫連接。 EncdbSDKBuilder setDbConnection(java.sql.Connection dbConnection); // (必選)設定EncDB SDK對接的用戶端類型。對於全密態MySQL,您應該設定MYSQL_PROXY選項 EncdbSDKBuilder setKeyMgmtType(KeyMgmtType kmType); // (必選)設定使用者主要金鑰。這裡我們要求一個128位(即16位元組)的byte[]對象 EncdbSDKBuilder setMek(byte[] mek); // (可選)設定密碼編譯演算法。可選項有AES_128_GCM、AES_128_CTR、AES_128_CBC、AES_128_ECB、SM4_128_CBC、SM4_128_ECB、SM4_128_GCM、SM4_128_CTR。不設定的話預設為SM4_128_CBC。 EncdbSDKBuilder setEncAlgo(EncAlgo encAlgo); // 在完成上述設定之後,構造一個EncdbSDK對象 EncdbSDK build();
EncdbSDK
即com.alibaba.encdb.EncdbSDK
。使用中您需要以下API:// 擷取一個Cryptor對象,用於操作密文/明文。 Cryptor getCryptor();
Cryptor
即com.alibaba.encdb.Cryptor
。使用中您需要以下API:// 輸入密文,返回對應的明文 byte[] decrypt(byte[] val);