10 データベースへのアプリケーション・データ使用状況の登録
この章では、アプリケーション・データ使用状況のドメインおよび注釈と呼ばれる集中管理型のデータベース中心エンティティを使用して、アプリケーション・データの用途に関する情報を登録する方法について説明します。
Oracle Database 23cでは、データの用途情報を処理するためにアプリケーション使用状況ドメインと注釈を使用する、集中管理型のデータベース中心アプローチが導入されています。使用状況ドメインと注釈を一元的にデータベースに追加して、データの用途が登録されていると、様々なアプリケーションとツールからアクセスできるようになります。
関連項目:
-
アプリケーション使用状況ドメインとアプリケーション使用状況の注釈の詳細は、『Oracle Database概要』を参照してください。
-
使用状況のドメインと注釈に関する構文およびセマンティックの詳細は、『Oracle Database SQL言語リファレンス』を参照してください。
セクション:
10.1 アプリケーション使用状況ドメイン
この項では、アプリケーションでアプリケーション使用状況ドメイン(以下、「使用状況ドメイン」)を使用する方法について説明します。
10.1.1 使用状況ドメインの概要
使用状況ドメインは、軽量な使用状況指定子で、オプションでデータベース側に適用されます。この指定子は、アプリケーションが対象データの使用状況を一元的に文書化するために使用できます。高レベルのディクショナリ・オブジェクトとして、使用状況ドメインには、表列に関連付けられた組込みの使用状況プロパティ(デフォルト値、チェック制約、照合、表示書式や順序書式、注釈など)が含まれています。一元化したドメイン情報により、アプリケーションはアプリケーションレベルのメタデータに依存することなく操作を標準化できます。たとえば、使用状況ドメインは、クレジット・カード番号のマスクや、電話番号と通貨値の書式設定に使用できます。
データベース・オブジェクトとして、使用状況ドメインはスキーマに属し、基礎となる列データ型を変更することなく共通の列定義を提供します。使用状況ドメインは、表列のいくつかの共通する特性を再利用可能なオブジェクトにカプセル化します。このオブジェクトは、そうした特性を繰り返すことなく別の表列で再利用できます。
たとえば、スキーマには請求Eメール、伝票Eメール、顧客担当者EメールなどのEメール・アドレスを保持する列がある多数の表が含まれていることがあります。電子メール・アドレスは、"@"記号を必要とする特別な形式を持ちます。電子メール・アドレス用の使用状況ドメインは、regexp_like (email_dom, '^(\S+)\@(\S+)\.(\S+)$')
などのチェック制約を使用して定義できます。このドメインを別の電子メールの列に関連付けることで、アプリケーションは関連付けられた列の電子メール・アドレスをドメイン名の前に"@"記号が付いた標準形式で表示できます。同様に、自動車のライセンス・プレートの表示形式を標準化することもできます。この形式には、番号とその他の情報を分離するハイフンが必要になることがあります。使用状況ドメインを使用すると、このライセンス情報は、ライセンス列のデータ型がvarchar2(6)の場合でも"ABC-123"の形式で表示できます。
使用状況ドメインを使用する利点は、アプリケーション全体で一貫した値の処理ができることと、アプリケーション全体で列のプロパティと制約を再利用できるためにコーディングが削減されることです。また、アプリケーションが操作対象データを理解するために該当する使用状況ドメインについて問い合せることができることから操作の一貫性と明確さを確保できます。
関連項目:
アプリケーション使用状況ドメインの詳細は、『Oracle Database概要』を参照してください
10.1.2 使用状況ドメインのタイプと使用する局面
ドメインのタイプには、単一列ドメイン、複数列ドメインおよびフレキシブル・ドメインの3種類があります。
単一列使用状況ドメイン
単一列使用状況ドメインは1つの列に対して作成され、アプリケーション全体で列の使用状況定義を一貫させる場合に使用します。たとえば、単一列ドメインは電子メール・アドレス用、郵便番号用、または車両番号用に作成できます。
複数列またはフレキシブルという接頭辞が付いていない場合、このドキュメントでは、「使用状況ドメイン」または「ドメイン」は単一列使用状況ドメインを意味します。
複数列使用状況ドメイン
複数列使用状況ドメインでは、1つのドメインで複数の列の列使用状況定義を作成します。複数列使用状況ドメインは、複数の表列にまたがる論理エンティティがある場合に理想的です。たとえば、複数列使用状況ドメインは、住所を表すために使用できます。
フレキシブル使用状況ドメイン
フレキシブル使用状況ドメインは、判別式列の値に基づいて単一列または複数列の使用状況ドメインのセットから動的に選択するドメインです。フレキシブル・ドメインは、1つ以上の判別式列で構成されるマッピング式に基づいて、特定のドメイン(構成要素ドメインとも呼ばれる)を値列のセットに割り当てます。
これらの使用状況ドメインのタイプに加えて、表列に対する組込みの使用状況ドメインを直接使用することもできます。例として、email_d、ssn_dおよびcredit_card_number_dが挙げられます。
関連項目:
-
アプリケーション使用状況ドメインのタイプの詳細は、『Oracle Database概要』を参照してください
10.1.3 使用状況ドメインに必要な権限
使用状況ドメインを操作するには、次の権限が必要です。
ノート:
データベース管理者(DBA)ロールには、次のすべての権限が含まれています。
DDL権限 | アクション |
---|---|
CREATE DOMAIN |
自分のスキーマ内にドメインを作成できます。 RESOURCEロールとDB_DEVELOPER_ROLEロールには、CREATE DOMAIN権限が含まれています。 |
CREATE ANY DOMAIN |
任意のスキーマ内にドメインを作成できます。 |
ALTER ANY DOMAIN |
任意のスキーマ内のドメインを変更できます。 |
DROP ANY DOMAIN |
任意のスキーマ内のドメインを削除できます。 |
EXECUTE ANY DOMAIN |
任意のスキーマ内のドメインを使用および参照できます。 ユーザーに任意のスキーマ内のドメイン対する実行権限を明示的に付与するには、次のコードを使用します。
|
10.1.4 単一列使用状況ドメインの使用
この項では、単一列使用状況ドメイン(これ以降、「使用状況ドメイン」または「ドメイン」と表記)を作成、関連付け、変更、関連付け解除および削除する方法について説明します。
10.1.4.1 使用状況ドメインの作成
電子メール・アドレスやクレジット・カード番号など、共通の値を表すオプションのプロパティと制約のセットをカプセル化するために、使用状況ドメインを定義できます。
次に、いくつかの使用状況ドメインの作成例を示します。この例のドメインは、表列のプロパティ(デフォルト値、制約、注釈、表示と順序の式など)に基づいています。
例10-1 時給用の使用状況ドメインの作成
人材管理アプリケーション(HRA)では、それぞれの会社ごとに多数の表を作成します。ほとんどの会社には、時給を格納する列があります。HRAでは、次のようにして時給列用の使用状況ドメインを作成できます。
CREATE DOMAIN HourlyWages AS NUMBER
DEFAULT ON NULL 15
CONSTRAINT MinimalWage CHECK (HourlyWages > = 7 AND HourlyWages <=1000) ENABLE
DISPLAY TO_CHAR(HourlyWages, '$999.99') ORDER ( -1*HourlyWages )
ANNOTATIONS (properties '{"Purpose": "Wages", "Applicability": "USA", "Industry": {"Sales", "Manufacturing"} }');
例10-2 サロゲート・キー用の使用状況ドメインの作成
データベース・アプリケーションでサロゲート・キー列に注釈を付けて、該当する列の標準メタデータを維持する場合は、次のようなドメインを作成します。
CREATE DOMAIN surrogate_id AS INTEGER
STRICT
NOT NULL
ANNOTATIONS ( primary_key, mandatory, operations '["insert", "delete"]' );
例10-3 生年月日用の使用状況ドメインの作成
次の使用状況ドメインでは、生年月日のすべての列が"日付のみ"であることを確実にして、年齢が年数で表示されるようにします。
CREATE DOMAIN birth_date AS DATE
CONSTRAINT birth_date_only_c check ( birth_date = trunc ( birth_date ) )
DISPLAY FLOOR ( months_between ( sysdate, birth_date ) / 12 ) || ' years'
ANNOTATIONS ( sensitive 'PII Data', operations '["insert", "update"]' );
例10-4 デフォルトの日時値用の使用状況ドメインの作成
日時値用の使用状況ドメインを作成することで、挿入が標準形式であることを確実にします。
CREATE DOMAIN insert_timestamp AS
TIMESTAMP WITH LOCAL TIME ZONE
DEFAULT ON NULL systimestamp;
例10-5 正の身長用の使用状況ドメインの作成
次の使用状況ドメインでは、個人の身長が正であることを確実にして、身長が降順にソートされます。
CREATE DOMAIN height AS NUMBER
CONSTRAINT positive_height_c CHECK ( value > 0 )
ORDER value * -1
ANNOTATIONS ( operations '["insert", "update"]' );
例10-6 正の体重用の使用状況ドメインの作成
次の使用状況ドメインでは、個人の体重が正であることを確実にします。
CREATE DOMAIN weight AS NUMBER
CONSTRAINT positive_weight_c CHECK ( value > 0 )
ANNOTATIONS ( operations '["insert", "update"]' );
例10-7 チェック制約が複数あるドメインの定義
次の例のように、複数のCHECK
制約がある電子メール・アドレス用の使用状況ドメインを定義できます。
CREATE SEQUENCE IF NOT EXISTS email_seq;
CREATE DOMAIN email AS VARCHAR2(100)
DEFAULT ON NULL email_seq.NEXTVAL || '@domain.com'
CONSTRAINT email_c CHECK (REGEXP_LIKE (email, '^(\S+)\@(\S+)\.(\S+)$'))
CONSTRAINT email_max_len_c CHECK (LENGTH(email) <=100) DEFERRABLE INITIALLY DEFERRED
DISPLAY '---' || SUBSTR(email, INSTR(email, '@') + 1);
両方の制約を満たすVARCHAR2(L [BYTE|CHAR])
データ型の任意の列をドメインに関連付けできます。INITIALLY DEFERRED
句により、制約email_max_len_c
の値の検証をコミット時まで延期します。
例10-8 JSONスキーマの検証
次の例のように、再利用可能なJSONスキーマ検証にもドメインが使用できます。
CREATE DOMAIN department_json_doc AS JSON
CONSTRAINT CHECK (
department_json_doc IS JSON VALIDATE USING '{
"type": "object",
"properties": {
"departmentName": { "type": "string" },
"employees": { "type": "array" }
},
"required" : [ "departmentName", "employees" ],
"additionalProperties": false
}' );
関連項目:
-
使用状況ドメインの作成に対する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: CREATE DOMAINを参照してください。
10.1.4.2 表作成時の使用状況ドメインと列の関連付け
使用状況ドメインの定義後に、そのドメインは表の作成時に新しい表列に関連付けることも、既存の表の既存の列に関連付けることもできます。使用状況ドメインを列に関連付けると、そのドメインのオプションのプロパティと制約が列に明示的に適用されます。
CREATE TABLE
DDLを使用すると、新しく作成した列に使用状況ドメインを関連付けることができます。次の例は、新しい表列に使用状況ドメインを関連付ける方法を示しています。次に示す各例は、前述の例で作成した使用状況ドメインを使用しています。
例10-9 表作成時のHourlyWages
使用状況ドメインの関連付け
HourlyWages
ドメインを使用すると、HRAは賃金列のドメイン特性が同じになる複数の表を作成できます。
CREATE TABLE employee (
name VARCHAR2(100),
id NUMBER,
wage NUMBER DOMAIN HourlyWages);
CREATE TABLE wage (
name VARCHAR2(100),
id NUMBER,
wage NUMBER DOMAIN HourlyWages,
gross_pay NUMBER,
deductions NUMBER,
net_pay NUMBER);
例10-10 表作成時のsurrogate_id
使用状況ドメインの関連付け
列にsurrogate_id
などの厳密な使用状況ドメインを関連付ける場合は、関連付けられる列のデータ型がドメインと同じであることを確認してください。厳密なドメインでは、列の長さ、スケールおよび精度がドメインと一致することも必要です。
次のコードは、NUMBER
データ型の列をINTEGER/NUMBER(*,0)
データ型のドメインにリンクしようとしているため、ORA-11517: the column data type does not match the domain column
で失敗します。
CREATE TABLE orders (
order_id NUMBER DOMAIN surrogate_id,
customer_id NUMBER,
order_datetime TIMESTAMP WITH LOCAL TIME ZONE
DEFAULT SYSTIMESTAMP);
この関連付けが機能するように、NUMBER(*,0)
列データ型を使用して、surrogate_id
使用状況ドメイン(INTEGER == NUMBER(*,0)
)に関連付けできます。
CREATE TABLE orders (
order_id NUMBER(*,0) DOMAIN surrogate_id,
customer_id NUMBER,
order_datetime TIMESTAMP WITH LOCAL TIME ZONE
DEFAULT SYSTIMESTAMP);
例10-11 表作成時のsurrogate_id
、birth_date
、height
およびweight
使用状況ドメインの関連付け
DOMAIN
キーワードはオプションです。次の例では、DOMAIN
キーワードなしで、birth_date
ドメインがdate_of_birth
列に関連付けられていることがわかります。この例は、精度とスケールに関して、ドメイン内のものよりも正確なデータ型を定義できることも示しています。height_in_cm
列とweight_in_kg
列には、NUMBER
としてのドメイン・データ型が関連付けられていますが、列データ型にはNUMBER(4,1)
などの精度およびスケール値があります。
CREATE TABLE people (
person_id DOMAIN surrogate_id
GENERATED BY DEFAULT AS IDENTITY
PRIMARY KEY,
full_name VARCHAR2(256),
date_of_birth birth_date,
height_in_cm NUMBER(4, 1) DOMAIN height,
weight_in_kg NUMBER(6, 3) DOMAIN weight);
例10-12 表作成時のdepartment_json_doc
使用状況ドメインの関連付け
CREATE TABLE departments (
department_id INTEGER PRIMARY KEY,
department_doc JSON DOMAIN department_json_doc);
ガイドライン
-
ドメインを列に関連付けるときには、列のデータ型に加えてドメイン名も指定できます。この場合は、ドメインのデータ型が列のデータ型と互換性があるときには、列のデータ型が使用されます。
-
ドメインを列に関連付けるときには、列のデータ型のかわりにドメイン名を指定できます。この場合は、ドメイン・データ型が列に使用されます。そのときには、
DOMAIN
キーワードがオプションになります。 -
ドメインが
STRICT
として定義されているときには、ドメインのデータ型、スケールおよび精度が列のデータ型、スケールおよび精度と一致する必要があります。 -
ドメインが
STRICT
として定義されていないときには、任意の長さの列に任意の長さのドメインを関連付けできます。たとえば、VARCHAR2(10)
のドメインは任意のVARCHAR2
列に関連付けできます。
関連項目:
-
使用状況ドメインの作成に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: CREATE DOMAINを参照してください
-
列とドメインのデータ型に関する詳細は、「ドメインのデータ型の指定」を参照してください
10.1.4.2.1 使用状況ドメインに関連付けられた列に対するDMLの使用
次に、使用状況ドメインが関連付けられた新しく作成する表列に使用できるDML文の例をいくつか示します。
例10-13 people
表に対するDML文の使用
次のINSERT
コマンドは、people
表の列にデータを挿入します。そのときに、関連付けられたドメインで指定されたチェック制約に違反していないことを確認します。
INSERT INTO people
VALUES ( 1, 'Sally Squirell', date'1981-01-01', 180.1, 61 );
INSERT INTO people
VALUES ( 2, 'Brian Badger', date'2016-12-31', 120.4, 27.181 );
次のINSERT
コマンドは、height
が負の数として指定されていることから、関連するチェック制約に違反するために失敗します。
INSERT INTO people
VALUES ( 3, 'Fergal Fox', date'2023-04-12', -99, 1 );
出力は次のとおりです。
ORA-11534: check constraint (HR.SYS_C009232) due to domain constraint HR.POSITIVE_HEIGHT_C of domain HR.HEIGHT violated
関連付けられたドメインを使用することで、身長が降順でソートされたデータを表示し、それに対応する年齢と体重も表示できます。
SELECT full_name, DOMAIN_DISPLAY ( date_of_birth ) age,
height_in_cm, weight_in_kg
FROM people
ORDER BY DOMAIN_ORDER ( height_in_cm );
関連項目:
DOMAIN_DISPLAY
やDOMAIN_ORDER
などのドメイン関数の詳細は、「ドメイン使用状況用のSQL関数」を参照してください。
出力は次のとおりです。
FULL_NAME AGE HEIGHT_IN_CM WEIGHT_IN_KG
-------------------- ---------- ------------ ------------
Sally Squirell 42 years 180.1 61
Brian Badger 6 years 120.4 27.181
people
表は、データ型定義と参照先ドメイン情報を確認するように記述できます。
DESC people;
出力は次のとおりです。
Name Null? Type
---------------------- -------- ----------------------------------------
PERSON_ID NOT NULL NUMBER(38) HR.SURROGATE_ID
FULL_NAME VARCHAR2(256)
DATE_OF_BIRTH DATE HR.BIRTH_DATE
HEIGHT_IN_CM NUMBER(4,1) HR.HEIGHT
WEIGHT_IN_KG NUMBER(6,3) HR.WEIGHT
次のSELECT
コマンドを使用すると、関連付けられたドメインから継承されている列の注釈を表示できます。
SELECT column_name, annotation_name, annotation_value
FROM user_annotations_usage
WHERE object_name = 'PEOPLE';
出力は次のとおりです。
COLUMN_NAME ANNOTATION_NAME ANNOTATION_VALUE
-------------------- -------------------- --------------------
PERSON_ID PRIMARY_KEY <null>
PERSON_ID MANDATORY <null>
PERSON_ID OPERATIONS ["insert", "delete"]
DATE_OF_BIRTH OPERATIONS ["insert", "update"]
DATE_OF_BIRTH SENSITIVE PII Data
HEIGHT_IN_CM OPERATIONS ["insert", "update"]
WEIGHT_IN_KG OPERATIONS ["insert", "update"]
例10-14 JSONデータを使用したdepartments
表に対するDML文の使用
次のdepartments
表に対するINSERT
コマンドは、department_json_doc
ドメイン内のすべてのJSON属性が含まれているために成功します。
INSERT INTO departments
VALUES ( 1, '{
"departmentName" : "Accounting",
"employees" : [
{"empName":"William"},
{"empName":"Shelley"}
]
}');
次のINSERT
コマンドは、employees
属性がないために、ORA-40875: JSON schema validation error - missing employees attribute
で失敗します。
INSERT INTO departments
VALUES ( 2, '{
"departmentName" : "Finance"
}');
次のINSERT
コマンドは、関連付けられたdepartment_json_doc
使用状況ドメイン内にmanager
属性が見つからないために、ORA-40875: JSON schema validation error - extra manager attribute
で失敗します。
INSERT INTO departments
VALUES ( 3, '{
"departmentName" : "Executive",
"employees" : [
{"empName":"Lex"},
{"empName":"Neena"}
],
"manager" : {"empName":"Lex"}
}');
10.1.4.3 使用状況ドメインと既存または新規の列の関連付け
ALTER TABLE
DDLは、MODIFY
句またはADD
句とともに使用することで、既存の列または新規に追加された列に使用状況ドメインを関連付けることができます。
例10-15 新規作成された列への使用状況ドメインの関連付け
新規作成されたcustomers
表の場合:
CREATE TABLE customers (
cust_id NUMBER,
cust_email VARCHAR2(100));
ADD
を使用することで、新しい列のcust_new_email
を追加して、その列にemail
ドメインを関連付けできます。
ALTER TABLE customers
ADD (cust_new_email VARCHAR2(100) DOMAIN email);
例10-16 email使用状況ドメインと既存の列の関連付け
MODIFY
を使用することで、既存の列のcust_email
を変更して、その列にemail
ドメインを関連付けできます。
ALTER TABLE customers
MODIFY (cust_email VARCHAR2(100) DOMAIN email);
また、ALTER TABLE ... MODIFY
文を使用して、列に使用状況ドメインを追加することもできます。次の例では、orders
表の列であるorder_datetime
と、insert_timestamp
ドメインのデフォルトが異なっています。insert_timestamp
ドメインには、DEFAULT
がありON NULL
句が指定されていますが、order_datetime
列にはありません。そのため、列にドメインを関連付けようとすると、エラーORA-11501: The column default does not match the domain default of the column
が発生します。
ALTER TABLE orders
MODIFY order_datetime DOMAIN insert_timestamp;
このデフォルトの不一致を解決するために、ドメインのデフォルトと一致する列のdefault句を指定します。
ALTER TABLE orders
MODIFY order_datetime DOMAIN insert_timestamp
DEFAULT ON NULL systimestamp;
例10-17 関連付けられているドメインを表示するための問合せ
SELECT constraint_name, search_condition_vc, domain_constraint_name
FROM user_constraints
JOIN user_cons_columns
USING ( constraint_name, table_name )
WHERE table_name = 'PEOPLE'
AND constraint_type = 'C'
AND column_name = 'WEIGHT_IN_KG';
出力は次のとおりです。
CONSTRAINT_NAME SEARCH_CONDITION_VC DOMAIN_CONSTRAINT_NAME
-------------------- ------------------------------ --------------------------
SYS_C008493 "WEIGHT_IN_KG">0 POSITIVE_WEIGHT_C
ガイドライン
-
ALTER TABLE .. ADD
文のDOMAIN
キーワードは、新しく追加した列にドメインのみを指定する際のオプションです。 -
ALTER TABLE .. MODIFY
文には、DOMAIN
キーワードが必須になります。 -
列のデータ型には、ドメインのデータ型との互換性があることが必要です。
-
ドメインにデフォルトの式または照合がある場合は、関連付けられた列のデフォルトの式および照合と一致している必要があります。
-
関連付けられる列にすでにドメインが関連付けられている場合は、エラーが返されます。
10.1.4.4 使用状況ドメインの変更
使用状況ドメインの表示式、順序式および注釈は変更可能です。サポートされているALTER DOMAIN
DDL文は、次のとおりです。
例10-18 ドメインからの順序式の削除
height
使用状況ドメイン定義にはVALUE
という順序式があるため、順序式を削除するために、順序式をドロップする必要があります。
ALTER DOMAIN height DROP ORDER;
例10-19 使用状況ドメインへの表示式の追加
height
使用状況ドメインに表示式を追加するには、次のALTER
コマンドを使用します。
ALTER DOMAIN height
ADD DISPLAY round ( value ) || ' cm';
例10-20 birth_date
ドメインの表示式の変更
birth_date
ドメインの表示式を年数と月数に変更するには、次のALTER
コマンドを使用します。
ALTER DOMAIN birth_date
MODIFY DISPLAY
FLOOR ( months_between ( sysdate, birth_date ) / 12 ) || ' years ' ||
MOD ( FLOOR ( months_between ( sysdate, birth_date ) ), 12 ) || ' months';
例10-21 変更したbirth_date
、height
およびweight
ドメインについてのpeople
表の問合せ
COLUMN age FORMAT A20
SELECT full_name, DOMAIN_DISPLAY ( date_of_birth ) age,
DOMAIN_DISPLAY ( height_in_cm ) height_in_cm, weight_in_kg
FROM people
ORDER BY DOMAIN_ORDER ( height_in_cm );
関連項目:
DOMAIN_DISPLAY
やDOMAIN_ORDER
などのドメイン関数の詳細は、「ドメイン使用状況用のSQL関数」を参照してください。
出力は次のとおりです。
FULL_NAME AGE HEIGHT_IN_CM WEIGHT_IN_KG
-------------------- -------------------- ------------- ------------
Sally Squirell 42 years 5 months 180 cm 61
Brian Badger 6 years 5 months 120 cm 27.181
例10-22 使用状況ドメインの注釈の変更
次のコードでは、height
使用状況ドメインの注釈を追加します。
ALTER DOMAIN height
ANNOTATIONS (
operations '["insert", "update", "sort"]',
sensitive 'Private data');
例10-23 注釈の変更についてのディクショナリ・ビューの問合せ
COLUMN annotation_value FORMAT A40
SELECT column_name, annotation_name, annotation_value
FROM user_annotations_usage
WHERE object_name = 'PEOPLE';
出力は次のとおりです。
COLUMN_NAME ANNOTATION_NAME ANNOTATION_VALUE
-------------------- -------------------- ----------------------------------------
PERSON_ID PRIMARY_KEY <null>
PERSON_ID MANDATORY <null>
PERSON_ID OPERATIONS ["insert", "delete"]
DATE_OF_BIRTH SENSITIVE PII Data
DATE_OF_BIRTH OPERATIONS ["insert", "update"]
HEIGHT_IN_CM OPERATIONS ["insert", "update"]
HEIGHT_IN_CM OPERATIONS ["insert", "update", "sort"]
HEIGHT_IN_CM SENSITIVE Private data
WEIGHT_IN_KG OPERATIONS ["insert", "update"]
ガイドライン
-
ドメインの表示式は、そのドメインがフレキシブル・ドメインの構成要素でない場合にのみ変更できます。
-
ドメインの順序式は、そのドメインがフレキシブル・ドメインの構成要素でない場合にのみ変更できます。
-
ドメイン・レベルの注釈のみを変更できます。
関連項目:
-
使用状況ドメインの変更に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: ALTER DOMAINを参照してください。
-
使用状況ドメインのディクショナリ・ビューについては、「ドメイン情報の表示」を参照してください
10.1.4.5 列からの使用状況ドメインの関連付け解除
ALTER TABLE
DDLは、DROP
句とともに使用することで、列から使用状況ドメインの関連付けを解除できます。
例10-24 列からの使用状況ドメインの関連付け解除
customers
表のcust_email
列から関連付けられたドメインを削除するには:
ALTER TABLE customers MODIFY ( cust_email ) DROP DOMAIN;
ドメインを削除するが、ドメインの制約を維持するには:
ALTER TABLE customers MODIFY ( cust_email ) DROP DOMAIN PRESERVE CONSTRAINTS;
例10-25 列からの使用状況ドメインの関連付け解除
次のコードは、制約を維持しながら、people
表のheight_in_cm
列からheight
ドメインのドメイン関連付けを削除します。
ALTER TABLE people
MODIFY ( height_in_cm ) DROP DOMAIN PRESERVE CONSTRAINTS;
例10-26 使用状況ドメインの関連付けが解除された列の問合せ
user_constraints
ディクショナリ表に対するSELECT
問合せによって、変更内容が表示されます。
SELECT constraint_name, search_condition_vc, domain_constraint_name
FROM user_constraints
JOIN user_cons_columns
USING ( constraint_name, table_name )
WHERE table_name = 'PEOPLE'
AND constraint_type = 'C';
出力は次のとおりです。
CONSTRAINT_NAME SEARCH_CONDITION_VC DOMAIN_CONSTRAINT_NAME
-------------------- ---------------------------------------- ------------------------------
SYS_C009491 "DATE_OF_BIRTH"=TRUNC("DATE_OF_BIRTH") BIRTH_DATE_ONLY_C
SYS_C009494 "WEIGHT_IN_KG">0 POSITIVE_WEIGHT_C
SYS_C009489 "PERSON_ID" IS NOT NULL <null>
SYS_C009490 "HEIGHT_IN_CM">0 <null>
例10-27 削除したheight
ドメインの再追加
次のコードでは、削除したheight
ドメインをpeople
表のheight_in_cm
列に再追加します。
ALTER TABLE people
MODIFY ( height_in_cm ) ADD DOMAIN height;
例10-28 再追加したドメインの問合せ
再追加したheight
ドメインによって、重複するheight_in_cm > 0
制約が作成されます。
SELECT constraint_name, search_condition_vc, domain_constraint_name
FROM user_constraints
JOIN user_cons_columns
USING ( constraint_name, table_name )
WHERE table_name = 'PEOPLE'
AND constraint_type = 'C'
ORDER BY search_condition_vc;
出力は次のとおりです。
CONSTRAINT_NAME SEARCH_CONDITION_VC DOMAIN_CONSTRAINT_NAME
-------------------- ---------------------------------------- ------------------------------
SYS_C009491 "DATE_OF_BIRTH"=TRUNC("DATE_OF_BIRTH") BIRTH_DATE_ONLY_C
SYS_C009495 "HEIGHT_IN_CM">0 POSITIVE_HEIGHT_C
SYS_C009490 "HEIGHT_IN_CM">0 <null>
SYS_C009489 "PERSON_ID" IS NOT NULL <null>
SYS_C009494 "WEIGHT_IN_KG">0 POSITIVE_WEIGHT_C
ガイドライン
列のドメインを削除すると、デフォルトで次の項目が保持されます。
-
ドメインの照合。
-
列に追加されているドメイン以外の制約。
ドメインのデフォルト値は保持されません。デフォルトが明示的に列に適用されている場合にのみ保持されます。
関連項目:
-
使用状況ドメインの変更に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: ALTER DOMAINを参照してください。
-
使用状況ドメインのディクショナリ・ビューについては、「ドメイン情報の表示」を参照してください
10.1.4.6 使用状況ドメインの削除
使用状況ドメインは削除できます。ドメインの削除の詳細は、『Oracle Database SQL言語リファレンス』を参照してください。
例10-29 使用状況ドメインの削除
次のcustomers
表には、email
ドメインに関連付けられている列が1つあります。
CREATE TABLE customers ( cust_id NUMBER, cust_email VARCHAR2(100) DOMAIN email);
次のDROP
コマンドは、customers
表のcust_email
列にemail
ドメインが関連付けられているため、エラーを返します。
DROP DOMAIN email;
次のDROP
コマンドは成功します:
DROP DOMAIN email FORCE;
cust_email
列はemail
ドメインからの関連付けが解除され、email
ドメインにかかわる文のすべてが無効になります。
例10-30 制約が保持されるドメインの削除
次のDROP
コマンドは成功しますが、デフォルト式と制約式は保持されます。
DROP DOMAIN email FORCE PRESERVE;
cust_email
列にはON NULL email_seq.NEXTVAL || '@domain.com'
が維持され、制約は制約内のドメイン名を列名に置き換えた後に保持されます: CONSTRAINT email_c CHECK (REGEXP_LIKE (cust_email, '^(\S+)\@(\S+)\.(\S+)$'))
。
ガイドライン
-
フレキシブル・ドメインで参照されているドメインを削除する場合は、
FORCE
オプションを指定したDROP DOMAIN
を使用します。 -
ドメインが表列に関連付けられていないときに、ドメインがフレキシブル・ドメインの構成要素でない場合、ドメインは削除されます。使用状況ドメインが使用中の場合、
DROP
文は失敗します。 -
ドメインがいずれかの表列に関連付けられている場合は、ドメインの削除に
FORCE
オプションを使用する必要があります。FORCE
オプションを使用すると、次の作用が伴われます:-
ドメインのデフォルトのみが設定されている場合は、デフォルトの式が削除されます。
-
ドメインと列の両方にデフォルトが設定されている場合は、列のデフォルト式が保持されます。
-
すべての関連付けられた列からドメインの注釈が削除されます。
-
ドメインに関連付けられた列の照合が保持されます。
-
カーソル・キャッシュ内のすべてのSQL依存文が無効になります。
-
FORCE PRESERVE
が使用されている場合は、ドメインに関連付けられている列の制約が保持されます。
-
関連項目:
-
使用状況ドメインの削除に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: DROP DOMAINを参照してください。
10.1.4.6.1 ドメインの削除とごみ箱について
削除された表は、ごみ箱に配置されます。ごみ箱内の表に関連付けられているドメインを削除するには、DROP
コマンドにFORCE
オプションを指定する必要があります。
ごみ箱内にある削除した表は、FLASHBACK TABLE
コマンドを使用すると削除前の配置にリストアできます。関連付けられたドメインの削除後に、表が削除前の配置にリストア(FLASHBACK TABLE TO BEFORE DROP
)されると、その表には削除前のものと同じデフォルト、照合、NULL値可能性および制約が保持されています。ただし、そうした属性はいずれもドメインから継承されたものとしてのマークがありません。
例10-31 削除した表に関連付けられている使用状況ドメインの削除
次のDROP
コマンドでは、people
表のweight_in_kg
列に関連付けられているweight
ドメインの削除を試行します。
DROP DOMAIN weight;
このコマンドは次のエラー出力を返します:
ORA-11502: The domain WEIGHT to be dropped has dependent objects.
people
表を削除してからweightドメインを削除すると、その表がごみ箱に残っているため、エラーが返されます。
DROP TABLE people;
DROP DOMAIN weight;
このコマンドは次のエラー出力を返します:
ORA-11502: The domain WEIGHT to be dropped has dependent objects.
ごみ箱からpeople
表を完全に削除してから、weight
ドメインに対してDROP
コマンドを実行すると、weight
ドメインが削除されます。
PURGE TABLE people;
DROP DOMAIN weight;
ガイドライン
削除した表(ごみ箱内の表)に関連付けられているドメインを削除する際には、次の点に注意してください。
-
表がごみ箱にある間は、その表に対する
ALTER
コマンドは許可されません。 -
ごみ箱にドメインに関連付けられている表がある場合は、関連付けられたドメインは削除できず、
DROP DOMAIN
コマンドは失敗します。 -
DROP DOMAIN FORCE
コマンドとDROP DOMAIN FORCE PRESERVE
コマンドを使用すると、ごみ箱内の表のドメインからの関連付けが解除されます。データベースでは、FORCE
のみを指定した場合でも、ごみ箱内の表に対してはFORCE PRESERVE
セマンティクスが使用されます。 -
ごみ箱内の表に関連付けられているドメインを削除する場合は、ごみ箱から表を削除するために
PURGE TABLE
コマンドを使用し、ドメインを削除するためにDROP DOMAIN
コマンドを実行します。
10.1.5 複数列使用状況ドメインの使用
この項では、複数列使用状況ドメインを作成、関連付け、変更、関連付け解除および削除する方法について説明します。
10.1.5.1 複数列使用状況ドメインの作成
複数列使用状況ドメインを使用して、表の列にまたがる住所などの論理エンティティをグループ化できます。
例10-32 住所用の複数列使用状況ドメインの作成
住所エントリ用に3つの列が含まれている"US_city"という複数列使用状況ドメインは、次のように作成できます。
CREATE DOMAIN US_city AS (
name AS VARCHAR2(30) ANNOTATIONS (Address),
state AS VARCHAR2(2) ANNOTATIONS (Address),
zip AS NUMBER ANNOTATIONS (Address)
)
CONSTRAINT City_CK CHECK(state in ('CA','AZ','TX') and zip < 100000)
DISPLAY name||', '|| state ||', '||TO_CHAR(zip)
ORDER state||', '||TO_CHAR(zip)||', '||name
ANNOTATIONS (Title 'Domain Annotation');
例10-33 通貨用の複数列使用状況ドメインの作成
次のコードでは、貨幣価値を特定の通貨の金額として通貨コードと表示する、currency
という複数列使用状況ドメインを作成します。表示は値でソートされ(低から高)、その後で通貨コードでソートされます。
CREATE DOMAIN currency AS (
amount AS NUMBER,
iso_currency_code AS CHAR(3 CHAR)
)
DISPLAY iso_currency_code || TO_CHAR ( amount, '999,999,990.00' )
ORDER TO_CHAR ( amount, '999,999,990.00' ) || iso_currency_code;
ガイドライン
-
複数列使用状況ドメインの個別の列に、単一列使用状況ドメインと同じデータ型を設定できます。
-
複数列使用状況ドメインの場合、異なるドメイン間での列の重複は許容されません。たとえば、表T(TC1、TC2、TC3、TC4)、ドメインD1(C1、C2)およびD2(C1、C2)の場合は、D1(TC1、TC2)とD2(TC2、TC3)のような関連付けはできません。
-
同じ表内の列の複数の順序付きサブセットは、同じドメインに関連付けできます。たとえば、ドメインD1は、D1(TC1、TC2)とD1(TC3、TC4)のような関連付けができます。
-
表には最大で1つの
LONG
列を含めることができますが、ドメインには複数のLONG
データ型の列を含めることができます。そのようなドメインは、DOMAIN_CHECK
演算子を使用して複数のLONG
列が関与するチェック条件を評価する場合に役立ちます。
関連項目:
-
使用状況ドメインの作成に対する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: CREATE DOMAINを参照してください。
10.1.5.2 表作成時の複数列使用状況ドメインの関連付け
CREATE TABLE
DDL文を使用すると、新しく作成した列に複数列使用状況ドメインを関連付けることができます。
例10-34 US_city
ドメインと複数の列の関連付け
customer
表を作成して、その表の3つの列にUS_city
ドメインを関連付けることができます。
CREATE TABLE customer( cust_id NUMBER, cust_name VARCHAR2(30), city_name VARCHAR2(30), state VARCHAR2(2), zip NUMBER, DOMAIN US_city(city_name, state, zip));
次の例では、ドメイン間でCITY
列とSTATE
列が重複しているため、エラーが返されます。
CREATE TABLE customer( cust_id NUMBER, cust_name VARCHAR2(30), city_name VARCHAR2(30), state VARCHAR2(2), zip NUMBER, DOMAIN US_city(city_name, state, zip), DOMAIN US_city(cust_name, state, zip));
次の例では、CITY_NAME
列が繰り返されるため、同様にエラーが返されます。
CREATE TABLE customer( cust_id NUMBER, cust_name VARCHAR2(30), city_name VARCHAR2(30), state VARCHAR2(2), zip NUMBER, DOMAIN US_city(city_name, city_name, zip));
例10-35 currency
ドメインと複数の列の関連付け
currency
ドメインに関連付けられたtotal_paid
列とcurrency_code
列を保持するorder_items
表を作成できます。
CREATE TABLE order_items (
order_id INTEGER, product_id INTEGER,
total_paid NUMBER(10, 2), currency_code char (3 CHAR ),
DOMAIN currency ( total_paid, currency_code ));
ガイドライン
-
実際のパラメータとしてドメインに渡される列名は一意であることが必要です。
-
ドメイン列は、名前が異なる表列に関連付けできます。
-
DOMAIN
キーワードは必須です。
10.1.5.2.1 複数列ドメインに関連付けられた列に対するDMLの使用
次に、複数列使用状況ドメインが関連付けられた新しく作成する表列に使用できるDML文の例をいくつか示します。
例10-36 関連付けられた列に対するDMLコマンドの使用
値を挿入して表を問い合せると、currency
ドメインの表示式と順序式に基づいた結果が表示されます。
INSERT INTO order_items
VALUES (1, 1, 9.99, 'USD'),
(2, 2, 8.99, 'GBP'),
(3, 3, 8.99, 'EUR'),
(4, 4, 1399, 'JPY'),
(5, 5, 825, 'INR');
SELECT order_id, product_id,
DOMAIN_DISPLAY ( total_paid, currency_code ) amount_paid
FROM order_items
ORDER BY DOMAIN_ORDER ( total_paid, currency_code );
関連項目:
DOMAIN_DISPLAY
やDOMAIN_ORDER
などのドメイン関数の詳細は、「ドメイン使用状況用のSQL関数」を参照してください。
出力は次のとおりです。
ORDER_ID PRODUCT_ID AMOUNT_PAID
---------- ---------- ------------------
3 3 EUR 8.99
2 2 GBP 8.99
1 1 USD 9.99
5 5 INR 825.00
4 4 JPY 1,399.00
10.1.5.3 複数列使用状況ドメインの既存の列との関連付け
ALTER TABLE
DDL文は、MODIFY
句またはADD
句とともに使用することで、既存の列または既存の表に新しく追加された列に複数列使用状況ドメインを関連付けることができます。
例10-37 複数列使用状況ドメインの既存の列との関連付け
次の例では、US_city
ドメインをcustomer
表の3つの列に適用します。
ALTER TABLE customer MODIFY (city_name, state, zip) ADD DOMAIN US_city;
ノート:
ALTER TABLE .. MODIFY
文には、DOMAIN
キーワードが必須になります。
10.1.5.4 複数列使用状況ドメインの変更
単一列使用状況ドメインの変更と同様に、複数列使用状況ドメインも変更できます。複数列使用状況ドメインでは、DISPLAY
プロパティとORDER
プロパティを変更できます。複数列ドメインの場合、現在時点では列レベルでの注釈の変更はサポートされていませんが、オブジェクト・レベルの注釈は変更できます。
例10-38 複数列使用状況ドメインの表示式と順序式の変更
次のALTER
文では、currency
ドメインの表示式を変更します。現在の表示式では、通貨コードと通貨値が表示されます。変更した表示式では、通貨値の後に通貨コードが表示されます。
ALTER DOMAIN currency
MODIFY DISPLAY TO_CHAR ( amount, '999,990.00' ) || '-' || iso_currency_code;
次のALTER
文では、currency
ドメインの順序式を変更します。現在の順序式では、通貨値でソートされた後に通貨コードでソートされます。変更した順序式では、通貨コードでソートされた後に通貨値でソートされます。
ALTER DOMAIN currency
MODIFY ORDER iso_currency_code || TO_CHAR ( amount, '999,990.00' );
例10-39 変更した複数列ドメインに関連付けられた表の問合せ
SELECT order_id, product_id,
DOMAIN_DISPLAY ( total_paid, currency_code ) amount_paid
FROM order_items
ORDER BY DOMAIN_ORDER ( total_paid, currency_code );
出力は次のとおりです。
ORDER_ID PRODUCT_ID AMOUNT_PAID
----------- ------------- ---------------
3 3 8.99-EUR
2 2 8.99-GBP
5 5 825.00-INR
4 4 1,399.00-JPY
1 1 9.99-USD
関連項目:
-
使用状況ドメインの変更に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: ALTER DOMAINを参照してください。
10.1.5.5 列からの複数列使用状況ドメインの関連付け解除
ALTER TABLE
DDL文は、DROP
句とともに使用することで、列から複数列使用状況ドメインの関連付けを解除できます。
例10-40 複数列使用状況ドメインの関連付け解除の例
次のALTER TABLE
コマンドは、customer
表のcity_name
列、state
列およびzip
列からUS_City
ドメインを削除します。
ALTER TABLE customer
MODIFY(city_name, state, zip) DROP DOMAIN;
表Tの列(c1、c2、c3)がドメインDに関連付けられていて、その他の列セット(c4、c5、c6)もドメインDに関連付けられている場合は、すべての列のドメインを削除できます。
ALTER TABLE T
MODIFY (c1, c2, c6, c5, c4, c3) DROP DOMAIN;
複数列ドメインに関連付けられている列のサブセットのみを削除することはできません。たとえば、表Tの場合は、c1列とc2列のみを削除すると、エラーが返されます:
ALTER TABLE T
MODIFY (c1, c2) DROP DOMAIN;
例10-41 複数列使用状況ドメインの関連付け解除のその他の例
次のコードでは、order_items
表のtotal_paid
列とcurrency_code
列からcurrency
ドメインを削除します。
ALTER TABLE order_items
MODIFY ( total_paid, currency_code ) DROP DOMAIN;
ガイドライン
-
同じドメインに関連付けられている、同じ表内の列の複数の順序付きサブセットが存在していることがあります。複数列ドメインを削除する構文では、関連付けられた列のうち関連付けを解除する列のリストを指定する必要があります。
-
ドメイン名は指定できません。
-
ALTER TABLE ..DROP DOMAIN
のALTER TABLE ..MODIFY
には、その他のオプションを指定できません。
10.1.5.6 複数列使用状況ドメインの削除
複数列使用状況ドメインを削除する場合は、単一列使用状況ドメインに使用したものと同じ構文を使用します。
ガイドライン
-
フレキシブル・ドメインで参照されているドメインを削除する場合は、
FORCE
オプションを指定したDROP DOMAIN
を使用します。
関連項目:
-
使用状況ドメインの削除に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: DROP DOMAINを参照してください
-
使用状況ドメインの削除の詳細は、「使用状況ドメインの削除」を参照してください。
10.1.6 フレキシブル使用状況ドメインの使用
この項では、フレキシブル使用状況ドメインを作成、関連付け、関連付け解除および削除する方法について説明します。
ノート:
フレキシブル使用状況ドメインは変更できません。そのかわりに、表からフレキシブル・ドメインの関連付けを解除し、ドメインをDROP
し、ドメインを再作成して、表との関連付けを再実行することはできます。
10.1.6.1 フレキシブル使用状況ドメインの作成
フレキシブルでない別のドメイン(単一列および複数列の使用状況ドメイン)を参照するフレキシブル使用状況ドメインを作成し、それらのいずれかのドメインをデータのコンテキストに応じて表列に適用できます。たとえば、各国の住所の書式を検証するための複数列ドメインを作成できます。表列は1つのドメインにのみ属することが可能です。そのため、データベースで行ごとの各国に対応する住所ドメインを使用できるようにするには、国ドメインにわたるフレキシブル・ドメインを作成します。判別式の列として国を使用して、フレキシブル・ドメインに列を関連付けます。各行には、対応する国ドメインの住所ルールを適用できます。
例10-42 温度測定用のフレキシブル使用状況ドメインの作成
次のコードでは、3つのcelcius
、fahrenheit
、kelvin
というドメインから、temperature
というフレキシブル使用状況ドメインを作成します。それぞれの温度スケールに応じて作成されたドメインには、適切な絶対零度のチェックと表示式があります。フレキシブル・ドメインにはELSE
句がないため、別の温度単位の値の挿入が可能ですが、そうした温度単位の温度値は制約されません。
CREATE DOMAIN celcius AS NUMBER
CONSTRAINT abs_zero_c_c CHECK ( celcius >= -273.15 )
DISPLAY celcius || ' °C';
CREATE DOMAIN fahrenheit AS NUMBER
CONSTRAINT abs_zero_f_c CHECK ( fahrenheit >= -459.67 )
DISPLAY fahrenheit || ' °F';
CREATE DOMAIN kelvin AS NUMBER
CONSTRAINT abs_zero_k_c CHECK ( kelvin >= 0 )
DISPLAY kelvin || ' K';
次のコードでは、温度単位に基づいて使用するドメインを選択するフレキシブル・ドメインを作成します。
CREATE FLEXIBLE DOMAIN temperature (
temp
) CHOOSE DOMAIN USING ( units char(1) )
FROM (
CASE units
WHEN 'C' THEN celcius ( temp )
WHEN 'F' THEN fahrenheit ( temp )
WHEN 'K' THEN kelvin ( temp )
END);
例10-43 住所用のフレキシブル使用状況ドメインの作成
次のコードでは、米国とイギリス(英国)のアドレスを表す複数列使用状況ドメインと、その他の国に向けたデフォルトの住所ドメインを作成します。
/* US addresses */
CREATE DOMAIN us_address AS (
line_1 AS VARCHAR2(255 CHAR) NOT NULL,
town AS VARCHAR2(255 CHAR) NOT NULL,
state AS VARCHAR2(255 CHAR) NOT NULL,
zipcode AS VARCHAR2(10 CHAR) NOT NULL
) CONSTRAINT us_address_c check (
REGEXP_LIKE ( zipcode, '^[0-9]{5}(-[0-9]{4}){0,1}$' ));
/* British addresses */
CREATE DOMAIN gb_address AS (
street AS VARCHAR2(255 CHAR) NOT NULL,
locality AS VARCHAR2(255 CHAR),
town AS VARCHAR2(255 CHAR) NOT NULL,
postcode AS VARCHAR2(10 CHAR) NOT NULL
) CONSTRAINT gb_postcode_c check (
REGEXP_LIKE (
postcode, '^[A-Z]{1,2}[0-9][A-Z]{0,1} [0-9][A-Z]{2}$' ));
/* Default address */
CREATE DOMAIN global_address AS (
line_1 AS VARCHAR2(255) NOT NULL,
line_2 AS VARCHAR2(255),
line_3 AS VARCHAR2(255),
line_4 AS VARCHAR2(255),
postcode AS VARCHAR2(10));
次のコードでは、国コードに基づいて使用する複数列住所ドメインを選択するフレキシブル・ドメインを作成します。
CREATE FLEXIBLE DOMAIN address (
line_1, line_2, line_3, line_4,
postal_code
)
CHOOSE DOMAIN USING ( country_code VARCHAR2(2 char) )
FROM (
CASE country_code
WHEN 'GB' THEN gb_address ( line_1, line_2, line_3, postal_code )
WHEN 'US' THEN us_address ( line_1, line_2, line_3, postal_code )
ELSE global_address ( line_1, line_2, line_3, line_4, postal_code )
END);
ノート:
フレキシブル・ドメインを作成するには、構成要素ドメインごとにEXECUTE
権限が必要です。
関連項目:
使用状況ドメインの作成に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: CREATE DOMAINを参照してください
10.1.6.2 表作成時のフレキシブル使用状況ドメインの関連付け
CREATE TABLE
DDLを使用すると、新しい表に新しく作成した列のセットにフレキシブル使用状況ドメインを関連付けできます。列のセットにフレキシブル・ドメインを追加するには、ドメインに関連付ける列のリストを(ドメインの列順序で)指定し、判別式として使用する列のリストを(フレキシブル・ドメインの判別式の列順序で)指定します。
例10-44 temperature
フレキシブル・ドメインと新しい表列の関連付け
temperature
フレキシブル・ドメインを使用するsensor_readings
表を作成し、USING
キーワードで判別式の列を指定します。
CREATE TABLE sensor_readings (
sensor_id integer, reading_timestamp TIMESTAMP,
temperature_reading NUMBER,
temperature_units CHAR(1 CHAR),
DOMAIN temperature ( temperature_reading )
USING ( temperature_units ));
例10-45 address
フレキシブル・ドメインと新しい表列の関連付け
次のコードでは、addresses
という新しい表を作成し、その表の列をaddress
フレキシブル・ドメインに関連付けます。
CREATE TABLE addresses (
line_1 VARCHAR2(255) NOT NULL,
line_2 VARCHAR2(255),
line_3 VARCHAR2(255),
line_4 VARCHAR2(255),
country_code VARCHAR2(2 CHAR) NOT NULL,
postal_code VARCHAR2(10 CHAR),
DOMAIN address (
line_1, line_2, line_3, line_4, postal_code)
USING ( country_code ));
ノート:
キーワードのDOMAIN
とUSING
は、フレキシブル・ドメインを関連付けするときには必須です。
10.1.6.2.1 フレキシブル・ドメインに関連付けられた列に対するDMLの使用
次に、フレキシブル使用状況ドメインが関連付けられた新しく作成する表列に対するDML文の例を示します。
例10-46 temperature
フレキシブル・ドメインに関連付けられた列に対するDMLコマンドの使用
INSERT INTO sensor_readings
VALUES ( 1, timestamp'2023-06-08 12:00:00', 21.1, 'C' ),
( 1, timestamp'2023-06-08 12:05:00', 21.2, 'C' ),
( 1, timestamp'2023-06-08 12:10:00', 20.9, 'C' ),
( 2, timestamp'2023-06-08 12:00:00', 68.5, 'F' ),
( 2, timestamp'2023-06-08 12:05:00', 68.1, 'F' ),
( 2, timestamp'2023-06-08 12:10:00', 68.9, 'F' ),
( 3, timestamp'2023-06-08 12:00:00', 290.23, 'K' ),
( 3, timestamp'2023-06-08 12:05:00', 289.96, 'K' ),
( 3, timestamp'2023-06-08 12:10:00', 289.65, 'K' ),
( 4, timestamp'2023-06-08 12:00:00', 528.15, 'R' ),
( 4, timestamp'2023-06-08 12:05:00', 528.42, 'R' ),
( 4, timestamp'2023-06-08 12:10:00', 527.99, 'R' );
SELECT sensor_id, reading_timestamp,
DOMAIN_DISPLAY ( temperature_reading, temperature_units ) temp
FROM sensor_readings;
関連項目:
DOMAIN_DISPLAY
やDOMAIN_ORDER
などのドメイン関数の詳細は、「ドメイン使用状況用のSQL関数」を参照してください。
出力は次のとおりです。
SENSOR_ID READING_TIMESTAMP TEMP
---------- ------------------------------ -------------------------------------------
1 08-JUN-2023 12.00.00.000000000 21.1 °C
1 08-JUN-2023 12.05.00.000000000 21.2 °C
1 08-JUN-2023 12.10.00.000000000 20.9 °C
2 08-JUN-2023 12.00.00.000000000 68.5 °F
2 08-JUN-2023 12.05.00.000000000 68.1 °F
2 08-JUN-2023 12.10.00.000000000 68.9 °F
3 08-JUN-2023 12.00.00.000000000 290.23 K
3 08-JUN-2023 12.05.00.000000000 289.96 K
3 08-JUN-2023 12.10.00.000000000 289.65 K
4 08-JUN-2023 12.00.00.000000000 <null>
4 08-JUN-2023 12.05.00.000000000 <null>
4 08-JUN-2023 12.10.00.000000000 <null>
例10-47 範囲外制約エラー
次の値は、それぞれの温度スケールに対して範囲外制約エラーになります。
INSERT INTO sensor_readings
VALUES ( 1, timestamp'2023-06-08 12:15:00', -400, 'C' );
INSERT INTO sensor_readings
VALUES ( 2, timestamp'2023-06-08 12:15:00', -999, 'F' );
INSERT INTO sensor_readings
VALUES ( 3, timestamp'2023-06-08 12:15:00', -1, 'K' );
例10-48 address
フレキシブル・ドメインに関連付けられた列に対するDMLの使用
-- Great Britian
INSERT INTO addresses ( line_1, line_3, country_code, postal_code )
VALUES ( '10 Big street', 'London', 'GB', 'N1 2LA' );
-- United States
INSERT INTO addresses ( line_1, line_2, line_3, country_code, postal_code )
VALUES ( '10 another road', 'Las Vegas', 'NV', 'US', '87654-3210' );
-- Tuvalu
INSERT INTO addresses ( line_1, country_code )
VALUES ( '10 Main street', 'TV' );
SELECT * FROM addresses;
出力は次のとおりです。
LINE_1 LINE_2 LINE_3 LINE_4 COUNTRY_CODE POSTAL_CODE
------------------ ------------ --------- --------- --------------- -----------
10 Big street <null> London <null> GB N1 2LA
10 another road Las Vegas NV <null> US 87654-3210
10 Main street <null> <null> <null> TV <null>
次のINSERT
コマンドは、US郵便番号が含まれたUK住所を挿入しようとしているため、エラーを返します。
INSERT INTO addresses ( line_1, line_3, country_code, postal_code )
VALUES ( '10 Big street', 'London', 'GB', '12345-6789' );
ORA-11534: check constraint (schema.SYS_C0010286) due to domain constraint schema.SYS_DOMAIN_C00639 of domain schema.ADDRESS violated
次のINSERT
コマンドは、州の値のないUS住所を挿入しようとしているため、エラーを返します。
INSERT INTO addresses ( line_1, line_2, country_code, postal_code )
VALUES ( '10 another road', 'Las Vegas', 'US', '87654-3210' );
ORA-11534: check constraint (schema.SYS_C0010289) due to domain constraint schema.SYS_DOMAIN_C00636 of domain schema.ADDRESS violated
10.1.6.3 フレキシブル・ドメインの既存の列との関連付け
ALTER TABLE
DDLは、MODIFY
句またはADD
句とともに使用することで、既存の列または既存の表に新しく追加された列にフレキシブル使用状況ドメインを関連付けることができます。
例10-49
次のコードでは、temp_sensor_readings
という新しい表を作成します。
CREATE TABLE temp_sensor_readings (
sensor_id integer, reading_timestamp TIMESTAMP,
temperature_reading NUMBER,
temperature_units CHAR(1 CHAR));
次のコードでは、temperature
フレキシブル・ドメインをtemperature_reading
という既存の列に関連付けます。
ALTER TABLE temp_sensor_readings
MODIFY (temperature_reading, temperature_units)
ADD DOMAIN temperature;
ガイドライン
-
DOMAIN
キーワードは、フレキシブル・ドメインを関連付けるときには必須です。 -
ALTER TABLE .. ADD
文には、USING
キーワードが必須になります。 -
複数のフレキシブル・ドメインには、ドメイン列としても判別式の列としても、同じ列を関連付けることはできません。
-
同一のドメインに列を関連付けることはできませんが、別の列位置を関連付けできます。
10.1.6.4 列からのフレキシブル使用状況ドメインの関連付け解除
ALTER TABLE
DDLは、DROP
句とともに使用することで、列からフレキシブル使用状況ドメインの関連付けを解除できます。
例10-50
次のコードでは、temp_sensor_readings
表からtemperature
ドメインを削除します。
ALTER TABLE temp_sensor_readings
MODIFY (temperature_reading, temperature_units) DROP DOMAIN;
ガイドライン
-
ドメイン名は不要です。これは、どの列がどのドメインに関連付けられているかをデータベースが認識していて、1つの列は1つのドメインにのみ関連付けできるためです。
-
ALTER TABLE ..DROP DOMAIN
のALTER TABLE ..MODIFY
には、その他のオプションを指定できません。
10.1.6.5 フレキシブル使用状況ドメインの削除
フレキシブル使用状況ドメインを削除する場合は、単一列使用状況ドメインに使用したものと同じ構文を使用します。
ガイドライン
-
フレキシブル・ドメインで参照されているドメインを削除する場合は、
FORCE
オプションを指定したDROP DOMAIN
を使用します。この操作により、フレキシブル・ドメインも削除されます。 -
フレキシブル・ドメインを
FORCE
モードで削除するには、構成要素のフレキシブル・ドメインを削除する権限が必要です。
関連項目:
-
使用状況ドメインの削除に関する構文とセマンティックの詳細は、『Oracle Database SQL言語リファレンス』: DROP DOMAINを参照してください。
-
使用状況ドメインの削除の詳細は、「使用状況ドメインの削除」を参照してください。
10.1.7 ドメインのデータ型の指定
ドメイン・データ型は、Oracleデータ型のいずれかになります。修飾ドメイン名は、修飾されたユーザー定義データ型やOracle組込み型と競合しないようにする必要があります。
列がドメインに関連付けられていて、列のデータ型が指定されていない場合は、ドメインのデータ型が、関連付けられた列のデフォルトのデータ型として使用されます。関連付けられた列にすでにデータ型がある場合は、その列のデータ型が使用されます。
ドメイン・データ型がSTRICT
以外として定義されている場合、関連付けられた列のデータ型はドメイン・データ型との互換性のみが必要です。つまり、データ型は同じであることが必要ですが、長さ、精度およびスケールは異なっていてもかまいません。たとえば、strict以外のドメインの場合、VARCHAR2(10)
のドメインは、どのVARCHAR2
列にも関連付けできます。
ドメイン・データ型がSTRICT
として定義されている場合、関連付けられた列のデータ型はドメイン・データ型と互換性があり、ドメイン・データ型の長さ、精度およびスケールも一致している必要があります。
例10-51 列とドメイン・データ型の関連付け
次の例では、year_of_birth
ドメインとemail_dom
ドメインを作成し、ドメインを列に関連付けて、ドメインと列のデータ型の互換性を示します。
DROP DOMAIN IF EXISTS year_of_birth;
CREATE DOMAIN year_of_birth AS NUMBER(4)
CONSTRAINT CHECK ( (TRUNC(year_of_birth) = year_of_birth) AND (year_of_birth >= 1900) );
DROP DOMAIN IF EXISTS email_dom;
CREATE DOMAIN email_dom AS VARCHAR2(100)
CONSTRAINT email_chk check (REGEXP_LIKE (email_dom, '^(\S+)\@(\S+)\.(\S+)$'));
DROP TABLE IF EXISTS newcustomers PURGE;
CREATE TABLE newcustomers (
cust_Id NUMBER,
cust_year_of_birth NUMBER(6) DOMAIN year_of_birth,
cust_hq_email VARCHAR2(50),
cust_office_email VARCHAR2(100),
cust_rep_email VARCHAR2(100));
DESC newcustomers;
出力は次のとおりです。
Name Null? Type
----------------------------- -------- ----------------------------
CUST_ID NUMBER
CUST_YEAR_OF_BIRTH NUMBER(6) SH.YEAR_OF_BIRTH
CUST_HQ_EMAIL VARCHAR2(50)
CUST_OFFICE_EMAIL VARCHAR2(100)
CUST_REP_EMAIL VARCHAR2(200)
cust_year_of_birth
列は、Oracleデータ型のNumber
として定義されていて、year_of_birth
ドメインにも関連付けられるため、その列のデータ型が列に割り当てられます。cust_year_of_birth
列は、year_of_birth
ドメインで定義されているすべてのプロパティ(制約、表示、順序付けのプロパティなど)を継承します。
次の例では、year_of_birth
ドメインに関連付けられた列があるukcustomers
表を作成しますが、その列にはデータ型がありません:
CREATE TABLE ukcustomers (
cust_Id NUMBER,
cust_year_of_birth DOMAIN year_of_birth);
DESC ukcustomers;
出力は次のとおりです。
Name Null? Type
------------------------------ -------- ----------------------------
CUST_ID NUMBER
CUST_YEAR_OF_BIRTH NUMBER(4) SH.YEAR_OF_BIRTH
ここでは、cust_year_of_birth
列に、ドメインのデータ型NUMBER(4)
が割り当てられています。
次の例では、DOMAIN
キーワードが省略されています。
CREATE TABLE incustomers (
cust_id NUMBER,
cust_year_of_birth year_of_birth);
DESC incustomers;
出力は次のとおりです。
Name Null? Type
----------------------------- -------- ----------------------------
CUST_ID NUMBER
CUST_YEAR_OF_BIRTH NUMBER(4) SH.YEAR_OF_BIRTH
列定義句では、ドメイン句はデータ型句を置き換えるか、その直後に続ける必要があります。
ドメイン列データ型がSTRICT
として定義されていない場合は、列の長さに関係なく、同じデータ型の列にドメインを関連付けできます。
次のALTER
コマンドは成功します。これは、ドメインと列のデータ型が同じで、列の長さがSTRICT
以外のドメインではチェックされないためです。
ALTER TABLE newcustomers
MODIFY cust_hq_email DOMAIN email_dom;
ALTER TABLE newcustomers
MODIFY cust_office_email DOMAIN email_dom;
ALTER TABLE newcustomers
MODIFY cust_rep_email DOMAIN email_dom;
ドメイン列データ型がSTRICT
として定義されている場合、ドメイン関連付けは、列とドメインのデータ型が同じで長さも一致している場合にのみ機能します。
DROP DOMAIN IF EXISTS email_dom;
CREATE DOMAIN email_dom AS VARCHAR2(100) STRICT
CONSTRAINT email_chk check (REGEXP_LIKE (email_dom, '^(\S+)\@(\S+)\.(\S+)$'));
次のALTER
コマンドは成功します。
ALTER TABLE newcustomers
MODIFY cust_office_email DOMAIN email_dom;
次のALTER
コマンドは、列長とドメイン長が一致しないために失敗します。
ALTER TABLE newcustomers
MODIFY cust_hq_email DOMAIN email_dom;
ALTER TABLE newcustomers
MODIFY cust_rep_email DOMAIN email_dom;
表列データ型からSTRICT
以外のドメイン列データ型への互換性
STRICT
以外のドメインでは、表列とドメイン列に異なる長さ、精度およびスケールを設定できます。
-
NUMBER
、NUMER(p)
、NUMBER(p, s)
、NUMERIC
、NUMERIC(p)
、NUMERIC(p, s)
、DECIMAL
、DECIMAL(p)
、DEC
、DEC(p)
、INTEGER
、INT
、SMALLINT
、FLOAT
、FLOAT(p)
、REAL
、DOUBLE_PRECISION
-
CHAR(L)
、CHAR(L CHAR)
、CHAR(L BYTE)
、CHARACTER(L CHAR)
、CHARACTER(L BYTE)
、CHARACTER(L)
-
NCHAR(L)
、NATIONAL CHARACTER(L)
、NATIONAL CHAR (L)
-
VARCHAR2(L)
、VARCHAR2(L CHAR)
、VARCHAR2(L BYTE)、
CHAR VARYING(L CHAR)
、CHAR VARYING(L BYTE)
、CHAR VARYING(L)、
CHARACTER VARYING(L CHAR)
、CHARACTER VARYING(L BYTE)
、CHARACTER VARYING(L)
-
NVARCHAR2(L)
、NATIONAL CHAR VARYING (L)
、NATIONAL CHARACTER VARYING (L)
-
TIMESTAMP
、TIMESTAMP(p)
-
TIMESTAMP WITH TIME ZONE
、TIMESTAMP(p) WITH TIME ZONE
-
TIMESTAMP WITH LOCAL TIME ZONE
、TIMESTAMP(p) WITH LOCAL TIME ZONE
-
INTERVAL YEAR TO MONTH
、INTERVAL YEAR(p) TO MONTH
-
INTERVAL DAY TO SECOND
、INTERVAL DAY(p) TO SECOND
、INTERVAL DAY TO SECOND(s)
、INTERVAL DAY(p) TO SECOND(s)
-
ROWID
、UROWID
、UROWID(p)
-
RAW(p)
、RAW(p)
表列データ型からSTRICT
ドメイン列データ型への互換性
次の各項目は、互換性のある型を示します。ドメイン列の型に互換性があれば、任意の表列を関連付けできます。STRICT
ドメインの場合、表列とドメイン列は、長さ、精度およびスケールについて完全に一致する必要があります。
-
NUMBER(*)
、NUMBER
-
表列データ型とドメイン列データ型の精度が同じ場合、
NUMBER(p, 0)
、NUMERIC(p)
、NUMERIC(p, 0)
、DECIMAL(p)
、DEC(p)
。 -
表列データ型とドメイン列データ型の精度とスケールが同じ場合、
NUMBER(p, s)
、NUMERIC(p, s)
、DECIMAL(p, s)
、DEC(p, s)
。 -
NUMBER(*,0)
、NUMERIC(*)
、NUMERIC(*,0)
、DEC(*)
、DEC(*,0)
、DECIMAL(*)
、DECIMAL(*,0)
、INTEGER
、INT
、SMALLINT
-
FLOAT(63)
、REAL
-
FLOAT
、FLOAT(126)
、DOUBLE PRECISION
-
列データ型とドメイン列データ型のサイズ(バイト単位)が同じ場合、
CHAR(L CHAR)
、CHAR(L BYTE)
、CHARACTER (L)
。たとえば、1文字が4バイトの場合、CHAR (4 BYTE)
はCHAR(1 CHAR)
のSTRICT
ドメイン列に関連付けできます。 -
列データ型とドメイン列データ型のサイズ(バイト単位)が同じ場合、
NCHAR(L)
、NATIONAL CHARACTER(L)
、NATIONAL CHAR (L)
。 -
列データ型とドメイン列データ型のサイズ(バイト単位)が同じ場合、
VARCHAR2(L CHAR)
、VARCHAR2(L BYTE)
、CHARACTER VARYING (L)
、CHAR VARYING(L)
。 -
列データ型とドメイン列データ型のサイズ(バイト単位)が同じ場合、
NVARCHAR2(L)
、NATIONAL CHAR VARYING (L)
、NATIONAL CHARACTER VARYING (L)
。 -
TIMESTAMP
、TIMESTAMP(6)
-
TIMESTAMP WITH TIME ZONE
、TIMESTAMP(6) WITH TIME ZONE
-
TIMESTAMP WITH LOCAL TIME ZONE
、TIMESTAMP(6) WITH LOCAL TIME ZONE
-
INTERVAL YEAR TO MONTH
、INTERVAL YEAR(2) TO MONTH
-
INTERVAL DAY TO SECOND
、INTERVAL DAY(2) TO SECOND
、INTERVAL DAY TO SECOND(6)
、INTERVAL DAY(2) TO SECOND(6)
-
ROWID
、UROWID(10)
-
UROWID
、UROWID(4000)
、ROWID(4000)
表列データ型からドメイン列データ型への互換性
次の列データ型は、同等のドメイン列データ型とのみ互換性があります。たとえば、DATE
列型は、DATE
ドメイン列型にのみ関連付けできます。
-
BINARY_FLOAT
-
BINARY_DOUBLE
-
DATE
-
BLOB
-
CLOB
-
NCLOB
-
BFILE
-
LONG
-
LONG RAW
-
JSON
データ型に基づいた表列と使用状況ドメインの関連付けのルール
ドメインのデータ型がVARCHAR2(L [CHAR|BYTE])
の場合、各国語サポート(NLS)設定のセッション・レベルの長さセマンティクス値がNLS_LENGTH_SEMANTICS
でBYTE
として設定されているときには、Lのバイト数をLに対応する最大長(バイト単位)にします。
ドメインに列を関連付ける場合は、次のルールが適用されます:
-
ドメインが
STRICT
以外として定義されている場合、そのドメインは任意のxバイトのデータ型VARCHAR2(x)
の列に関連付けできます。STRICT
以外のドメインの場合は、Lとxが異なっていてもかまいません。 -
ドメインが
STRICT
として定義されている場合、そのドメインは任意のxバイト = Lバイトのデータ型VARCHAR2(x)
の列に関連付けできます。STRICT
ドメインの場合、L|xCHAR
を必要に応じてBYTES
に変換した後でも、Lとxのバイト数は同じであることが必要です。
たとえば、ドメイン・データ型の指定がVARCHAR2 STRICT
のときに、MAX_STRING_SIZE
がSTANDARD
の場合、そのドメインはL = 4000のVARCHAR2(L BYTE)
データ型の列と関連付けできます。セッションの現在のNLS設定が、文字を表すために最大2バイトを必要とする場合、ドメインにはVARCHAR2(2000 CHAR)
データ型の列を関連付けることができます。MAX_STRING_SEMANTICS
がEXTENDED
に変更されると、L = 32767のVARCHAR2(L BYTE)
またはVARCHAR2(16383 CHAR)
のデータ型の列をドメインに関連付けできます。
同様のルールはNVARCHAR2(L)
、CHAR(L [CHAR|BYTE])
およびNCHAR(L)
にも適用されます。
10.1.8 使用状況ドメインのプロパティの変更
アプリケーションの進化につれて、列定義の変更が必要になることがあり、それに伴って関連する使用状況ドメインのプロパティの変更も必要になります。ドメインの変更時には、ドメインの注釈、表示式および順序式のみを変更できます。次に、ドメインのその他のプロパティを変更する方法を示します。
これらの例は、開始手段として利用することも、特定のデータとビジネスの要件にあわせて構築して適応させることもできます。最初の例では手動の方法を示し、その次の例ではdbms_redefinition
パッケージを使用したオンラインの方法を示します。
例10-52 ドメイン・プロパティの手動変更
電子メール・ドメイン・フィールドの文字列長を100から200に変更するとします。この変更を実施するには、次のステップを完了する必要があります。
-
関連付けられた列の文字列長を200に変更します。
-
列に関連付けられている現在のドメインを削除します。
-
電子メールの文字列長が200の新しいドメインを作成します。
-
現在のドメインに関連付けられていた列を新しいドメインに再関連付けします。
現在のドメイン定義と列の関連付けが次の場合:
CREATE DOMAIN email_dom AS VARCHAR2(100) CONSTRAINT email_chk CHECK (regexp_like (email_dom, '^(\S+)\@(\S+)\.(\S+)$')); CREATE TABLE t1 ( id NUMBER, email DOMAIN email_dom );
ドメインに関連付けられている列のリストを表示するには:
SELECT table_name, column_name FROM user_tab_columns WHERE domain_name = 'EMAIL_DOM'; TABLE_NAME COLUMN_NAME ---------------------- ------------------- T1 EMAIL
t1表を変更して、電子メール列の文字列サイズを200に変更します。
ALTER TABLE t1 modify email varchar2(200);
FORCE PRESERVE
オプションを指定してドメインを削除します:
DROP DOMAIN email_dom FORCE PRESERVE;
その後で、電子メールの文字列サイズが200の新しいドメインを作成します。
CREATE DOMAIN email_dom AS VARCHAR2(200) CONSTRAINT email_chk CHECK (regexp_like (email_dom, '^(\S+)\@(\S+)\.(\S+)$'));
さらに、新しいドメインを電子メール列に再関連付けします:
ALTER TABLE t1 MODIFY email DOMAIN email_dom;
例10-53 オンラインのdbms_redefinition
パッケージを使用したドメイン・プロパティの変更
Oracleオンライン表再編成パッケージのdbms_redefinition
を使用すると、サポートされている通貨の更新などの許可された値を変更できます。たとえば、通貨ドメインでサポートされている通貨を変更するために必要なステップは次のとおりです:
-
新しいドメインの作成
-
新しいドメインを使用するように、現在のドメインに関連付けられていた列を移行します。
次の例には、基本的なエラー処理のみが含まれています。新しい制約に一部のデータが違反している場合など、複数の表の移行後にエラーが発生することがあります。完全なソリューションでは、このようなシナリオを考慮する必要があります。
次のコードでは、USD、GBPおよびEURの通貨を許容する制約があるドメインを作成します。
CREATE DOMAIN currency AS (
amount AS NUMBER,
iso_currency_code AS CHAR ( 3 CHAR )
) CONSTRAINT supported_currencies_c
CHECK ( iso_currency_code in ( 'USD', 'GBP', 'EUR' ) );
次の表には、currency
ドメインに関連付けられた列があるとします。
CREATE TABLE order_items (
order_id INTEGER, product_id INTEGER,
total_paid NUMBER(10, 2), currency_code CHAR ( 3 CHAR ),
DOMAIN currency ( total_paid, currency_code ),
PRIMARY KEY ( order_id, product_id )
);
CREATE TABLE product_prices (
product_id INTEGER,
unit_price NUMBER(10, 2),
currency_code CHAR( 3 char ),
DOMAIN currency ( unit_price, currency_code ),
PRIMARY KEY ( product_id, currency_code )
);
INSERT
コマンドを使用して、product_prices
表とorder_items
表に、いくつかの値を格納します。
INSERT INTO product_prices
VALUES (1, 9.99, 'USD'),
(1, 8.99, 'GBP'),
(1, 8.99, 'EUR');
INSERT INTO order_items
VALUES (1, 1, 9.99, 'USD'),
(2, 1, 8.99, 'GBP'),
(3, 1, 8.99, 'EUR');
COMMIT;
ビジネスが拡大していて、さらに多くの通貨のサポートが必要になったとします。制約の直接的な変更はできないため、次のような代替方法が必要です。
-
新しいドメインの作成。
-
制約を保持しながら関連付けられている列から既存のドメインを削除するための、
product_prices
表とorder_items
表の変更。 -
新しいドメインを追加するための表の変更。
-
表からの保持した制約の削除。
ただし、これらはオンラインで実行すると、DDL文をブロックします。そのかわりに、dbms_redefinition
パッケージを使用すると、オンラインで制約を変更できます。
新しくサポートされた通貨が含まれている制約によって新規ドメインを作成し、そのドメインを一時表に関連付ける必要があります。新しいドメインで元のドメインを置き換えます。
CREATE DOMAIN currency_d as (
amount AS NUMBER,
iso_currency_code AS CHAR ( 3 CHAR )
) CONSTRAINT supported_currencies_d_c
CHECK ( iso_currency_code in ( 'USD', 'GBP', 'EUR', 'CAD', 'MXP', 'INR', 'JPY' ) );
CREATE TABLE order_items_tmp (
order_id INTEGER, product_id INTEGER,
total_paid NUMBER(10, 2), currency_code CHAR ( 3 CHAR ),
DOMAIN currency_d ( total_paid, currency_code ) ,
PRIMARY KEY ( order_id, product_id )
);
CREATE TABLE product_prices_tmp (
product_id INTEGER,
unit_price NUMBER(10, 2),
currency_code CHAR (3 CHAR),
DOMAIN currency_d ( unit_price, currency_code ),
PRIMARY KEY ( product_id, currency_code )
);
このコードの再利用性を高めるために、redefine_table
プロシージャを作成します。このプロシージャでは、dbms_redefinition
プロシージャをコールすることで、一時表の列のプロパティを現在の表列にコピーして、現在の表列を新しいドメインにスワップします。
DECLARE
PROCEDURE redefine_table ( current_table VARCHAR2, staging_table VARCHAR2 ) AS
num_errors pls_integer;
BEGIN
DBMS_REDEFINITION.CAN_REDEF_TABLE(user, current_table);
DBMS_REDEFINITION.START_REDEF_TABLE(user, current_table, staging_table);
DBMS_REDEFINITION.copy_table_dependents(
uname => user,
orig_table => current_table,
int_table => staging_table,
copy_constraints => false,
num_errors => num_errors);
IF num_errors > 0 THEN
dbms_redefinition.abort_redef_table(user, current_table, staging_table);
raise_application_error ( -20001, num_errors || ' errors copying dependents from ' || current_table || ' to ' || staging_table );
ELSE
dbms_redefinition.finish_redef_table(user, current_table, staging_table);
END IF;
END redefine_table;
BEGIN
FOR tabs IN (
SELECT distinct table_name from user_tab_cols
WHERE domain_name = 'CURRENCY'
) LOOP
redefine_table(tabs.table_name, tabs.table_name || '_TMP');
END LOOP;
END;
/
product_prices
表にDMLを使用して、新しい通貨が現在サポートされているかどうかを確認します。
-- New currencies now supported
INSERT INTO product_prices
VALUES (1, 9.99, 'CAD');
-- Invalid currencies raise exception
INSERT INTO product_prices
VALUES (1, 9.99, 'N/A');
SELECT * FROM product_prices;
出力は次のとおりです。
PRODUCT_ID UNIT_PRICE CUR
---------- ---------- ---
1 9.99 USD
1 8.99 GBP
1 8.99 EUR
1 9.99 CAD
一時オブジェクトと古いドメインcurrency
をクリーン・アップします。
DROP TABLE order_items_tmp PURGE;
DROP TABLE product_prices_tmp PURGE;
DROP DOMAIN currency;
関連項目:
『PL/SQLパッケージおよびタイプ・リファレンス』ガイドの「DBMS_REDEFINITION」
10.1.9 使用状況ドメイン用のSQL関数
ドメイン関数を使用すると、より効率的に使用状況ドメインを操作できます。
使用状況ドメインには、次のSQL関数を使用できます。
-
DOMAIN_DISPLAY
は、引数が関連付けられているドメインのドメイン表示式を返します。 -
DOMAIN_NAME
は、引数が関連付けられているドメインの修飾ドメイン名を返します。ドメインに対するパブリック・シノニムがある場合は、そのシノニムが返されます。それ以外の場合は、domain_owner.domain_name
の形式でドメイン名が返されます。 -
DOMAIN_ORDER
は、引数が関連付けられているドメインのドメイン順序式を返します。 -
DOMAIN_CHECK(domain_name, value1, value2, ...)
は、domain_name
の制約条件(NOT NULLまたはCHECK制約)をvalue
式に適用します。さらに、値の型互換性もチェックします。値は多数になる可能性があります。値式の数はドメイン内の列の数と一致する必要があります。一致していないと文でエラーが発生します。 -
DOMAIN_CHECK_TYPE(domain_name, value1, value2, ...)
では、入力式がドメインのデータ型と互換性があるかどうかを検証します。値は多数になる可能性があります。値式の数はドメイン内の列の数と一致する必要があります。一致していないと文でエラーが発生します。
関連項目:
使用状況ドメインでのSQL関数の使用の詳細は、『Oracle Database SQL言語リファレンス』のドメイン関数を参照してください
10.1.10 ドメイン情報の表示
ディクショナリ・ビューを使用すると、ドメインに関する情報を取得できます。ディクショナリ・ビューは、関連付けられたドメインと比較したときに、制約やデフォルト式などのプロパティが異なる列の識別にも役立ちます。
10.1.10.1 使用状況ドメインのディクショナリ・ビュー
ディクショナリ・ビューの[USER|DBA|ALL]_DOMAINS
と[USER|DBA|ALL]_DOMAIN_COLS
はドメインを表し、ドメイン列に関する次の情報を提供します。フレキシブル・ドメインの場合は、ドメイン・セレクタ式もビューに含まれます。
-
ドメイン名
-
ドメイン所有者
-
表示式と順序式
-
デフォルト値
-
ドメインのデータ型
-
照合
使用状況ドメインには、次のディクショナリ・ビューを使用できます。
-
ALL_DOMAINS
は、現行のユーザーがアクセスできるドメインを示します。 -
DBA_DOMAINS
は、データベース内のすべてのドメインを示します。 -
USER_DOMAINS
は、現行のユーザーが所有するドメインを示します。 -
ALL_DOMAIN_COLS
は、現行のユーザーがアクセスできるドメインの列を示します。 -
DBA_DOMAIN_COLS
は、データベース内のすべてのドメインの列を示します。 -
USER_DOMAIN_COLS
は、現行のユーザーが所有するドメインの列を示します。 -
ALL_DOMAIN_CONSTRAINTS
は、現行のユーザーがアクセスできるドメインの制約定義を示します。 -
DBA_DOMAIN_CONSTRAINTS
は、データベース内のすべてのドメインの制約定義を示します。 -
USER_DOMAIN_CONSTRAINTS
は、現行のユーザーが所有するドメインの制約定義を示します。
関連項目:
使用状況ドメインに使用されるビューの詳細は、『Oracle Databaseリファレンス』のビューALL_DOMAINS、DBA_DOMAINS、USER_DOMAINS、ALL_DOMAIN_COLS、DBA_DOMAIN_COLS、USER_DOMAIN_COLS、ALL_DOMAIN_CONSTRAINTS、DBA_DOMAIN_CONSTRAINTS、USER_DOMAIN_CONSTRAINTSを参照してください。
10.1.11 組込みの使用状況ドメイン
Oracle Databaseには、表列に直接使用できる組込みの使用状況ドメイン(email_d、ssn_d、credit_card_number_dなど)が用意されています。組込みの使用状況ドメインは、すべてのPDBに存在しています。新しいPDBがCDBに追加されると、組込みの使用状況ドメインが自動的に作成されてPDBに追加されます。
次に、Oracle Databaseでサポートされている、すべての組込みの使用状況ドメインのリストを示します。
表10-1 組込みのドメイン
名前 | 指定可能な値 | 説明: |
---|---|---|
email_d |
^([a-zA-Z0-9!#$%&*+=?^_`{|}~-]+(\.[ A-Za-z0-9!#$%&*+=?^_`{|}~-]+)*)@(([ a-zA-Z0-9]([a-zA-Z0-9-]*[a-zA-Z0-9] )?\.)+[a-zA-Z0-9]([a-zA-Z0-9-]*[a-z A-Z0-9])?)$ |
電子メール・アドレス 実装: Regex |
day_short_d |
'MON'、'TUE'、'WED'、'THU'、'FRI'、'SAT'、'SUN' |
短い形式での曜日 ドメイン順序: 実装: List |
day_d |
'MONDAY'、'TUESDAY'、'WEDNESDAY'、'THURSDAY'、'FRIDAY'、'SATURDAY'、'SUNDAY' |
長い形式での曜日 ドメイン順序: 実装: List |
month_short_d |
'JAN'、'FEB'、'MAR'、'APR'、'MAY'、'JUN'、'JUL'、'AUG'、'SEP'、'OCT'、'NOV'、'DEC' |
短い書式での月 実装: List |
month_d |
'JANUARY'、'FEBRUARY'、'MARCH'、'APRIL'、'MAY'、'JUNE'、 'JULY'、'AUGUST'、'SEPTEMBER'、'OCTOBER'、'NOVEMBER'、'DECEMBER' |
長い書式での月 実装: List |
year_d |
year > 0とyear <= 9999 |
年(0-9999) 実装: Check |
positive_number_d |
positive_number > 0 |
正の数値: 1、2、3、4、... 実装: Check |
negative_number_d |
negative_number < 0 |
負の数値: ...、-3、-2、-1 実装: Check |
non_positive_number_d |
non_positive_number <= 0 |
正でない数値: ...、-3、-2、-1、0 実装: Check |
non_negative_number_d |
non_negative_number >= 0 |
負でない数値: 0、1、2、3... 実装: Check |
mac_address_d |
^([a-fA-F0-9]{2}[-]){5}[a-fA-F0-9]{2}$ ^([a-fA-F0-9]{2}[:]){5}[a-fA-F0-9]{2}$ |
MACアドレス 実装: regex |
ssn_d |
^[0-9]{3}[-][0-9]{2}[-][0-9]{4}$ |
US SSN 実装: regex |
credit_card_number_d |
^([0-9]{4}[-]){3}[0-9]{4}$ ^([0-9]{4}[ ]){3}[0-9]{4}$ ^([0-9]{4}){3}[0-9]{4}$ ^[0-9]{4}[-][0-9]{6}[-][0-9]{5}$ ^[0-9]{4}[ ][0-9]{6}[ ][0-9]{5}$ ^[0-9]{15}$ |
クレジット・カード番号 実装: regex |
ipv4_address_d |
^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$ |
IPv4アドレス 実装: regex |
ipv6_address_d |
^([0-9a-fA-F]{4}[:]){7}[0-9a-fA-F]{4}$ ^([0-9a-fA-F]{4}[:]){6}(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$ |
IPv6アドレス 実装: regex |
subnet_mask_d |
^(((255\.){3}(255|254|252|248|240|224|192|128|0))|((255\.){2}(255|254|252|248|240|224|192|128|0)\.0)| ((255\.)(255|254|252|248|240|224|192|128|0)(\.0+){2})|((255|254|252|248|240|224|192|128|0)(\.0){3}))$ |
サブネット・マスク 実装: regex |
sha1_d |
^[0-9a-fA-F]{40}$ |
SHA1 実装: regex |
sha256_d |
^[0-9a-fA-F]{64}$ |
SHA256 実装: regex |
sha512_d |
^[0-9a-fA-F]{128}$ |
SHA512 実装: regex |
cidr_d |
^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\/([1-9]|[1-2][0-9]|3[0-2])$ |
CIDR 実装: regex |
phone_number_d |
^[+]{0,1}[0-9]{1,16}$ |
電話番号 実装: regex |
mime_type_d |
'application/epub+zip', 'application/gzip', 'application/java-archive', 'application/json', 'application/ld+json', 'application/msword', 'application/msword', 'application/ogg', 'application/pdf', 'application/rtf', 'application/vnd.amazon.ebook', 'application/vnd.apple.installer+xml'、 'application/vnd.ms-excel', 'application/vnd.ms-fontobject', 'application/vnd.ms-powerpoint', 'application/vnd.oasis.opendocument.presentation', 'application/vnd.oasis.opendocument.spreadsheet', 'application/vnd.oasis.opendocument.text', 'application/vnd.openxmlformats-officedocument.presentationml.presentation', 'application/vnd.openxmlformats-officedocument.wordprocessingml.document', 'application/vnd.rar', 'application/vnd.visio', 'application/x-abiword', 'application/x-bzip', 'application/x-bzip2', 'application/x-cdf', 'application/x-compressed', 'application/x-csh', 'application/x-freearc', 'application/x-httpd-php', 'application/x-sh', 'application/x-shockwave-flash', 'application/x-tar', 'application/x-zip-compressed', 'application/zip', 'audio/aac', 'audio/midi', 'audio/mpeg', 'audio/ogg', 'audio/opus', 'audio/wav', 'audio/webm', 'audio/x-midi', 'font/otf', 'font/ttf', 'image/avif', 'image/bmp', 'image/gif', 'image/jpeg', 'image/png', 'image/svg+xml', 'image/tiff', 'image/vnd.microsoft.icon', 'text/calendar', 'text/css', 'text/csv', 'text/html', 'text/javascript', 'text/javascript', 'text/plain', 'video/mp2t', 'video/mp4', 'video/mpeg', 'video/ogg', 'video/webm', 'video/x-msvideo' |
MIMEタイプ 実装: list |
10.2 アプリケーション使用状況の注釈
この項では、データベース・オブジェクトにアプリケーション使用状況の注釈(以降は、「注釈」と表記)を使用する方法について説明します。
多くのアプリケーションでは、表、ビュー、表の列、索引、ドメインなどのデータベース・オブジェクトに関する追加のプロパティ・メタデータを保持することが重要です。注釈を使用すると、アプリケーションで、データベース・オブジェクトおよび表の列に関するユーザー固有のメタデータをさらに格納および取得できます。アプリケーションでは、このようなメタデータを使用して、効果的なユーザー・インタフェースをレンダリングしたり、アプリケーション・ロジックをカスタマイズできます。
10.2.1 注釈の概要
注釈とは何ですか。また、どこで使用できますか。
注釈は、開発者がデータベース・スキーマ・オブジェクトの使用状況プロパティを一元的に登録するための軽量な宣言機能です。注釈はディクショナリ表に格納され、関連アプリケーションの共通データ全体にわたって動作の標準化を求めるアプリケーションで使用できます。注釈はデータベースによって解釈されません。これらはデータベース・メタデータのカスタム・データ・プロパティであり、表の列、表および索引に含まれており、アプリケーションは追加のプロパティ・メタデータとして使用してユーザー・インタフェースをレンダリングしたり、アプリケーション・ロジックをカスタマイズできます。
アプリケーション・メタデータをデータベースに一元的に定義および格納するメカニズムである注釈を使用すると、アプリケーション、モジュールおよびマイクロサービス間でメタデータ情報を共有できます。新しいオブジェクトを(CREATE
文を使用して)作成したり、既存のオブジェクトを(ALTER
文を使用して)変更するときに、注釈をスキーマ・オブジェクトに追加できます。
メタデータを使用してデータ・モデルに注釈を付けると、データの整合性と一貫性が向上し、データ・モデルのドキュメンテーションのメリットが高まります。アプリケーションでは、他のアプリケーションまたはユーザーが取得および使用できるデータベース・オブジェクトと表の列に関するユーザー定義のメタデータを格納できます。データとともにメタデータを格納すると、データを使用するユーザーまたはアプリケーションに対する一貫性と汎用的なアクセシビリティが保証されます。
個々の注釈には名前とオプションの値があります。名前とオプションの値は自由形式のテキスト・フィールドです。たとえば、名前と値のペアを持つ注釈(Display_Label 'Employee Salary'
など)を保持したり、名前のみを持つ(名前が説明なしでわかるため値が不要の)スタンドアロンの注釈(UI_Hidden
など)を保持できます。
次に、注釈の詳細を示します。
-
CREATE
DDL文を使用してスキーマ・オブジェクトに注釈名を指定すると、注釈が自動的に作成されます。 -
注釈は付加的です。つまり、同じスキーマ・オブジェクトに複数の注釈を指定できます。
-
1つのDDL文を使用して、一度に複数の注釈をスキーマ・オブジェクトに追加できます。同様に、1つのDDL文で複数の注釈をスキーマ・オブジェクトから削除できます。
-
注釈は、注釈を追加するデータベース・オブジェクトに対する下位要素として表されます。注釈は、データベース内に新しいオブジェクト・タイプを作成しません。
-
自分が所有しているか、スキーマ・オブジェクトに対する変更権限あれば、注釈をサポートする任意のスキーマ・オブジェクトに注釈を追加できます。注釈名をスキーマ修飾する必要はありません。
-
ディクショナリ・ビューに対してSQL問合せを発行して、名前と値およびスキーマ・オブジェクトでの使用を含め、すべての注釈を取得できます。
10.2.2 注釈とコメント
COMMENT
コマンドを使用して、表や表の列などのデータベース・オブジェクトに注釈を付けることもできます。スキーマ・オブジェクトに関連付けられたコメントは、オブジェクトのメタデータとともにデータ・ディクショナリに格納されます。
注釈は、コメントよりも使用しやすく、範囲が広くなります。コメントと注釈の主な違いは次のとおりです。
-
コメントは、表や列などの特定のスキーマ・オブジェクトにのみメタデータを追加するために使用されるコメント・メカニズムです。索引、プロシージャ、トリガー、ドメインなど、他のスキーマ・オブジェクトではコメントを使用できません。
-
コメントには名前がなく、自由形式の値しかありません。
-
コメントは付加的ではありません。つまり、同じオブジェクトに複数のコメントを追加することはできません。新しいコメントを指定すると、対応する表または列に関する前のコメントが上書きされます。
-
コメントには別々のDDL文が必要であるのに対し、複数の注釈を結合して1つのDDL文にできます。
-
エンティティごとに個別のディクショナリ・ビュー・セットが存在します。たとえば、表コメント用のビューと列コメント用の別のビューがあります。一方、注釈は、すべてのオブジェクト・タイプで統一されているため、問合せおよび使用が簡単になります。
関連項目:
COMMENTS
の使用方法の詳細は、コメントを参照してください。
10.2.3 サポートされているデータベース・オブジェクト
注釈は、次のデータベース・オブジェクトでサポートされています。
-
表および表の列
-
ビューおよびビューの列
-
マテリアライズド・ビューおよびマテリアライズド・ビューの列
-
索引
-
ドメインおよび複数列ドメインの列
10.2.4 注釈の使用に必要な権限
注釈を追加または削除するには、CREATE
またはALTER
DDL文で注釈が指定されているスキーマ・オブジェクトに対するCREATE
またはALTER
権限が必要です。
注釈を明示的に作成または削除することはできません。注釈は、初回使用時に自動的に作成されます。注釈は、注釈が定義されているデータベース・オブジェクト内の下位要素として格納されるため、注釈を追加してもデータベース内に新しいオブジェクト・タイプは作成されません。
10.2.5 注釈のDDL文
この項では、注釈の構文について説明し、表、表の列、ビュー、マテリアライズド・ビュー、索引およびドメインの注釈を定義または変更するためのDDL文を示します。
トピック:
10.2.5.1 注釈の構文
次のスニペットは、表、表の列、ビュー、マテリアライズド・ビュー、索引およびドメインの注釈を定義するためにDDL文で使用される注釈の構文を示しています。
annotations ::= 'ANNOTATIONS' '(' annotations_list ')' annotations_list ::= ( 'ADD' ('IF NOT EXISTS' | 'OR REPLACE' )? | 'DROP' 'IF EXISTS'? | REPLACE)? annotation ( ',' ( 'ADD' ('IF NOT EXISTS' | 'OR REPLACE' )? | 'DROP' 'IF EXISTS'? | REPLACE)? annotation )* annotation ::= annotation_name annotation_value? annotation_name ::= identifier annotation_value ::= character_string_literal
<annotation_value
>は、最大4000文字を保持できる文字列リテラルです。
<annotation_name
>は識別子であり、次の要件があります。
-
識別子は1024文字まで指定できます。
-
識別子が予約語である場合は、注釈名を二重引用符で囲む必要があります。
-
二重引用符で囲まれた識別子には、空白文字を含めることができます。
-
空白文字のみが含まれる識別子は使用できません。
10.2.5.2 表に注釈を付けるDDL文
次のDDL文を使用して、表を作成または変更するときに表に注釈を付けることができます。
CREATE TABLE
文の使用方法
次に、注釈を指定したCREATE TABLE
文の例を示します。
次の例では、JSON値の注釈Operation
と、もう1つのスタンドアロンで値のない注釈Hidden
を追加します。
CREATE TABLE Table1 ( T NUMBER) ANNOTATIONS(Operations '["Sort", "Group"]', Hidden);
注釈をするときには、その前にADD
キーワードを使用できます。すべての指定を省略すると、ADD
キーワードがデフォルトの操作とみなされます。
次の例では、オプションのADD
キーワードを使用して、Hidden
注釈(同様にスタンドアロン)をTable2
に追加します。
CREATE TABLE Table2 ( T NUMBER) ANNOTATIONS (ADD Hidden);
ADD
キーワードは、注釈を定義するときの暗黙的な操作であり、省略できます。
ALTER TABLE
文の使用方法
次の例では、ALTER TABLE
コマンドによって、注釈名Operations
およびHidden
のすべての注釈値が削除されます。
ALTER TABLE Table1 ANNOTATIONS(DROP Operations, DROP Hidden);
次の例のALTER TABLE
コマンドでは、Join
値の注釈JoinOperations
を追加して、注釈名Hidden
を削除します。注釈を削除するときには、DROP
コマンドに注釈名のみを含める必要があります。
ALTER TABLE Table1 ANNOTATIONS(ADD JoinOperations 'Join', DROP Hidden);
1つのDDL文に複数のADD
およびDROP
キーワードを指定できます。
ALTER TABLE Table1 ANNOTATIONS(ADD JoinOperations 'Join Ops');
出力は次のとおりです。
ORA-11552: Annotation name 'JOINOPERATIONS' already exists.
REPLACE
キーワードを使用して注釈値を置換できます。次の文では、JoinOperations
の値を'Join Ops
'に置き換えます:ALTER TABLE Table1 ANNOTATIONS(REPLACE JoinOperations 'Join Ops');
出力は次のとおりです
Table altered.
IF NOT EXISTS
句を使用することもできます。次の文では、JoinOperations
注釈が存在しない場合にのみ、その注釈を追加します。その注釈が存在する場合、注釈値は変更されず、エラーは発生しません。ALTER TABLE Table1 ANNOTATIONS(ADD IF NOT EXISTS JoinOperations 'Join Ops');
ALTER TABLE Table1 ANNOTATIONS(DROP Title);
出力は次のとおりです。
ORA-11553: Annotation name 'TITLE' does not exist.
IF EXISTS
句を使用できます。ALTER TABLE Table1 ANNOTATIONS(DROP IF EXISTS Title);
出力は次のとおりです。
Table altered.
関連項目:
句の完全な変更および定義については、『SQL言語リファレンス』のCREATE TABLEおよびALTER TABLE。
10.2.5.3 表の列に注釈を付けるDDL文
次のDDL文を使用して、表を作成または変更するときに表の列に注釈を付けることができます。
CREATE TABLE
文の使用方法
CREATE TABLE
文を使用して列レベルの注釈を追加するには、column_definition
句の一部として注釈を指定します。注釈は、末尾のインライン制約の後に指定されます。
次の例では、表作成時に列の注釈を指定します。
CREATE TABLE Table1 (T NUMBER ANNOTATIONS(Operations 'Sort', Hidden)); CREATE TABLE Table2 (T NUMBER ANNOTATIONS (Hidden));
次の例では、Employee
表に表レベルと列レベルの注釈を指定します。
CREATE TABLE Employee ( Id NUMBER(5) ANNOTATIONS(Identity, Display 'Employee ID', "Group" 'Emp_Info'), Ename VARCHAR2(50) ANNOTATIONS(Display 'Employee Name', "Group" 'Emp_Info'), Sal NUMBER ANNOTATIONS(Display 'Employee Salary', UI_Hidden) ) ANNOTATIONS (Display 'Employee Table');
前の例のEmployee
表には、列レベルとオブジェクト・レベルの注釈Display
があります。この注釈は、列レベルとオブジェクト・レベルで定義されています。新しい注釈は、それに対応するオブジェクトと列のペアが異なっていれば同じ名前で定義できます。たとえば、Employee
表にはDisplay
名が付いた別の注釈を定義することはできませんが、Sal
列に新しい注釈"Group
"を定義することはできます。注釈"Group
"は予約語であるため、二重引用符で囲む必要があります。
ALTER TABLE
文の使用方法
ALTER TABLE
文を使用して列レベルの注釈を追加するには、modify_col_properties
句の一部として注釈を指定します。注釈は、末尾のインライン制約の後に指定されます。
次の例では、Table1
表の列Tに、新しいIdentity
注釈を追加します。
ALTER TABLE Table1 MODIFY T ANNOTATIONS(Identity 'ID');
次の例では、Label
注釈を追加して、Identity
注釈を削除します。
ALTER TABLE Table1 MODIFY T ANNOTATIONS(ADD Label, DROP Identity);
関連項目:
句の完全な変更および定義については、『SQL言語リファレンス』のCREATE TABLEおよびALTER TABLE。
10.2.5.4 ビューおよびマテリアライズド・ビューに注釈を付けるDDL文
次のDDL文を使用して、ビューおよびマテリアライズド・ビューに注釈を付けることができます。
ビューおよびマテリアライズド・ビューは、ビュー・レベルおよび列レベルで注釈をサポートしています。列レベルの注釈は、列別名定義句の一部として表のビューでのみサポートされています。
CREATE VIEW
文の使用方法
次の例では、ビュー・レベルおよび列レベルの注釈を示します。
CREATE OR REPLACE VIEW HighWageEmp ( Id ANNOTATIONS(Identity, Display 'Employee ID', "Group" 'Emp_Info'), Ename ANNOTATIONS (Display 'Employee Name', "Group" 'Emp_Info'), Sal ANNOTATIONS (Display 'Emp Salary') ) ANNOTATIONS (Title 'High Wage Employee View') AS SELECT * FROM EMPLOYEE WHERE Sal > 100000;
CREATE MATERIALIZED VIEW
文の使用方法
次の例では、Materialized View
文でビュー・レベルの注釈を追加します:
CREATE MATERIALIZED VIEW MView1 ANNOTATIONS (Title 'Tab1 MV1', ADD Snapshot) AS SELECT * FROM Table1;
次の例では、Materialized View
文でビュー・レベルおよび列レベルの注釈を追加します:
CREATE MATERIALIZED VIEW MView1( T ANNOTATIONS (Hidden)) ANNOTATIONS (Title 'Tab1 MV1', ADD Snapshot) AS SELECT * FROM Table1;
ALTER VIEW
文の使用方法
注釈をサポートするために、ALTER VIEW
文に新しい副句が追加され、ビュー・レベルで注釈を変更できます。ALTER VIEW
文でサポートされている他の副句には、ビューの制約の変更、再コンパイルの有効化およびEDITIONABLE
プロパティの変更があります。
ビューの列レベルの注釈は変更できません。以前に追加された列レベルの注釈は、ビューを削除し、新しいものを再作成することによってのみ削除できます。
次の例は、Title
注釈を削除して、ビュー・レベルでIdentity
注釈を追加するALTER VIEW
文です。
ALTER VIEW HighWageEmp ANNOTATIONS(DROP Title, ADD Identity);
ALTER MATERIALIZED VIEW
文の使用方法
ALTER MATERIALIZED VIEW
文には、マテリアライズド・ビュー・レベルで注釈をグローバルに変更するために追加された新しい副句があります。列レベルの注釈は、マテリアライズド・ビューを削除して再作成することによってのみ削除できます。
次のALTER MATERIALIZED VIEW
文では、MView1
からSnapshot
注釈を削除します。
ALTER MATERIALIZED VIEW MView1 ANNOTATIONS(DROP Snapshot);
関連項目:
句の完全な変更および定義については、『SQL言語リファレンス』のCREATE VIEW、ALTER VIEW、CREATE MATERIALIZED VIEWおよびALTER MATERIALIZED VIEW。
10.2.5.5 索引に注釈を付けるDDL文
次のDDL文を使用して、索引に注釈を付けることができます。
CREATE INDEX
文の使用方法
次に、索引レベルの注釈の作成例を示します。
CREATE TABLE DEPARTMENT( DEPT_ID NUMBER, UNIT NUMBER); CREATE INDEX I_DEPT_ID ON DEPARTMENT(DEPT_ID) ANNOTATIONS(Display 'Department Index'); CREATE UNIQUE INDEX UI_UNIT ON DEPARTMENT(UNIT) ANNOTATIONS(Display 'Department Unique Index');
ALTER INDEX
文の使用方法
次に、索引レベルの注釈の変更例を示します。
ALTER INDEX I_DEPT_ID ANNOTATIONS(DROP Display, ADD ColumnGroup 'Group1');
関連項目:
句の完全な変更および定義については、『SQL言語リファレンス』のCREATE INDEXおよびALTER INDEX。
10.2.5.6 ドメインに注釈を付けるDDL文
次のDDL文を使用して、ドメインに注釈を付けることができます。
ドメインの注釈は、ドメイン・レベルまたは列レベルで指定できます。ドメインで定義された注釈は、そのドメインを参照するオブジェクトに継承されます。注釈は、通常のドメインにのみ使用できます。フレキシブル・ドメインには使用できません。
単一列ドメインのドメイン・レベルの注釈を指定するには、列レベルの注釈とオブジェクト・レベルの注釈を区別するために、カッコ付きの構文(複数列ドメインに使用)が必要です。それ以外の場合、単一列ドメインの注釈は列レベルとみなされます。
CREATE DOMAIN
文の使用方法
次の例では、単一列ドメインに列レベルの注釈を指定することで、ドメイン注釈を作成します。
CREATE DOMAIN dept_codes_1 AS NUMBER(3) CONSTRAINT dept_chk_1 CHECK (dept_codes_1 > 99 AND dept_codes_1 != 200) ANNOTATIONS (Title 'Column level annotation');
次の例では、単一列ドメインにドメイン・レベルの注釈を指定します。これには、複数列ドメインに対応するドメイン構文を使用する必要があります(列にカッコを使用します)。
CREATE DOMAIN dept_codes_2 AS ( code AS NUMBER(3) CONSTRAINT dept_chk_2 CHECK (code > 99 AND code != 200)) ANNOTATIONS (Title 'Domain Annotation');
CREATE DOMAIN HourlyWages AS Number(10) DEFAULT ON NULL 15 CONSTRAINT MinimalWage CHECK (HourlyWages > = 7 and HourlyWages <=1000) ENABLE DISPLAY TO_CHAR(HourlyWages, '$999.99') ORDER ( -1*HourlyWages ) ANNOTATIONS (Title 'Column level annotation');
次の例では、列レベルとドメイン・レベルの注釈がある複数列ドメインを作成します。
CREATE DOMAIN US_City AS ( name AS VARCHAR2(50) ANNOTATIONS (Address), state AS VARCHAR2(50) ANNOTATIONS (Address), zip AS NUMBER ANNOTATIONS (Address) ) CONSTRAINT City_CK CHECK(state in ('CA','AZ','TX') and zip < 100000) DISPLAY name || ', ' || state || ' , ' || TO_CHAR(zip) ORDER state || ', ' || TO_CHAR(zip) || ', ' || name ANNOTATIONS (Title 'Domain Annotation');
ALTER DOMAIN
文の使用方法
オブジェクト・レベルの注釈は、ALTER
文で変更できます。ドメインの列レベルの注釈は変更できません。以前に追加された列レベルの注釈は、ドメインを削除し、新しいものを再作成することによってのみ削除できます。
次の例では、dept_codes_2
ドメインのドメイン・レベルの注釈を変更します。
ALTER DOMAIN dept_codes_2 ANNOTATIONS(DROP Title, ADD Name 'Domain');
関連項目:
句の完全な変更および定義については、『SQL言語リファレンス』のCREATE DOMAINおよびALTER DOMAIN。
10.2.5.7 ディクショナリ表およびディクショナリ・ビュー
ANNOTATIONS_USAGE$
というディクショナリ表には、表やビューなどのスキーマ・オブジェクトでの注釈の使用がすべて含まれます。スキーマ・オブジェクトに新しい注釈名、値あるいはその両方を指定すると、ANNOTATIONS_USAGE$
表に新しいエントリが作成されます。同様に、スキーマ・オブジェクトで注釈が削除されると、対応するエントリがANNOTATIONS_USAGE$
表から削除されます。
次のディクショナリ・ビューでは、すべてのスキーマ・オブジェクトにわたって注釈とその使用のリストが追跡されます。
-
{DBA|USER|ALL|CDB}_ANNOTATIONS
-
{DBA|USER|ALL|CDB}_ANNOTATIONS_USAGE
-
{DBA|USER|ALL|CDB}_ANNOTATIONS_VALUES
10.2.5.7.1 ディクショナリ・ビューの問合せ
ディクショナリ・ビューに対して問合せを実行し、特定のスキーマ・オブジェクトに使用される注釈のリストを取得できます。
'EMP'表に対して発行された問合せ文の例を次に示します。
SELECT * FROM USER_ANNOTATIONS_USAGE WHERE Object_Name = 'EMPLOYEE' AND Object_Type = 'TABLE' AND Column_Name IS NULL;
SELECT * FROM USER_ANNOTATIONS_USAGE WHERE Object_Name = 'EMPLOYEE' AND Object_Type = 'TABLE' AND Column_Name IS NOT NULL;
SELECT U.Column_Name, JSON_ARRAYAGG(JSON_OBJECT(U.Annotation_Name, U.Annotation_Value)) FROM USER_ANNOTATIONS_USAGE U WHERE Object_Name = 'EMPLOYEE' AND Object_Type = 'TABLE' AND Column_Name IS NOT NULL GROUP BY Column_Name;