データベース

Oracle Database

概要

Oracle Databaseは、企業向けに設計された世界最高峰のリレーショナルデータベース管理システムです。高い信頼性、スケーラビリティ、セキュリティ機能を提供し、ミッションクリティカルなアプリケーションでの使用に最適化されています。金融、政府、大企業で広く採用されている業界標準のデータベースです。

詳細

Oracle Databaseは1979年にラリー・エリソンらによって開発が開始され、40年以上にわたる継続的な進化により、現在では以下の特徴を持つ包括的なデータベース・プラットフォームとなっています。

主要特徴

  • Autonomous Database: 自動化された管理、パッチ適用、チューニング
  • In-Memory Computing: メモリ内処理による超高速クエリ実行
  • Multitenant Architecture: コンテナ・データベース(CDB)とプラガブル・データベース(PDB)
  • Advanced Security: 透明なデータ暗号化、データマスキング、監査機能
  • Real Application Clusters (RAC): アクティブ-アクティブクラスタリング
  • Advanced Analytics: 機械学習、グラフ分析、空間データ処理
  • JSON and XML: NoSQLデータの完全サポート
  • Blockchain Tables: 改ざん防止機能付きテーブル

アーキテクチャ

  • System Global Area (SGA): 共有メモリ領域
  • Process Global Area (PGA): プロセス専用メモリ領域
  • Background Processes: PMON、SMON、DBWR、LGWR等
  • Oracle Net Services: ネットワーク通信とセキュリティ
  • Automatic Storage Management (ASM): ストレージ自動管理

エディション構成

  • Oracle Database Free: 開発・学習用無料版
  • Standard Edition: 中小企業向け
  • Enterprise Edition: 企業向け高機能版
  • Autonomous Database: クラウド最適化版

メリット・デメリット

メリット

  • 最高レベルの信頼性: エンタープライズグレードの可用性とデータ整合性
  • 優秀なパフォーマンス: In-Memoryテクノロジーによる高速処理
  • 包括的な機能: 分析、AI/ML、ブロックチェーン等の先進機能
  • 強力なセキュリティ: 多層防御とコンプライアンス機能
  • 豊富なツール: Oracle SQL Developer、Enterprise Manager等
  • 成熟したエコシステム: 豊富なサードパーティツールとベンダーサポート
  • 専門サポート: Oracleによる24/7エンタープライズサポート

デメリット

  • 高いコスト: ライセンス費用と保守費用が高額
  • 複雑な管理: 設定・チューニングに専門知識が必要
  • ベンダーロックイン: Oracle固有の機能に依存するリスク
  • リソース消費: 大量のメモリとストレージを必要とする
  • 学習コストの高さ: 習得に時間と投資が必要
  • ライセンス複雑性: 複雑なライセンス体系と監査リスク

主要リンク

書き方の例

インストール・セットアップ

# Oracle Database Free (Linux)
dnf install oracle-database-free-23c
/etc/init.d/oracle-db-free-23c configure

# Docker環境
docker pull container-registry.oracle.com/database/free:latest
docker run --name oracle-free \
  -p 1521:1521 -p 5500:5500 \
  -e ORACLE_PWD=mypassword \
  container-registry.oracle.com/database/free:latest

# 環境変数設定
export ORACLE_HOME=/opt/oracle/product/23c/dbhome_1
export ORACLE_SID=FREE
export PATH=$ORACLE_HOME/bin:$PATH

# SQLPlusでの接続
sqlplus sys/password@localhost:1521/FREE as sysdba

基本操作(CRUD)

-- 表領域とユーザー作成
CREATE TABLESPACE company_data
DATAFILE 'company_data.dbf' SIZE 100M AUTOEXTEND ON;

CREATE USER company_user IDENTIFIED BY strongpassword
DEFAULT TABLESPACE company_data;

GRANT CONNECT, RESOURCE TO company_user;

-- 接続とテーブル作成
CONNECT company_user/strongpassword@localhost:1521/FREE;

CREATE TABLE employees (
    employee_id NUMBER(10) PRIMARY KEY,
    first_name VARCHAR2(50) NOT NULL,
    last_name VARCHAR2(50) NOT NULL,
    email VARCHAR2(100) UNIQUE,
    hire_date DATE DEFAULT SYSDATE,
    salary NUMBER(10,2),
    department_id NUMBER(10)
);

-- シーケンス作成
CREATE SEQUENCE emp_seq START WITH 1 INCREMENT BY 1;

-- データ挿入
INSERT INTO employees VALUES (
    emp_seq.NEXTVAL, '太郎', '田中', '[email protected]', 
    SYSDATE, 75000, 100
);

-- データ選択
SELECT employee_id, first_name || ' ' || last_name AS full_name,
       email, hire_date, salary
FROM employees
WHERE department_id = 100;

-- データ更新
UPDATE employees 
SET salary = salary * 1.1 
WHERE hire_date < ADD_MONTHS(SYSDATE, -12);

COMMIT;

データモデリング

-- 外部キー制約付きテーブル設計
CREATE TABLE departments (
    department_id NUMBER(10) PRIMARY KEY,
    department_name VARCHAR2(100) NOT NULL,
    manager_id NUMBER(10),
    location_id NUMBER(10)
);

CREATE TABLE employees (
    employee_id NUMBER(10) PRIMARY KEY,
    first_name VARCHAR2(50) NOT NULL,
    last_name VARCHAR2(50) NOT NULL,
    department_id NUMBER(10),
    CONSTRAINT fk_emp_dept 
        FOREIGN KEY (department_id) 
        REFERENCES departments(department_id)
);

-- JSONサポート
CREATE TABLE customer_data (
    customer_id NUMBER PRIMARY KEY,
    customer_info JSON,
    preferences JSON
);

INSERT INTO customer_data VALUES (
    1,
    JSON_OBJECT('name' VALUE '田中太郎', 'age' VALUE 35, 'city' VALUE '東京'),
    JSON_OBJECT('newsletter' VALUE true, 'language' VALUE 'ja')
);

-- パーティショニング
CREATE TABLE sales_data (
    sale_id NUMBER,
    sale_date DATE,
    customer_id NUMBER,
    amount NUMBER(10,2)
) PARTITION BY RANGE (sale_date) (
    PARTITION sales_2023 VALUES LESS THAN (DATE '2024-01-01'),
    PARTITION sales_2024 VALUES LESS THAN (DATE '2025-01-01'),
    PARTITION sales_future VALUES LESS THAN (MAXVALUE)
);

インデックス・最適化

-- インデックス作成
CREATE INDEX idx_emp_department ON employees(department_id);
CREATE INDEX idx_emp_name ON employees(last_name, first_name);

-- 関数ベースインデックス
CREATE INDEX idx_emp_email_upper ON employees(UPPER(email));

-- ビットマップインデックス
CREATE BITMAP INDEX idx_emp_status ON employees(status);

-- 実行計画の確認
EXPLAIN PLAN FOR
SELECT * FROM employees WHERE department_id = 100;

SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);

-- 統計情報の更新
EXEC DBMS_STATS.GATHER_TABLE_STATS('COMPANY_USER', 'EMPLOYEES');

-- パフォーマンス監視
SELECT sql_text, executions, elapsed_time, cpu_time
FROM v$sql
WHERE executions > 10
ORDER BY elapsed_time DESC;

実用例

-- PL/SQLストアドプロシージャ
CREATE OR REPLACE PROCEDURE calculate_bonus(
    p_department_id IN NUMBER,
    p_bonus_rate IN NUMBER DEFAULT 0.1
) AS
    v_total_bonus NUMBER := 0;
BEGIN
    FOR emp_rec IN (SELECT employee_id, salary FROM employees 
                    WHERE department_id = p_department_id) LOOP
        UPDATE employees 
        SET bonus = salary * p_bonus_rate
        WHERE employee_id = emp_rec.employee_id;
        
        v_total_bonus := v_total_bonus + (emp_rec.salary * p_bonus_rate);
    END LOOP;
    
    DBMS_OUTPUT.PUT_LINE('Total bonus allocated: ' || v_total_bonus);
    COMMIT;
END;
/

-- PL/SQLファンクション
CREATE OR REPLACE FUNCTION get_employee_age(p_birth_date DATE)
RETURN NUMBER AS
BEGIN
    RETURN MONTHS_BETWEEN(SYSDATE, p_birth_date) / 12;
END;
/

-- トリガー
CREATE OR REPLACE TRIGGER audit_employee_changes
    AFTER UPDATE ON employees
    FOR EACH ROW
BEGIN
    INSERT INTO employee_audit (
        employee_id, change_date, old_salary, new_salary, changed_by
    ) VALUES (
        :NEW.employee_id, SYSDATE, :OLD.salary, :NEW.salary, USER
    );
END;
/

-- Advanced Queuing (メッセージキュー)
BEGIN
    DBMS_AQADM.CREATE_QUEUE_TABLE('order_queue_table', 'SYS.AQ$_JMS_TEXT_MESSAGE');
    DBMS_AQADM.CREATE_QUEUE('order_queue', 'order_queue_table');
    DBMS_AQADM.START_QUEUE('order_queue');
END;
/

ベストプラクティス

-- データベースリンク
CREATE DATABASE LINK remote_db
CONNECT TO remote_user IDENTIFIED BY password
USING 'remote_host:1521/remote_service';

-- マテリアライズドビュー
CREATE MATERIALIZED VIEW mv_sales_summary
REFRESH FAST ON COMMIT AS
SELECT department_id, SUM(salary) as total_salary, COUNT(*) as emp_count
FROM employees
GROUP BY department_id;

-- セキュリティ設定
-- Transparent Data Encryption
ALTER SYSTEM SET ENCRYPTION KEY IDENTIFIED BY "myencryptionkey";
ALTER TABLE sensitive_data MODIFY (ssn ENCRYPT);

-- 仮想プライベートデータベース (VPD)
CREATE OR REPLACE FUNCTION employee_security_policy(
    schema_var IN VARCHAR2,
    table_var IN VARCHAR2
) RETURN VARCHAR2 AS
BEGIN
    IF USER = 'HR_MANAGER' THEN
        RETURN '1=1';  -- フルアクセス
    ELSE
        RETURN 'department_id = SYS_CONTEXT(''USERENV'', ''CLIENT_IDENTIFIER'')';
    END IF;
END;
/

-- RACでの接続
-- tnsnames.ora設定例
ORCL_RAC = 
  (DESCRIPTION =
    (ADDRESS = (PROTOCOL = TCP)(HOST = node1)(PORT = 1521))
    (ADDRESS = (PROTOCOL = TCP)(HOST = node2)(PORT = 1521))
    (LOAD_BALANCE = yes)
    (CONNECT_DATA =
      (SERVER = DEDICATED)
      (SERVICE_NAME = orcl)
    )
  )