Oracleのバックアップとリストア

1月11日のエントリでもちらとふれたこの件、ようやく今日バックアップとリストアの試験を実施しました。
導入しているNetbackupを使えば自動でできるはずなんだけどなぁ。なんだかうまくいかないし、このあたりがブラックボックスになっているのも気持ちがわるいので、大昔に習得した原始的な方法でバックアップすることに。最終的には2つのSQL文と、1つのシェルファイルからなるバックアップスクリプトを作りました。

このあたりは自分あてのメモですね。

バックアップ

バックアップ対象のインスタンスはすでにアーカイブログモードで動作しているものとします。sqlplusでこんなコマンドを叩けばいいみたい。

SQL> ALTER DATABASE ARCHIVELOG;

バックアップが必要なものは、以下の4つ。

データファイル

テーブルスペースごとにバックアップモードに移行してからバックアップを実施します。対象になるインスタンスにどんなテーブルスペースがあるかは、こんなSQL文で調べられます。

SQL> select name from v$tablespace ;

今回実験したインスタンスでは29もあったので、こんなSQL文を別ファイルに作り、一度にバックアップモードに移行します。
まず、バックアップモードに移行するSQLファイルを用意して、

alter tablespace SYSTEM begin backup ;
alter tablespace RBS begin backup ;
alter tablespace TEMP begin backup ;
alter tablespace INDX begin backup ;
alter tablespace USERS begin backup ;
(中略)
quit ;

これをsqlplusに食わせる。

$ sqlplus 'system/password as sysdba' @beginbackup.sql

このfilename.sqlが上記で作ったSQL文のファイル名ですね。
次にバックアップをとるべきデータファイル名を調べます。

SQL> select name from v$datafile ;

これで出てくるファイル名をすべてバックアップ(テープに採ったり、別ディレクトリにコピーしたり)します。
このバックアップが終了したら、各テーブルスペースに対してバックアップモードを終了させます。こんなSQL文を用意して、

alter tablespace SYSTEM end backup ;
alter tablespace RBS end backup ;
alter tablespace TEMP end backup ;
alter tablespace INDX end backup ;
alter tablespace USERS end backup ;
(中略)
quit;

上記と同じようにsqlplusに食わせます。

$ sqlplus 'system/password as sysdba' @endbackup.sql

アーカイブログファイル

アーカイブログファイルをバックアップする前に、一瞬だけアーカイブを停止します。停止した瞬間にlsコマンドを使って現在存在するアーカイブログファイルのリストをシェル変数に保存、アーカイブを復活させてからアーカイブログファイルをバックアップします。
アーカイブ先はこんなコマンドで調べられます。

SQL> archive log list 

実際のバックアップシェルではこんな感じ。

sqlplus /nolog <<EOF
    conn system/password as sysdba ;
    archive log stop
    exit ;
EOF

archivefile=`ls /home/instance_name/arch/*`

sqlplus /nolog <<EOF
    conn system/password as sysdba ;
    archive log start
    exit ;
EOF

/usr/local/bin/tar -zcvf /back/up/dist/archive.ta.gz $archivefile

redoログファイル

なんだかいろんな本を読むと、リストアにはredoログファイルは必要ないなんて書いてあるのもあるんですが、経験上絶対必要。こいつらのバックアップには特段注意は必要ありません。
どこにファイルがあるかはこんなコマンドで調べられます。

SQL> select member from v$logfile ;

これで調べたファイルをバックアップします。

/usr/local/bin/tar -zcvf /back/up/dist/redolog.tar.gz 

コントロールファイル

最後にコントロールファイル。コントロールファイルがなくなったときなんかには必要ですね。あと、まったく別の環境にデータを移すときなんかにも使います(そういう時はexpを使ったほうがいいか)。

sqlplusでバックアップを作成します。

SQL> alter database backup controlfile to '/back/up/dist/controlfile.bak'
SQL> alter database backup controlfile to trace as '/back/up/dist/controlfile.trc'

参考シェル

でもって、作ったシェルはこんな感じ。

#!/usr/bin/bash
export ORACLE_SID=インスタンス名
export ORACLE_BASE=この辺は適切に設定する
export ORACLE_HOME=この辺は適切に設定する
export PATH=パスも適当に設定する

datestr=`date '+%y%m%d'`

#バックアップ先のディレクトリを作成する。
#日付ごとにディレクトリを作成する。Ex. 070130とか
mkdir /back/up/dist/$datestr

#バックアップモードに移行する。
sqlplus 'system/manager as sysdba' @startbackup.sql

#データファイルをバックアップする。
/usr/local/bin/tar -zcvf /back/up/dist/$datestr/datafiles.tar.gz   \
    データファイル1  \
    データファイル2     \
  (中略:必要なデータファイルを全部かく)
    データファイルn

sqlplus 'system/password as sysdba' @endbackup.sql

#アーカイブを停止
sqlplus /nolog <<EOF
    conn system/manager as sysdba ;
    archive log stop
    exit ;
EOF

#いま現在あるアーカイブファイルのリストを取得する。
archivefile=`ls /hoge/INSTANCE/arch/*`

#アーカイブを開始
sqlplus /nolog <<EOF
    conn system/password as sysdba ;
    archive log start
    exit ;
EOF

#アーカイブログをバックアップする。
/usr/local/bin/tar -zcvf /back/up/dist/$datestr/archivefiles.tar.gz $archivefile

#redoログファイルをバックアップする。
/usr/local/bin/tar -zcvf /back/up/dist/$datestr/redofiles.tar.gz \
    redoログファイル1            \
    redoログファイル2     

sqlplus /nolog <<EOF
    conn system/password as sysdba ;
    alter database backup controlfile to '/back/up/dist/$datestr/controlfile.bak' ;
    alter database backup controlfile to trace as '/back/up/dist/$datestr/controlfile.trc' ;
    exit ;
EOF

本来ならば、バックアップしなければいけないファイル名なんかも全部sqlplusで調べて全自動にできるはずなんですが、途中で力尽きました(泣)。

リストアの手順も一日のエントリで書こうかと思っていたんですが、ちょっと長くなりそうなので明日にします。