転職を繰り返したサラリーマンの多趣味ブログ

30才未経験でSEに転職した人の多趣味ブログ

【技術書メモ】基礎からのサーブレット⑬

データベース

データベース・・・検索や更新などが行いやすい形式に整理されたデータの集まり。
データベース管理システム・・・データベースを構築したり操作したりするためのソフトウェア

・接続文字列について
以下のような形式で記述することで、システムに登録されたJDBCドライバの中から、適切なドライバが選択される。

jdbc:サブプロトコル:サブネーム

サブプロトコル:h2、oracleなどのデータベース製品を指定。
サブネーム:データベース製品ごとに記法が異なる。h2をWebアプリケーションで利用する場合は、以下のように記載する。
tcp://ホスト名/データベースの保存先/データベース名

例:
tcp://localhost/~/book
ユーザー/ユーザ名/book.mv.dbというファイルが作られ、データベースが保存される。

JDBC

JDBC・・・Javaからデータベースを操作するためのAPIJavaプログラムからRDBMSSQL文を発行、結果を取得できる。
JDBCの利点は、データベース間の違いを吸収してくれるため、データベースによってプログラムを書き換えなくていい点。
そのため、データベース毎にJDBCのドライバが存在する。

データソース

データソース・・・アプリケーションサーバを利用してデータベースに接続する仕組み。
接続情報を設定ファイルに記述できるため、管理がしやすい。データソースを使用しない場合は、以下のようにソースに記述する必要がある。

Class.forName("JDBCのクラス名");
Connection conn = DriverManager.getConnection("接続文字列","ユーザ名","パスワード");

また、コネクションプールで、データベースの接続を再利用できる。
JDBCを使ったデータベースアクセスは、データソースの操作を行うたびに接続と切断を繰り返し、処理時間がかかってしまう。

コネクションプール

あらかじめ複数コネクションが用意されており、データベース接続の際は新規にコネクションを作成せずに、既存のコネクションを取得する。
データベースの接続を終えたら、使用したコネクションをコネクションプールに戻す。結果、処理時間の短縮につながる。

データソースを利用するには、context.xmlの設定が必要。
Eclipseを使用している場合の配置場所は、~/WebContent/META-INF/context.xml

<Context reloadable = "true">
	<Resource
		name="jdbc/book"
		auth="Container"
		type="javax.sql.DataSource"
		driverClassName="org.h2.Driver"
		url="jdbc:h2:tcp://localhost/~/book"
		username="sa"
		password=""
	/>
</Context>

name・・・データソースの名前
auth・・・Containerを指定すると、Webコンテナ(Tomcat)が認証の処理を行う
type・・・リソースのクラス名またはインタフェース名
driverClassname・・・JDBCドライバのクラス名
url・・・接続文字列
username・・・ユーザ名
password・・・パスワード

Javaとデータベースの連携プログラム

事前にJDBCドライバの導入が必要。
~/WebContents/WEB-INF/lib/h2-1.4.194.jar

@WebServlet(urlPatterns={"/chapter14/all"})
public class All extends HttpServlet {

	@Override
	public void doGet (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

		PrintWriter out=response.getWriter();
		Page.header(out);

		try {

			// JNDIを使用するために、InitialContextクラスのオブジェクト生成
			// JNDIは、データやオブジェクトを名前で参照するためのAPI
			// データソース名を指定し、コネクションプールからコネクションを取得するためにJNDIを使用
			InitialContext ic=new InitialContext();

			// データソースの取得
			// 引数には、context.xmlのname属性に指定した値を設定
			DataSource ds=(DataSource)ic.lookup("java:/comp/env/jdbc/book");

			// Connectionオブジェクトの取得
			Connection con=ds.getConnection();

			// SQL文の指定
			PreparedStatement st=con.prepareStatement("select * from product");

			// SQL文の実行
			ResultSet rs=st.executeQuery();

			// SQLの結果が、ResultSetオブジェクトで返却される
			// 値の取得には、カーソル(現在処理中の行を特定するための仕組み)を利用
			// ResultSetクラスのnextメソッドで、カーソルを1行目から1行ずつ移動する
			while (rs.next()) {
				out.println(rs.getInt("id"));
				out.println(":");
				out.println(rs.getString("name"));
				out.println(":");
				out.println(rs.getInt("price"));
				out.println("<br>");
			}

			// データベースからの切断
			// ResultSetクラスは、PreparedStatemntクラスがクローズされると自動的にクローズされるため省略可
			st.close();
			con.close();

		} catch (Exception e) {
			e.printStackTrace(out);
		}

		Page.footer(out);

	}
}