Hologres kompatibel dengan protokol kabel PostgreSQL, sehingga alat atau aplikasi apa pun yang menggunakan PostgreSQL JDBC Driver dapat terhubung dengannya. Panduan ini memandu Anda melalui penyiapan koneksi JDBC, penulisan dan pengambilan data, serta penyetelan performa.
Di halaman ini
Prasyarat
Sebelum memulai, pastikan Anda telah memiliki:
-
Instans Hologres dengan database yang telah dibuat
-
Titik akhir (endpoint), port, dan nama database instans Anda (tersedia di halaman Instance Details pada Konsol Hologres, di bawah Network Information)
-
ID AccessKey dan Rahasia AccessKey Anda
Catatan penggunaan
-
Gunakan PostgreSQL JDBC Driver versi 42.3.2 atau lebih baru untuk menulis data melalui koneksi JDBC.
-
Untuk pengujian performa tulis, gunakan jaringan Virtual Private Cloud (VPC). Jaringan publik tidak dapat memenuhi tolok ukur pengujian performa.
-
Hologres tidak mendukung beberapa operasi tulis dalam satu transaksi. Atur
autoCommitketrue. Nilai default JDBC adalahtrue, jadi jangan panggil commit secara eksplisit dalam kode Anda. Jika Anda menerima errorERROR: INSERT in transaction is not supported now, aturautoCommitsecara eksplisit:Connection conn = DriverManager.getConnection(url, user, password); conn.setAutoCommit(true);
Terhubung ke Hologres menggunakan JDBC
Langkah 1: Tambahkan dependensi driver
Sebagian besar alat klien SQL menyertakan driver PostgreSQL bawaan — gunakan jika tersedia. Untuk aplikasi Java, tambahkan PostgreSQL JDBC Driver ke proyek Maven Anda. Unduh dari jdbc.postgresql.org/download dan gunakan versi 42.3.2 atau lebih baru (disarankan menggunakan versi stabil terbaru).
Hologres menggunakan PostgreSQL JDBC Driver standar — tidak ada driver khusus Hologres yang perlu diinstal.
Tambahkan dependensi berikut ke file pom.xml Anda:
<dependencies>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.3.2</version>
</dependency>
</dependencies>
Langkah 2: Buat string koneksi
Format string koneksi adalah:
jdbc:postgresql://<ENDPOINT>:<PORT>/<DBNAME>?user=<ACCESS_ID>&password=<ACCESS_KEY>
Parameter wajib
| Parameter | Deskripsi |
|---|---|
<ENDPOINT> |
Titik akhir jaringan instans Hologres. Temukan di halaman Instance Details pada Konsol Hologres, di bawah Network Information. Pilih titik akhir yang sesuai dengan lingkungan jaringan tempat kode Anda berjalan — ketidaksesuaian jenis jaringan menyebabkan kegagalan koneksi. |
<PORT> |
Port instans Hologres. Tersedia di bagian Network Information yang sama. |
<DBNAME> |
Nama database di Hologres. |
<ACCESS_ID> |
ID AccessKey Anda. Simpan dalam variabel lingkungan, bukan hardcoding. |
<ACCESS_KEY> |
Rahasia AccessKey Anda. Simpan dalam variabel lingkungan, bukan hardcoding. |
Parameter opsional
Tambahkan parameter berikut ke string koneksi sesuai kebutuhan. Pisahkan beberapa parameter dengan &.
| Parameter | Efek |
|---|---|
ApplicationName=<name> |
Memberi tag koneksi dengan nama aplikasi Anda, sehingga lebih mudah mengidentifikasinya di slow query checklist. |
reWriteBatchedInserts=true |
Menulis ulang batch insert menjadi satu pernyataan INSERT multi-nilai untuk throughput tulis yang lebih tinggi. |
currentSchema=<schema> |
Mengatur skema default. Diperlukan saat mengambil data dari tabel eksternal setelah mengaktifkan pemuatan otomatis tabel eksternal dari MaxCompute — nama Proyek MaxCompute dipetakan ke skema dengan nama yang sama. |
Contoh string koneksi dengan opsi yang direkomendasikan:
jdbc:postgresql://<ENDPOINT>:<PORT>/<DBNAME>?user=<ACCESS_ID>&password=<ACCESS_KEY>&ApplicationName=myApp&reWriteBatchedInserts=true
Langkah 3: Simpan kredensial dalam variabel lingkungan
Hardcoding kredensial dalam string koneksi menimbulkan risiko keamanan. Simpan sebagai variabel lingkungan sebagai gantinya. Di Linux, tambahkan baris berikut ke file ~/.bash_profile Anda:
export ALIBABA_CLOUD_USER=<ACCESS_ID>
export ALIBABA_CLOUD_PASSWORD=<ACCESS_KEY>
Langkah 4: Terhubung dan jalankan kueri
Untuk mencegah koneksi hang, konfigurasikan socket_timeout, login_timeout, dan tcp_keep_alive melalui PGProperty. Lihat contoh berikut.
Contoh berikut membaca kredensial dari variabel lingkungan, mengatur properti timeout, terhubung ke Hologres, dan menjalankan kueri SELECT dasar menggunakan Statement standar:
public class HologresTest {
private void jdbcExample() throws SQLException {
String user = System.getenv("ALIBABA_CLOUD_USER");
String password = System.getenv("ALIBABA_CLOUD_PASSWORD");
String url = String.format(
"jdbc:postgresql://<ENDPOINT>:<PORT>/<DBNAME>?currentSchema=<SCHEMA_NAME>&user=%s&password=%s",
user, password
);
Properties props = new Properties();
// Atur SOCKET_TIMEOUT berdasarkan waktu eksekusi kueri aktual untuk menghindari
// timeout prematur sebelum kueri selesai.
PGProperty.SOCKET_TIMEOUT.set(props, 3600);
PGProperty.LOGIN_TIMEOUT.set(props, 60);
PGProperty.TCP_KEEP_ALIVE.set(props, true);
try (Connection conn = DriverManager.getConnection(url, props)) {
try (Statement st = conn.createStatement()) {
String sql = "SELECT * FROM table where xxx limit 100";
try (ResultSet rs = st.executeQuery(sql)) {
while (rs.next()) {
// Baca nilai kolom pertama
String c1 = rs.getString(1);
}
}
}
}
}
}
Tulis dan ambil data
Tulis data
Anda dapat menulis data menggunakan mode Statement atau Prepared Statement di JDBC. Gunakan mode Prepared Statement untuk operasi tulis. Dalam mode ini, server menyimpan cache hasil kompilasi SQL, yang mengurangi latensi tulis dan meningkatkan throughput. Atur ukuran batch menjadi kelipatan 256 — ukuran batch minimum yang direkomendasikan adalah 256.
Batch insert
/*
* Tulis data dalam batch menggunakan mode Prepared Statement.
* Ukuran batch: 256 baris (minimum yang direkomendasikan).
*/
private static void writeBatchWithPreparedStatement(Connection conn) throws Exception {
try (PreparedStatement stmt = conn.prepareStatement("insert into test_tb values (?,?,?,?)")) {
int batchSize = 256;
for (int i = 0; i < batchSize; ++i) {
stmt.setInt(1, 1000 + i);
stmt.setString(2, "1");
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
Date parsedDate = dateFormat.parse("1990-11-11 00:00:00");
stmt.setTimestamp(3, new java.sql.Timestamp(parsedDate.getTime()));
stmt.setDouble(4, 0.1);
stmt.addBatch();
}
stmt.executeBatch();
}
}
Upsert dengan INSERT ON CONFLICT
Untuk memperbarui baris yang sudah ada saat terjadi konflik, gunakan sintaksis PostgreSQL INSERT ON CONFLICT. Tabel tujuan harus memiliki primary key.
private static void insertOverwrite(Connection conn) throws Exception {
try (PreparedStatement stmt = conn.prepareStatement(
"insert into test_tb values (?,?,?,?), (?,?,?,?), (?,?,?,?), (?,?,?,?), (?,?,?,?), (?,?,?,?) " +
"on conflict(pk) do update set f1 = excluded.f1, f2 = excluded.f2, f3 = excluded.f3"
)) {
int batchSize = 6;
for (int i = 0; i < batchSize; ++i) {
stmt.setInt(i * 4 + 1, i);
stmt.setString(i * 4 + 2, "1");
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
Date parsedDate = dateFormat.parse("1990-11-11 00:00:00");
stmt.setTimestamp(i * 4 + 3, new java.sql.Timestamp(parsedDate.getTime()));
stmt.setDouble(i * 4 + 4, 0.1);
}
int affectedRows = stmt.executeUpdate();
System.out.println("affected rows => " + affectedRows);
}
}
Contoh berikut menggunakan mode Prepared Statement untuk operasi tulis, yang meningkatkan throughput untuk insert berulang:
private void jdbcPreparedStmtExample() throws SQLException {
String user = System.getenv("ALIBABA_CLOUD_USER");
String password = System.getenv("ALIBABA_CLOUD_PASSWORD");
String url = String.format(
"jdbc:postgresql://<ENDPOINT>:<PORT>/<DBNAME>?currentSchema=<SCHEMA_NAME>&user=%s&password=%s",
user, password
);
try (Connection conn = DriverManager.getConnection(url)) {
String sql = "insert into test values" +
"(?, ?), (?, ?), (?, ?), (?, ?), (?, ?), " +
"(?, ?), (?, ?), (?, ?), (?, ?), (?, ?)";
try (PreparedStatement st = conn.prepareStatement(sql)) {
for (int i = 0; i < 10; ++i) {
for (int j = 0; j < 2 * 10; ++j) {
st.setString(j + 1, UUID.randomUUID().toString());
}
System.out.println("affected row => " + st.executeUpdate());
}
}
}
}
Kueri data
Gunakan pernyataan SELECT SQL standar untuk mengambil data dari tabel Hologres. Contoh SELECT dasar di Langkah 4 menunjukkan pola ini.
Konfigurasi kolam koneksi Druid
Gunakan Druid versi 1.1.12 atau lebih baru untuk terhubung ke Hologres.
Catatan penggunaan:
-
Atur
keepAlive=trueuntuk menggunakan kembali koneksi dan menghindari pergantian koneksi yang sering. -
Versi Druid 1.2.12 hingga 1.2.21 memiliki masalah yang diketahui di mana
connectTimeoutdansocketTimeoutsecara default bernilai 10 detik jika tidak ditentukan. Lakukan upgrade ke versi yang lebih baru jika Anda mengalami masalah ini. -
Atur
initialSize,minIdle, danmaxActiveberdasarkan ukuran instans dan beban kerja Anda.
<bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource"
init-method="init" destroy-method="close">
<!-- URL endpoint dari halaman konfigurasi instans di konsol -->
<property name="url" value="${jdbc_url}" />
<!-- ID AccessKey akun pengguna -->
<property name="username" value="${jdbc_user}" />
<!-- Rahasia AccessKey akun pengguna -->
<property name="password" value="${jdbc_password}" />
<!-- Ukuran pool: sesuaikan berdasarkan ukuran instans dan workload -->
<property name="initialSize" value="5" />
<property name="minIdle" value="10" />
<property name="maxActive" value="20" />
<!-- Tunggu hingga 60 detik untuk mendapatkan koneksi dari pool -->
<property name="maxWait" value="60000" />
<!-- Periksa koneksi idle setiap 2 detik -->
<property name="timeBetweenEvictionRunsMillis" value="2000" />
<!-- Hapus koneksi yang idle lebih dari 10 menit -->
<property name="minEvictableIdleTimeMillis" value="600000" />
<property name="maxEvictableIdleTimeMillis" value="900000" />
<property name="validationQuery" value="select 1" />
<property name="testWhileIdle" value="true" />
<!-- Jangan uji koneksi saat dipinjam/dikembalikan (mengurangi overhead) -->
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<property name="keepAlive" value="true" />
<property name="phyMaxUseCount" value="100000" />
<property name="filters" value="stat" />
</bean>
Atur parameter GUC
Parameter Grand Unified Configuration (GUC) mengontrol perilaku tingkat sesi seperti timeout. Atur parameter tersebut saat koneksi menggunakan PGProperty.OPTIONS.
Contoh berikut mengatur statement_timeout dan idle_in_transaction_session_timeout menjadi 12.345 milidetik:
import org.postgresql.PGProperty;
import java.sql.*;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
public class GucDemo {
public static void main(String[] args) {
String hostname = "hgpostcn-cn-xxxx-cn-hangzhou.hologres.aliyuncs.com";
String port = "80";
String dbname = "demo";
String jdbcUrl = "jdbc:postgresql://" + hostname + ":" + port + "/" + dbname;
Properties properties = new Properties();
properties.setProperty("user", "xxxxx");
properties.setProperty("password", "xxxx");
// Atur parameter GUC tingkat session
PGProperty.OPTIONS.set(properties,
"--statement_timeout=12345 --idle_in_transaction_session_timeout=12345");
try {
Class.forName("org.postgresql.Driver");
Connection connection = DriverManager.getConnection(jdbcUrl, properties);
PreparedStatement preparedStatement =
connection.prepareStatement("show statement_timeout");
ResultSet resultSet = preparedStatement.executeQuery();
while (resultSet.next()) {
ResultSetMetaData rsmd = resultSet.getMetaData();
int columnCount = rsmd.getColumnCount();
Map<String, Object> map = new HashMap<>();
for (int i = 0; i < columnCount; i++) {
map.put(rsmd.getColumnName(i + 1).toLowerCase(), resultSet.getObject(i + 1));
}
System.out.println(map);
}
} catch (Exception exception) {
exception.printStackTrace();
}
}
}
Untuk daftar lengkap parameter GUC yang tersedia, lihat parameter GUC.
Penyetelan performa
Terapkan praktik berikut untuk memaksimalkan throughput tulis:
-
Gunakan jaringan VPC. Jaringan publik menambahkan latensi yang menghambat pencapaian performa tulis optimal.
-
Aktifkan penulisan ulang batch. Tambahkan
reWriteBatchedInserts=trueke string koneksi. Ini menulis ulang insert individual menjadi satu pernyataan multi-nilai, yang secara signifikan meningkatkan throughput. -
Gunakan mode Prepared Statement. Server menyimpan cache hasil kompilasi SQL, sehingga mengurangi latensi per baris.
-
Atur ukuran batch menjadi kelipatan 256. Ukuran batch efektif minimum adalah 256. Kelipatan yang lebih besar memberikan peningkatan throughput lebih lanjut. Untuk batching otomatis, gunakan Holo Client.
Contoh string koneksi dengan semua opsi performa diaktifkan:
jdbc:postgresql://<ENDPOINT>:<PORT>/<DBNAME>?ApplicationName=<APPLICATION_NAME>&reWriteBatchedInserts=true
Load balancing
Mulai dari Hologres V1.3, Anda dapat mengonfigurasi beberapa instans secondary read-only dalam JDBC untuk mendistribusikan beban kerja baca. Untuk instruksi penyiapan, lihat Load balancing berbasis JDBC.