テーブルは、Hologres でデータを格納および整理するための基本単位です。ストレージフォーマット、テーブルインデックス、およびプロパティを設定することで、効率的なリアルタイムデータ処理と大規模なデータ分析を実現できます。
クイックスタート
事前準備
テーブルの作成
Hologres V2.1 以降で利用可能な CREATE TABLE WITH 構文を使用することを推奨します。次の例では、階層的な命名規則に従い、さまざまなフィールドと包括的なコメントを含む取引詳細テーブルを作成します。
BEGIN;
-- 取引詳細のファクトテーブルを作成 (標準の非パーティションテーブル)
-- public スキーマを明示的に指定し、テーブル名に階層的な命名 (dwd_xxx) を使用
CREATE TABLE IF NOT EXISTS public.dwd_trade_orders (
order_id BIGINT NOT NULL, -- 一意の注文 ID
shop_id INT NOT NULL, -- ショップ ID
user_id TEXT NOT NULL, -- ユーザー ID
order_amount NUMERIC(12, 2) DEFAULT 0.00, -- 注文金額
payment NUMERIC(12, 2) DEFAULT 0.00, -- 支払金額
payment_type INT DEFAULT 0, -- 支払タイプ (0: 未払い, 1: Alipay, 2: WeChat, 3: クレジットカード)
is_delivered BOOLEAN DEFAULT false, -- 配送済みかどうか
dt TEXT NOT NULL, -- データタイムスタンプ
order_time TIMESTAMPTZ NOT NULL DEFAULT CURRENT_TIMESTAMP, -- 注文時間
PRIMARY KEY (order_id) -- プライマリキーを設定してデータの一意性を保証
)
WITH (
orientation = 'column', -- カラムストアを使用: 大量データセットに対するリアルタイム分析 (OLAP) に最適
distribution_key = 'order_id', -- ディストリビューションキーを設定: order_id によってデータがシャーディングされる
clustering_key = 'order_time:asc', -- クラスタリングキーを設定: ファイル内で時間によってデータが昇順にソートされる
event_time_column = 'order_time', -- セグメントキーを設定: ファイルレベルのプルーニングを有効にし、時間範囲を迅速にフィルタリング
bitmap_columns = 'shop_id,payment_type,is_delivered', -- ビットマップインデックスを設定: 低カーディナリティ列での等価フィルターを高速化
dictionary_encoding_columns = 'user_id:auto' -- ディクショナリエンコーディングを設定: 文字列型の列での集約とフィルタリングを高速化
);
-- メタデータコメントの追加
COMMENT ON TABLE public.dwd_trade_orders IS '取引注文詳細の基本ファクトテーブル';
COMMENT ON COLUMN public.dwd_trade_orders.order_id IS '一意の注文 ID';
COMMENT ON COLUMN public.dwd_trade_orders.shop_id IS '一意のショップ ID';
COMMENT ON COLUMN public.dwd_trade_orders.user_id IS '購入者のユーザー ID';
COMMENT ON COLUMN public.dwd_trade_orders.dt IS 'データタイムスタンプ、フォーマット YYYYMMDD';
COMMENT ON COLUMN public.dwd_trade_orders.order_time IS '注文が作成された正確なタイムスタンプ';
COMMIT;テーブル構造の表示
次のコマンドを実行して、テーブルのデータ定義言語 (DDL) 文を表示できます。
SELECT hg_dump_script('public.dwd_trade_orders');データの挿入
Hologres は、標準のデータ操作言語 (DML) 構文をサポートしています。次の例では、シミュレートされた本番データを 10 行テーブルに挿入します。
INSERT INTO public.dwd_trade_orders (order_id, shop_id, user_id, order_amount, payment, payment_type, is_delivered, dt, order_time) VALUES
(50001, 101, 'U678', 299.00, 280.00, 1, true, '20231101', '2023-11-01 10:00:01+08'),
(50002, 102, 'U992', 59.00, 59.00, 2, false, '20231101', '2023-11-01 10:05:12+08'),
(50003, 101, 'U441', 150.00, 145.00, 1, true, '20231101', '2023-11-01 10:10:45+08'),
(50004, 105, 'U219', 888.00, 888.00, 3, true, '20231101', '2023-11-01 10:20:11+08'),
(50005, 102, 'U883', 35.00, 30.00, 1, false, '20231101', '2023-11-01 10:32:00+08'),
(50006, 110, 'U007', 120.50, 120.50, 2, true, '20231101', '2023-11-01 10:45:33+08'),
(50007, 101, 'U321', 210.00, 210.00, 1, true, '20231101', '2023-11-01 11:02:19+08'),
(50008, 108, 'U556', 45.00, 45.00, 2, false, '20231101', '2023-11-01 11:15:04+08'),
(50009, 101, 'U112', 300.00, 290.00, 3, true, '20231101', '2023-11-01 11:25:55+08'),
(50010, 105, 'U449', 99.90, 99.90, 1, true, '20231101', '2023-11-01 11:40:22+08');データのクエリ
-- ショップごとの合計支払額を計算し、金額の降順でソート
SELECT
shop_id,
COUNT(1) as total_orders,
SUM(payment) as total_payment
FROM public.dwd_trade_orders
GROUP BY shop_id
ORDER BY total_payment DESC;クエリは次の結果を返します。
shop_id total_orders total_payment
105 2 987.90
101 4 925.00
110 1 120.50
102 1 59.00
108 1 45.00構文リファレンス
テーブル作成構文
Hologres は、テーブルプロパティの設定とコメントの追加のために 2 つの構文を提供します。
標準構文 (V2.1 以降で推奨)
WITH句を使用してプロパティを定義できます。この構文はよりコンパクトで、パフォーマンスも向上します。CREATE TABLE 文の後にコメントを追加できます。完全な例については、「テーブルの作成」をご参照ください。BEGIN; CREATE TABLE [ IF NOT EXISTS] [schema_name.]table_name ([ { column_name column_type [column_constraints, [...]] | table_constraints [,...] } ]) [WITH ( property = 'value', [, ...] )] ; [COMMENT ON COLUMN <[schema_name.]tablename.column> IS '<value>';] [COMMENT ON TABLE <[schema_name.]tablename> IS '<value>';] COMMIT;互換構文 (すべてのバージョンでサポート)
set_table_propertyを伴うCALL文を使用してプロパティを設定し、COMMENT文を使用してコメントを追加できます。これらの文は、CREATE TABLE文と同じトランザクションブロック (BEGIN...COMMIT) 内にある必要があります。BEGIN; CREATE TABLE [ IF NOT EXISTS] [schema_name.]table_name ([ { column_name column_type [column_constraints, [...]] | table_constraints [,...] } ]); CALL set_table_property('[schema_name.]<table_name>', '<property>', '<value>'); COMMENT ON COLUMN <[schema_name.]tablename.column> IS '<value>'; COMMENT ON TABLE <[schema_name.]tablename> IS '<value>'; COMMIT;
テーブルプロパティ
パラメーター | 説明 | カラムストアテーブル | 行指向テーブル | ハイブリッドテーブル | 推奨値 | テーブル作成後に変更可能か |
orientation | テーブルのストレージフォーマットを指定します。詳細については、「テーブルストレージフォーマット:カラムストア、ローストア、ハイブリッド」をご参照ください。 |
「例:大規模データに対するリアルタイム分析 (ファクトテーブル)」をご参照ください。 |
「例:プライマリキーによる高同時実行ポイントルックアップ (ディメンションテーブル)」をご参照ください。 |
「例:混合ワークロード (ハイブリッドストレージ)」をご参照ください。 | column | いいえ、変更できません。変更するにはテーブルを再作成する必要があります。 |
distribution_key | データ分散戦略を決定するディストリビューションキーを指定します。詳細については、「ディストリビューションキー」をご参照ください。 | デフォルトではプライマリキーが使用されます。ビジネスシナリオに基づいてキーを変更できます。 | デフォルトではプライマリキーが使用されます。 | デフォルトではプライマリキーが使用されます。 | プライマリキーのサブセット。1 つの列のみを使用することを推奨します。 | |
clustering_key | クラスタリングキーを指定することで、クエリのパフォーマンスが向上します。詳細については、「クラスタリングキー」をご参照ください。 | デフォルトでは空です。 | デフォルトではプライマリキーが使用されます。 | デフォルトでは空です。 | 昇順に指定する列は、1 つまでとすることを推奨します。 | |
event_time_column | クエリパフォーマンスを向上させるセグメントキーを指定します。詳細については、「イベント時間列 (セグメントキー)」をご参照ください。 | デフォルトでは、NULL でない最初のタイムスタンプ列が使用されます。 | 非サポート | デフォルトでは、NULL でない最初のタイムスタンプ列が使用されます。 | タイムスタンプ列を使用することを推奨します。 | |
table_group | shard 数を管理するために使用される論理的なストレージ概念です。詳細については、「テーブルグループと shard 数ガイド」をご参照ください。 | デフォルトでは | デフォルト値を使用します。 | いいえ。テーブルグループを変更するには、テーブルを再作成するか、リシャーディングを実行する必要があります。 | ||
bitmap_columns | ビットマップインデックスを指定します。詳細については、「ビットマップインデックス」をご参照ください。 | 必要に応じて使用します。 | 非サポート | 必要に応じて使用します。 | 等価比較で使用される列に推奨されます。通常、列数は 10 以下に制限されます。 | はい。詳細については、「ALTER TABLE」をご参照ください。 |
ディクショナリエンコーディング。 | 必要に応じて使用します。 | 非サポート | 必要に応じて使用します。 | 最大 10 個の低カーディナリティ列を使用することを推奨します。 | はい。詳細については、「ALTER TABLE」をご参照ください。 | |
テーブル内のデータの有効期間 (TTL) を秒単位で指定します。TTL は正確ではありません。本番環境でデータライフサイクルを管理するために TTL を使用しないでください。パーティションテーブルの使用を推奨します。詳細については、「CREATE PARTITION TABLE」をご参照ください。 | 必要に応じて使用します。 | デフォルト値を使用します。このパラメーターを設定する必要はありません。 | はい。詳細については、「ALTER TABLE」をご参照ください。 | |||
dictionary_encoding_columns
このプロパティは、ディクショナリエンコーディングを有効にする列を指定します。ディクショナリエンコーディングは、列の値をディクショナリにマッピングし、文字列比較を数値比較に変換することで、GROUP BY およびフィルター操作を高速化します。デフォルトでは、カラムストアテーブルのすべての TEXT 列でディクショナリエンコーディングが有効になっています。Hologres V0.9 以降では、データ特性に基づいてディクショナリエンコーディングが自動的に適用されます。
CALL set_table_property('table_name', 'dictionary_encoding_columns', '[columnName{:[on|off|auto]}[,...]]');time_to_live_in_seconds
このプロパティは、テーブル内のデータの生存期間 (TTL) を指定します。単位:秒。構文は次のとおりです。
TTL は、データが更新された時間ではなく、データが書き込まれた時間から計算されます。このプロパティを設定しない場合、デフォルトの TTL は 100 年です。Hologres V1.3.24 以降では、最小 TTL は 1 日 (86,400 秒) です。使用方法の詳細については、「SQL コマンドリファレンス」をご参照ください。
TTL は正確ではありません。期限切れのデータは特定の時点ではなく、ある時間範囲内で削除されます。これにより、プライマリキーの重複やクエリ結果の不整合などの問題が発生する可能性があります。
CALL set_table_property('table_name', 'time_to_live_in_seconds', '<non_negative_literal>');シナリオ例
例:データタイムスタンプによるパーティションテーブル
シナリオ説明: ビジネスの成長に伴い、1 日の注文量が数千万、さらには数億に達することがあります。「クイックスタート」セクションの単一テーブル構造 (dwd_trade_orders) を使用すると、履歴データのクリーンアップなどの大規模なデータ削除や、日付指定のクエリ実行時にシステム負荷が高くなる可能性があります。この例では、標準テーブルをパーティションテーブルにアップグレードする方法を示します。パーティションテーブルは、基本テーブルのすべてのフィールド定義とインデックス設定を継承しますが、PARTITION BY 句を使用してデータを日ごとに物理的に分離します。これにより、DROP TABLE 文を使用して期限切れのパーティションを数秒でクリーンアップでき、クエリ時に正確なパーティションプルーニングが可能になります。これは、本番環境で超大規模なリアルタイムデータを管理するための推奨アプローチです。
BEGIN;
-- アップグレード版: 親パーティションテーブルの作成
-- 構造はクイックスタートの例を完全に継承するが、プライマリキーにはパーティションキー dt を含める必要がある
CREATE TABLE IF NOT EXISTS public.dwd_trade_orders_partitioned (
order_id BIGINT NOT NULL,
shop_id INT NOT NULL,
user_id TEXT NOT NULL,
order_amount NUMERIC(12, 2) DEFAULT 0.00,
payment NUMERIC(12, 2) DEFAULT 0.00,
payment_type INT DEFAULT 0,
is_delivered BOOLEAN DEFAULT false,
dt TEXT NOT NULL, -- パーティションキー
order_time TIMESTAMPTZ NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (order_id, dt) -- 複合プライマリキー: ビジネスプライマリキーとパーティションキーを含む
)
PARTITION BY LIST (dt) -- リストパーティションを有効化
WITH (
orientation = 'column',
distribution_key = 'order_id',
event_time_column = 'order_time',
clustering_key = 'order_time:asc'
);
COMMIT;
-- 1. 子テーブルの作成: 特定の日付の物理ストレージ領域を割り当てる
CREATE TABLE IF NOT EXISTS public.dwd_trade_orders_20231101
PARTITION OF public.dwd_trade_orders_partitioned FOR VALUES IN ('20231101');
-- 2. データの挿入: アプリケーションロジックは基本テーブルと同じ。データは自動的に 20231101 の子テーブルにルーティングされる
INSERT INTO public.dwd_trade_orders_partitioned (order_id, shop_id, user_id, order_amount, payment, payment_type, is_delivered, dt, order_time) VALUES
(50001, 101, 'U678', 299.00, 280.00, 1, true, '20231101', '2023-11-01 10:00:01+08'),
(50002, 102, 'U992', 59.00, 59.00, 2, false, '20231101', '2023-11-01 10:05:12+08'),
(50003, 101, 'U441', 150.00, 145.00, 1, true, '20231101', '2023-11-01 10:10:45+08'),
(50004, 105, 'U219', 888.00, 888.00, 3, true, '20231101', '2023-11-01 10:20:11+08'),
(50005, 102, 'U883', 35.00, 30.00, 1, false, '20231101', '2023-11-01 10:32:00+08'),
(50006, 110, 'U007', 120.50, 120.50, 2, true, '20231101', '2023-11-01 10:45:33+08'),
(50007, 101, 'U321', 210.00, 210.00, 1, true, '20231101', '2023-11-01 11:02:19+08'),
(50008, 108, 'U556', 45.00, 45.00, 2, false, '20231101', '2023-11-01 11:15:04+08'),
(50009, 101, 'U112', 300.00, 290.00, 3, true, '20231101', '2023-11-01 11:25:55+08'),
(50010, 105, 'U449', 99.90, 99.90, 1, true, '20231101', '2023-11-01 11:40:22+08');
-- 3. パーティションプルーニング: dt 条件でクエリを実行すると、システムは関連する子テーブルのみをスキャンし、フルテーブルスキャンを回避する
SELECT COUNT(*) FROM public.dwd_trade_orders_partitioned WHERE dt = '20231101';
-- 4. 高速クリーンアップ: 期限切れのデータを削除するには、子テーブルを直接ドロップして即座に領域を解放する
-- DROP TABLE public.dwd_trade_orders_20231101; 例:大量データのリアルタイム分析 (ファクトテーブル)
シナリオ説明: このタイプのテーブルは、リアルタイムのダッシュボード集計に使用されます。これらのテーブルは通常、大量のデータを保持します。中核となる要件は、商品総流通額 (GMV) や注文量などの高性能な統計集計を実現することです。
BEGIN;
-- public スキーマを明示的に指定
CREATE TABLE IF NOT EXISTS public.dwd_order_summary (
order_id BIGINT PRIMARY KEY,
category_id INT NOT NULL,
gmv NUMERIC(15, 2),
order_time TIMESTAMPTZ NOT NULL
) WITH (
orientation = 'column', -- ストレージフォーマット: カラムストア。大量集計分析に最適で、高い圧縮率と効率的なカラムスキャンを提供
distribution_key = 'order_id', -- ディストリビューションキー: order_id でデータをシャーディングして均等な分散を保証。他の注文テーブルと結合する際に Local Join を有効化
event_time_column = 'order_time', -- セグメントキー: 通常は時間フィールドに設定。システムはこのフィールドでファイルをセグメント化し、時間範囲のフィルタリングを高速化
clustering_key = 'order_time:asc' -- クラスタリングキー: データを時間昇順で物理的にソート。「直近 1 時間」や「特定の日」のデータをクエリする際のディスク I/O を削減
);
-- 将来のデータガバナンスをサポートするためにメタデータコメントを追加
COMMENT ON TABLE public.dwd_order_summary IS '注文概要ファクトテーブル';
COMMENT ON COLUMN public.dwd_order_summary.order_id IS '一意の注文 ID';
COMMENT ON COLUMN public.dwd_order_summary.category_id IS 'カテゴリ ID';
COMMENT ON COLUMN public.dwd_order_summary.gmv IS '商品総流通額';
COMMENT ON COLUMN public.dwd_order_summary.order_time IS '注文時間';
COMMIT;例:プライマリキーによる高並行ポイントルックアップ (ディメンションテーブル)
シナリオ説明: このタイプのテーブルは、user_id によってユーザーペルソナをミリ秒単位で取得するために使用されます。これらのテーブルは、高い QPS (queries per second) の下で超低レイテンシーの応答を提供するように設計されています。
BEGIN;
-- public スキーマを明示的に指定
CREATE TABLE IF NOT EXISTS public.dim_user_persona (
user_id TEXT PRIMARY KEY, -- プライマリキー: ポイントルックアップシナリオに不可欠
user_level INT,
persona_jsonb JSONB
) WITH (
orientation = 'row' -- ストレージフォーマット: ローストア。プライマリキーによるポイントルックアップ (Point Lookup) に特化して最適化されており、ミリ秒単位の応答時間を実現
-- 注意: ローストアテーブルは自動的にプライマリキーをディストリビューションキーとクラスタリングキーとして使用するため、追加の設定は不要です。
);
-- メタデータコメントの追加
COMMENT ON TABLE public.dim_user_persona IS 'ユーザーペルソナディメンションテーブル';
COMMENT ON COLUMN public.dim_user_persona.user_id IS '一意のユーザー ID';
COMMENT ON COLUMN public.dim_user_persona.user_level IS 'ユーザーレベル';
COMMENT ON COLUMN public.dim_user_persona.persona_jsonb IS 'JSON 形式のユーザープロファイル特徴';
COMMIT;
例:混合ワークロード (ハイブリッドストレージ)
シナリオ説明: このタイプのテーブルは、物流アフターサービスシステムで使用されます。これらのシステムでは、物流ステータスの分析集計と、注文 ID による物流詳細の即時取得の両方が必要です。
BEGIN;
-- public スキーマを明示的に指定
CREATE TABLE IF NOT EXISTS public.ads_shipping_info (
order_id BIGINT PRIMARY KEY,
shipping_status INT,
receiver_address TEXT,
update_time TIMESTAMPTZ
) WITH (
orientation = 'row,column', -- ストレージフォーマット: ハイブリッド。ミリ秒単位のポイントルックアップ (ローストア) と効率的な集計分析 (カラムストア) を組み合わせる
distribution_key = 'order_id', -- ディストリビューションキー: shard 間でのデータ分散ロジックを決定
bitmap_columns = 'shipping_status' -- ビットマップインデックス: ステータスフィールドのような低カーディナリティの列に設定し、「ステータスフィルター」クエリを大幅に高速化
);
-- メタデータコメントの追加
COMMENT ON TABLE public.ads_shipping_info IS '物流ステータス照会アプリケーションテーブル';
COMMENT ON COLUMN public.ads_shipping_info.order_id IS '注文 ID';
COMMENT ON COLUMN public.ads_shipping_info.shipping_status IS '物流ステータス (1: 出荷待ち, 2: 輸送中, 3: 配達済み)';
COMMENT ON COLUMN public.ads_shipping_info.receiver_address IS '配送先住所';
COMMIT;
制限事項
プライマリキーの制限
複合プライマリキー:複数のフィールドをプライマリキーとして設定できます。すべてのフィールドは
NOT NULLでなければならず、単一のステートメントで定義する必要があります。BEGIN; CREATE TABLE public.test ( "id" text NOT NULL, "ds" text NOT NULL, PRIMARY KEY (id,ds) ); CALL SET_TABLE_PROPERTY('public.test', 'orientation', 'column'); COMMIT;型に関する制限:Float、Double、Numeric、Array、JSON、Date などの複雑なデータ型はサポートされていません。
変更に関する制限:プライマリキーは変更できません。プライマリキーを変更するには、テーブルを再作成する必要があります。
ストレージへの依存:ローストアテーブルとハイブリッドの行列表はプライマリキーを持つ必要があります。カラムストアテーブルはプライマリキーを必要としません。
制約のサポート
パラメーター | column_constraints | table_constraints |
primary key | サポート | サポート |
not null | サポート | - |
null | サポート | - |
unique | 非サポート | 非サポート |
check | 非サポート | 非サポート |
default | サポート | 非サポート |
キーワード、大文字/小文字の区別、エスケープの制限
命名規則:列名は
hg_で始めることはできません。スキーマ名はholo_、hg_、またはpg_で始めることはできません。エスケープ要件:キーワード、予約語、システムフィールド (例:
ctid)、大文字と小文字を区別する名前、特殊文字、数字で始まる名前は、二重引用符 ("") で囲む必要があります。V2.0 での構文の改善:
レガシー構文を有効にする:
-- セッションレベルでレガシー構文を有効にする set hg_disable_parse_holo_property = on; -- データベースレベルでレガシー構文を有効にする alter database <db_name> set hg_disable_parse_holo_property = on;エスケープされた列のプロパティ設定例:
create table "TBL" (a int); select relname from pg_class where relname = 'TBL'; insert into "TBL" values (-1977); select * from "TBL"; ------------------------------------------------------------------ -- Hologres V2.0 以降のエスケープされた列に対するテーブルプロパティ設定構文 begin; create table tbl (c1 int not null); call set_table_property('tbl', 'clustering_key', '"c1":asc'); commit; -- Hologres V2.0 以前のエスケープされた列に対するテーブルプロパティ設定構文 begin; create table tbl (c1 int not null); call set_table_property('tbl', 'clustering_key', '"c1:asc"'); commit; ------------------------------------------------------------------ -- Hologres V2.1 以降の複数列プロパティ (大文字を含む) の設定構文 begin; create table tbl ("C1" int not null, c2 text not null) with (clustering_key = '"C1",c2'); commit; -- Hologres V2.0 以降の複数列プロパティ (大文字を含む) の設定構文 begin; create table tbl ("C1" int not null, c2 text not null); call set_table_property('tbl', 'clustering_key', '"C1",c2'); commit; -- Hologres V2.0 以前の複数列プロパティ (大文字を含む) の設定構文 begin; create table tbl ("C1" int not null, c2 text not null); call set_table_property('tbl', 'clustering_key', '"C1,c2"'); commit; ------------------------------------------------------------------ create table "Tab_$A%*" (a int); select relname from pg_class where relname = 'Tab_$A%*'; insert into "Tab_$A%*" values (-1977); select * from "Tab_$A%*"; ------------------------------------------------------------------ create table tbl ("2c" int not null); insert into tbl values (3), (4); select "2c" from tbl;
テーブル作成ロジックの制限
設定 | IF NOT EXISTS を指定 | IF NOT EXISTS を指定しない |
同名のテーブルが存在する | NOTICE が表示され、操作はスキップされ、成功ステータスが返されます。 | ERROR メッセージが返されます。 |
同名のテーブルが存在しない | ステートメントは正常に実行されます。 | 成功応答 |
変更の制限
長さの制限:テーブル名は 127 バイトを超えることはできません。
以下の項目は変更できません:
データ型は変更できません。
列の順序は変更できません。
NULL 値許容制約は変更できません。例えば、
not nullとnullableを切り替えることはできません。ストレージレイアウトプロパティ:テーブル作成後、
orientation、distribution_key、clustering_key、またはevent_time_columnプロパティは変更できません。
サポートされる変更:テーブル作成後に
bitmap_columnsおよびdictionary_encoding_columnsプロパティは変更できます。