はじめに
データベースを操作していると、データベース間でデータをコピーする作業が必要になることがよくあります。これは単純な作業のように思えますが、単なるコピーだけでは済まないことも少なくありません。たとえば、データの一部だけを移動したい場合や、コピーの際にデータを変更したい場合があります。本稿では、私が「データムーバー」(DataMover)と呼んでいる簡単なアプリケーションを使って、基本的なデータベースのコピー(データベース間のテーブルの移動)を実行する一連のクラスを紹介します。このサンプルは、データベース全体をコピーする方法を示す叩き台にすぎませんが、コードに手を加えることにより、必要に応じて個別のテーブルまたは特定のテーブルの行や列をコピーするなど、望みどおりのデータコピー/変換操作を実行できることが分かるでしょう。
本稿では、JDBC(Java Database Connectivity)の扱いに不慣れな方のために、入門編として、次のようなJDBCの基本的な使い方を説明します。
- データベースへの接続を開く
- クエリを作成して発行する
- クエリによって返される
ResultSetを処理する
さらに、データベースにクエリを発行し、データベースの構造に関する情報を収集する方法についても説明します。これにより、DataMoverユーティリティを使ってデータベースに関する情報を収集し、データベースをコピーできるようになります。DataMoverは、次の4段階の手順に沿って処理を実行します。
- コピー先のテーブルを作成するSQL(
CREATE TABLE文)を生成する - 既存のテーブルを削除するSQLを生成する
- コピー元のテーブルからデータを選択(
SELECT)するSQLを生成する - コピー先のテーブルにデータを挿入(
INSERT)するSQLを生成する
DataMoverアプリケーションをプログラムする詳しい方法を説明する前に、このアプリケーションを使ってデータベースをコピーする方法を説明します。
DataMoverを使ってデータベースをコピーする
本稿のダウンロードサンプルには、DataMoverUtilityという簡単なユーティリティが含まれています。このユーティリティは設定ファイルを読み取り、コピー元データベースのデータをコピー先データベースにコピーします。
ユーティリティを実行するには、まず設定ファイルを作成する必要があります。このファイルには、4行のデータを記述します。たとえば、DataMoverをテストするために、私は次のような設定ファイルを使いました。
sourceDriver=com.mysql.jdbc.Driver sourceURL=jdbc:mysql://127.0.0.1/test?user=root targetDriver=com.mysql.jdbc.Driver targetURL=jdbc:mysql://127.0.0.1/test2?user=root
この設定ファイルでは、MySQLデータベース間でデータをコピーすることを指定しています。データベースは両方ともローカルコンピュータ(127.0.0.1)上にあるという前提です。JDBCのデータベースごとに、ドライバと接続URLを指定する必要があります。sourceDriverとsourceURLには、コピー元データベースのドライバとURLを指定します。同様に、targetDriverとtargetURLには、コピー先データベースの情報を指定します。
DataMoverユーティリティを実行するときに、この設定ファイルを最初のパラメータとして指定します。たとえば次のように指定します。
java DataMoverUtility c:\export.txt
MySQLをJavaで使用する
JDBCアプリケーションをコンパイルして使用する前に、使用するデータベースのドライバをインストールする必要があります。通常は、ドライバのJARファイルをプロジェクトのクラスパスに追加するだけです。
本稿では、MySQLを使用するという前提で話を進めます。ただし、ここで示すコードはほとんどのデータベースと非常に高い互換性があります。MySQLに固有と考えられる部分は、すべて「MySQL.java」クラスファイルにまとめられています。他のデータベースを使う場合は、単純にDatabaseクラスを拡張し、そのデータベース特有のコードを追加します。
MySQLでは、Connector/Jドライバを使います。これはwww.mysql.orgからダウンロードできます。パッケージにJARファイルが含まれているので、それをクラスパスに追加します。これでMySQLデータベースに接続する準備は完了です。
DataMoverの構造
DataMoverは、主要な2つのパッケージから成ります。com.heatonresearch.datamoverという名前のパッケージには、DataMoverクラスとDataMoverUtilityクラスが含まれています。DataMoverクラスには、データベース間のテーブルコピーを実行したり、より高度な操作を実装するときの叩き台になったりする再利用可能な関数がいくつか含まれます。DataMoverUtilityクラスは、本稿で紹介するクラスの使い方の一例です。
com.heatonresearch.datamover.dbという名前のパッケージには、下位レベルのすべてのデータベースクラスが含まれています。本稿では、DatabaseException、Database、およびMySQLの3つのクラスを使用します。DatabaseExceptionクラスは、データベースの問題が発生したときにDataMoverがスローする例外を定義します。Databaseクラスは、データベースアクセスのためのすべての基本関数を提供します。MySQLクラスはDatabaseクラスを継承し、MySQL固有のコードを実装します。このMySQLクラスと同様に、Databaseクラスから新しいデータベースクラスを派生させることにより、このクラスライブラリを拡張して別のデータベースを扱うことができます。
MySQLに接続する
どのような操作を行うにも、まずデータベースに接続する必要があります。JDBC経由でデータベースに接続するには、2つの情報を知っておく必要があります。JDBCドライバ名と、データベースURLです。
JDBCドライバ名は、単なるクラス名です。MySQLでは、クラスは以前にインストールしたMySQL JARファイルによって提供されます。データベースURLでは、データベースの名前、場所、および使用するユーザーを指定します。データベースへの接続を開くには、Databaseクラスのconnectメソッドを使います。次のコードは、connectメソッドの実装コードのうち、データベースに接続する部分を示しています。
try { Class.forName(driver).newInstance(); connection = DriverManager.getConnection(url); } catch (InstantiationException e) { throw new DatabaseException(e); } catch (IllegalAccessException e) { throw new DatabaseException(e); } catch (ClassNotFoundException e) { throw new DatabaseException(e); } catch (SQLException e) { throw new DatabaseException(e); }
コードの最初の2行で、ドライバとURLを処理しています。残りの行では、データベースを開くときに起こりうるいろいろな例外を処理しています。いずれかの例外が発生した場合は、その例外をDatabaseExceptionとしてパッケージ化してスローします。
