表階層

Oracle NoSQL Databaseでは、表を親子関係にすることができます。これを表階層といいます。

CREATE TABLE文を使用すると、表を別の表の子として作成でき、その別の表が新しい表の親になります。これは、子表のコンポジット名(name_path)を使用して実行します。コンポジット名は、ドットで区切られたN個(N > 1)の識別子で構成されます。最後の識別子は子表のローカル名であり、最初のN-1個の識別子は親の名前です。

セマンティクス

親子関係の意味は次のとおりです。
  • 子表は、親表の主キー列を継承します。これは暗黙的に行われ、子のCREATE TABLE文に親列が含まれることはありません。たとえば、次の例5-8では、表A.Bにidaという追加の列があり、主キー列はidaおよびidbです。同様に、表A.B.Cには2つの追加の列(idaとidb)があり、主キー列はida、idbおよびidcです。継承された列は、最初に子表のスキーマに配置されます。
  • 階層内のすべての表には同じシャード・キー列があり、これらはルート表のCREATE TABLE文に指定されています。したがって、この例では、共通のシャード・キーは列idaです。ルート以外の表のCREATE TABLE文にshard key句を含めると、エラーが発生します。
  • 子が削除される前に親表を削除することはできません。
  • 子表Cとその親表Pの2つの行RCおよびRPそれぞれにおいて、共通の主キー列に同じ値がある場合、RPとRCは一致している、またはRPにRCが含まれているといいます。この場合、RPおよびRCには同じシャード・キーがあるため、これらの行は物理的にも同じ場所に配置されます。子表の主キー列が常に親表よりも多い場合は、親行に複数の子行が含まれる可能性がありますが、子行は最大で1つの親行と一致します。

ノート:

Oracle NoSQL Databaseでは、子表のすべての行が、親表に一致する行を持つ必要はありません。つまり、参照整合性制約は適用されません。

Oracle NoSQL Databaseモデルに配列およびマップが含まれる場合、子表がなぜ必要になるのか不思議に思われるかもしれません。結局のところ、親行ごとに、一致する子行を配列またはマップ内の親行自体に格納できます。ただし、このようにすると、親行が非常に大きくなり、パフォーマンスが低下する可能性があります。これは、Oracle NoSQL Databaseストアの追加のみのアーキテクチャの場合に特に当てはまり、行が更新されるたびに新しいバージョンの行全体が作成されます。したがって、子表は、各親行に多数の子行が含まれるとき、または子行が大きいときに考慮する必要があります。また、子行がそれほど頻繁にアクセスされない場合や、頻繁に更新される場合は、子表を使用するほうが魅力的になります。

例5-8 表階層

次の文は、親子関係で接続された表のツリーである表階層を作成します。Aはルート表、A.BおよびA.GはAの子、A.B.CはA.Bの子(およびAの孫)です。

CREATE TABLE A (
       ida INTEGER, a1 STRING, a2 INTEGER, PRIMARY KEY(ida));
CREATE TABLE A.B (
        idb INTEGER, b1 STRING, a2 STRING, PRIMARY KEY(idb));
CREATE TABLE A.B.C (
        idc INTEGER, b1 STRING, c2 STRING, PRIMARY KEY(idc));
CREATE TABLE A.G (
        idg INTEGER, g1 STRING, g2 DOUBLE, PRIMARY KEY(idg));

複数リージョン表での表階層:

既存の複数リージョン・アーキテクチャで子表を作成できます。たとえば、FRAおよびLONという2つのリージョンにusersという表を作成します。
CREATE TABLE users (
     id INTEGER,
     name STRING,
     team STRING,
     PRIMARY KEY (id))
   IN REGIONS FRA,LON;
users表の下に、この文を使用して子テーブルを作成できます。
CREATE TABLE users.userdet (
       pan INTEGER,
       address STRING,
       email STRING,
       PRIMARY KEY(pan));
複数リージョン子表の作成中にREGIONS句を指定すると、次に示すようにエラーが発生します。
REATE TABLE users.userinfo (pan INTEGER, address STRING, email STRING,  PRIMARY KEY(pan)
    IN REGIONS FRA,LON) ;

Error handling command CREATE TABLE users.userinfo (
       pan INTEGER,
       address STRING,
       email STRING,
       PRIMARY KEY(pan) IN REGIONS FRA,LON): Error: at (5, 24) missing ')' at 'IN', at line 5:24
       rule stack: [parse, statement, create_table_statement]
次に示すように、複数リージョン子表の説明を表示できます。なお、子表は、その親表の主キー列を自動的に継承します。
sql-> desc as json table users.userdet;
{
  "json_version" : 1,
  "type" : "table",
  "name" : "userdet",
  "parent" : "users",
  "regions" : {
    "2" : "FRA",
    "1" : "LON"
  },
  "fields" : [{
    "name" : "id",
    "type" : "INTEGER",
    "nullable" : false
  }, {
    "name" : "pan",
    "type" : "INTEGER",
    "nullable" : false
  }, {
    "name" : "address",
    "type" : "STRING",
    "nullable" : true
  }, {
    "name" : "email",
    "type" : "STRING",
    "nullable" : true
  }],
  "primaryKey" : ["id", "pan"],
  "shardKey" : ["id"]
}