~mv_products を用いたリフレッシュ操作と運用のポイント~
🔷 この記事の目的
本記事では、前回作成したマテリアライズド・ビュー mv_products を例に、Oracle Database における リフレッシュ(REFRESH)機能の仕組み・操作方法・注意点 を徹底的に解説します。
今回は、ベース表へのデータ追加も DBリンク経由で実施する方法を取り入れ、実務に即した内容に仕上げています。
🔔 補足:マテリアライズド・ビュー・ログ(MVログ)を用いた差分更新(FAST REFRESH)については、次回の記事で詳しく解説します。
🔷 構成のおさらい(対象MV)
CREATE MATERIALIZED VIEW mv_products
REFRESH ON DEMAND
AS
SELECT * FROM products@pdb02_link;
- 作成場所:PDB01(参照側)
- 参照元:PDB02(提供側)の
products表(DBリンク経由) - 更新方式:ON DEMAND(必要時に手動で更新)
🔷 リフレッシュとは何か?
リフレッシュとは、マテリアライズドビューが保持しているキャッシュデータを最新状態に更新する処理です。
┌────────────┐
│ ベース表 │ ← INSERT/UPDATE/DELETE
└────────────┘
│
(時間差あり)
▼
┌────────────┐
│ MV(古いデータ)│
└────────────┘
│
DBMS_MVIEW.REFRESH
▼
┌────────────┐
│ MV(最新状態) │
└────────────┘
🔷 リフレッシュの種類
OracleのMVリフレッシュには、以下の方式があります:
| リフレッシュタイプ | 内容 | 使用条件 |
|---|---|---|
| COMPLETE | MV全体を再作成(全件取得) | すべてのMVで使用可能 |
| FAST | 差分のみ更新(MVログ使用) | MVログが必要(※) |
| FORCE | FASTが可能ならFAST、無理ならCOMPLETE | デフォルト設定 |
※ 今回の
mv_productsは FAST REFRESH 未対応(MVログ未作成)
よって、REFRESHは COMPLETE方式 で行われます。
💡 MVログの作成とFAST REFRESHの手順は、次回の記事で解説予定です。
🔷 手動リフレッシュの実行方法
▼ DBMS_MVIEWパッケージを使う
-- デフォルト(FORCE)
EXEC DBMS_MVIEW.REFRESH('MV_PRODUCTS');
-- 明示的にCOMPLETE方式で実行
EXEC DBMS_MVIEW.REFRESH('MV_PRODUCTS', 'C');
-- 明示的にFAST(MVログありの場合)
EXEC DBMS_MVIEW.REFRESH('MV_PRODUCTS', 'F');
🔷 DBリンク経由でのデータ追加 → REFRESH 例
▼ 現在の状態確認(リフレッシュ前)
-- ローカル側(PDB01)のマテビュー確認
SELECT * FROM mv_products;
出力例(初期状態):
PRODUCT_ID PRODUCT_NAME PRICE
----------- ------------- -----
1 Keyboard 4000
2 Mouse 2500
3 Monitor 18000
▼ DBリンク経由でベース表に行を追加
-- DBリンク経由でリモートのproducts表にINSERT
INSERT INTO products@pdb02_link VALUES (4, 'Headset', 5500);
COMMIT;
🔎 この操作は、DBリンク先ユーザーにINSERT権限があることが前提です。
本記事の構成では、PDB02側でもhrユーザーを使っており、同一スキーマに対する操作が許可されています。
▼ マテビューをリフレッシュして反映確認
-- MVのリフレッシュ実行(COMPLETE方式)
EXEC DBMS_MVIEW.REFRESH('MV_PRODUCTS');
-- MVの最新内容確認
SELECT * FROM mv_products;
出力例(リフレッシュ後):
PRODUCT_ID PRODUCT_NAME PRICE
----------- ------------- -----
1 Keyboard 4000
2 Mouse 2500
3 Monitor 18000
4 Headset 5500 ← DBリンク越しに追加したデータが反映された!
✅ DBリンク越しの操作でも REFRESH により MV にデータが取り込まれることが確認できます。
🔷 REFRESH動作の内部的な流れ(COMPLETE)
1. MV表の全データ削除(DELETE)
2. DBリンクを使って最新データ取得(SELECT)
3. ローカルにINSERT(再構築)
このため、以下のような影響があります:
- 一時的にMVが空になる時間帯が存在
- ネットワーク越しのSELECTに遅延が発生する場合がある
- UNDOやTEMPの消費が発生する(大規模MVでは注意)
🔷 REFRESH状態の確認SQL
-- 最終リフレッシュ時刻を確認
SELECT MVIEW_NAME, LAST_REFRESH_TYPE, TO_CHAR(LAST_REFRESH_DATE, 'YYYY-MM-DD HH24:MI:SS') AS LAST_REFRESH
FROM USER_MVIEWS
WHERE MVIEW_NAME = 'MV_PRODUCTS';
出力例:
MVIEW_NAME LAST_REFRESH_TYPE LAST_REFRESH
------------ ------------------ ---------------------
MV_PRODUCTS COMPLETE 2025-07-11 14:45:22
🔷 自動リフレッシュ設定の例(補足)
BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'MV_REFRESH_JOB',
job_type => 'PLSQL_BLOCK',
job_action => 'BEGIN DBMS_MVIEW.REFRESH(''MV_PRODUCTS''); END;',
start_date => SYSTIMESTAMP,
repeat_interval => 'FREQ=HOURLY; INTERVAL=1',
enabled => TRUE
);
END;
/
1時間ごとに自動で mv_products を更新する設定です。
🔷 注意点まとめ
| 項目 | 注意点 |
|---|---|
| データ整合性 | COMPLETE方式では一時的にMVが空になる可能性あり |
| ネットワーク依存 | DBリンク経由のリフレッシュは通信エラーに注意 |
| リモート表へのDML | INSERT/UPDATE/DELETEには相応の権限が必要 |
| MVの無効化 | ベース表の構造変更(列削除など)でMVがINVALIDになる |
🔷 まとめ
マテリアライズド・ビューの運用において、リフレッシュは性能と整合性のバランスを取るための重要な要素です。
✅ 小規模データ:COMPLETE方式でも問題なし
✅ 頻繁な変更や大規模データ:FAST方式+MVログを検討
✅ DBリンク環境下でもREFRESHは確実に有効
マテビューのリフレッシュ設計を適切に行うことで、パフォーマンスと信頼性の高いシステム運用が実現できます。
[参考]
5 基本的なマテリアライズド・ビュー


コメント