Hologres是一款服務分析一體化的實時數倉,支持海量數據集(百億以上),基于SQL提供低延時(10ms以下)、高QPS(上百萬每秒)的Key/Value點查服務。本文主要指導您在點查場景的最佳實踐,包括建表和查詢方式等。
創建表
創建點查場景的表時,您需要注意如下幾點:
Key/Value點查的Key字段需要設置為主鍵(Primary Key)。
Primary Key與Clustering Key保持一致。
需要將查詢條件中的列設置為Distribution Key,一般默認主鍵為Distribution Key。
表的存儲類型需要設置為行存。
建議連接Hologres實例時使用VPC網絡的域名。
當有TEXT、VARCHAR、CHAR類型時,建議使用TEXT類型,而不是VARCHAR或者CHAR類型。
具體創建表的示例語句如下:
--創建一張行存表test_kv_table并將key字段設置為主鍵
begin;
create table test_kv_table(
key text primary key,
value text
);
call set_table_property('test_kv_table', 'orientation', 'row');
call set_table_property('test_kv_table', 'clustering_key', 'key');
call set_table_property('test_kv_table', 'distribution_key', 'key');
commit;
數據查詢
當您將數據導入表之后就可以對表數據進行點查詢。具體查詢方式如下所示:
一次查詢單個Key
select * from test_kv_table where key = '1';
一次查詢多個Key
select * from test_kv_table where key in ('1', '2', '3');
使用Java查詢
以Java為例,您可以使用Prepared Statement來進行Key/Value查詢,示例如下。
說明建議使用Hologres的VPC網絡的域名連接。
使用Prepared Statement進行Key/Value查詢會得到更好的查詢性能。
Prepared Statement可以復用,不需要每次查詢都新建一個Prepared Statement對象。
//查詢取值1-100的多個key private static void testKV(Connection conn) throws Exception { String sql = "select * from test_kv_table where key = ?"; try (PreparedStatement stmt = conn.prepareStatement(sql)) { for (int i = 0; i < 100; ++i) { stmt.setString(1, Integer.toString(i)); long begin = System.currentTimeMillis(); try (ResultSet rs = stmt.executeQuery()) { long cost = System.currentTimeMillis() - begin; while(rs.next()) { System.out.println("data => " + rs.getObject(1).toString() + " " + rs.getObject(2).toString() + " latency => [" + cost + "]ms"); } } } } }
使用HoloClient查詢
HoloClient會將多個查詢合并為一個SQL語句,簡化開發復雜度,示例如下,建議使用Maven上發布的最新版本。
<dependency> <groupId>com.alibaba.hologres</groupId> <artifactId>holo-client</artifactId> <version>{1.2.16.5}</version> </dependency> // 配置參數,url格式為 jdbc:postgresql://host:port/db HoloConfig config = new HoloConfig(); config.setJdbcUrl(url); config.setUsername(username); config.setPassword(password); config.setReadThreadCount(10);//讀并發,最多占用10個jdbc連接 try (HoloClient client = new HoloClient(config)) { //create table t0(id int not null,name0 text,address text,primary key(id)) TableSchema schema0 = client.getTableSchema("t0"); Get get = Get.newBuilder(schema).setPrimaryKey("id", 0).build(); // where id=0; client.get(get).thenAcceptAsync((record)->{ // do something after get result }); Get get1 = Get.newBuilder(schema).setPrimaryKey("id", 1).build(); // where id=1; client.get(get1).thenAcceptAsync((record)->{ // do something after get result }); catch(HoloClientException e){ }
Java使用示例
如下內容為完整的Java使用示例,指導您創建一張行存表test_kv_table并將key字段設置為主鍵,一次查詢多個Key并輸出查詢結果。
package test;
import org.postgresql.jdbc.PgConnection;
import java.sql.*;
//創建一張行存表test_kv_table并將key字段設置為主鍵
public class TestPointQuery {
private static void init(Connection conn) throws Exception {
try (Statement stmt = conn.createStatement()) {
stmt.execute("drop table if exists test_kv_table;");
stmt.execute("begin;");
stmt.execute("create table if not exists test_kv_table(key text primary key, value text);");
stmt.execute("call set_table_property('test_kv_table', 'orientation', 'row');");
stmt.execute("call set_table_property('test_kv_table', 'shard_count', '20');");
stmt.execute("end;");
stmt.execute("insert into test_kv_table select i, i from generate_series(1, 10000)i");
}
}
//查詢取值1-100的多個key
private static void testKV(Connection conn) throws Exception {
String sql = "select *from test_kv_table where key = ?";
try (PreparedStatement stmt = conn.prepareStatement(sql)) {
for (int i = 0; i < 100; ++i) {
stmt.setString(1, Integer.toString(i));
long begin = System.currentTimeMillis();
try (ResultSet rs = stmt.executeQuery()) {
long cost = System.currentTimeMillis() - begin;
while(rs.next()) {
System.out.println("data => " + rs.getObject(1).toString() + " " + rs.getObject(2).toString() + " latency => [" + cost + "]ms");
}
}
}
}
}
//輸出查詢結果
public static void main(String[] args) throws Exception {
Class.forName("org.postgresql.Driver").newInstance();
String host = "";
String db = "";
String user = "";
String password = "";
String url = "jdbc:postgresql://" + host + "/" + db;
try (PgConnection conn = (PgConnection) DriverManager.getConnection(url, user, password)) {
System.out.println("init the test_kv_table for testing");
init(conn);
System.out.println("run test on test_kv_table");
testKV(conn);
}
}
}
參數說明:
host:Hologres實例的域名,您可在Hologres控制臺實例詳情頁的網絡信息區域獲取域名。
db:Hologres實例下的數據庫名稱。
user:阿里云賬號的AccessKey ID。您可以進入AccessKey管理頁面獲取AccessKey ID。
password:對應阿里云賬號的AccessKey Secret。