Access SQL Azure with JDBC/Hibernate

前篇文章介紹了如何將Tomcat及Web應用程式部署到Windows Azure,凡事只要起了頭,接下來的工作就相對簡單許多,本篇文章接續前篇,介紹如何透過JDBC來存取SQL Azure。

Access SQL Azure with JDBC/Hibernate

 

/黃忠成

 

 

Using JDBC with SQL Azure

 

  前篇文章介紹了如何將Tomcat及Web應用程式部署到Windows Azure,凡事只要起了頭,接下來的工作就相對簡單許多,本篇文章接續前篇,介紹如何透過JDBC來存取SQL Azure。

  開始之前,請透過Windows Azure的管理網站建立SQL Azure資料庫。

圖1

於其中建立PersonData資料庫,接著建立PERSONS資料表,其結構如下圖。

圖2

接下來只要透過SQL Azure的JDBC Driver便可連結到SQL Azure了,而安裝Windows Azure SDK Plug-In for Eclipse時,附帶安裝了MS SQL Server 的JDBC Driver,

這個Driver也支援SQL Azure所以讀者們不需額外下載,只需將其加入Web Project的Library即可。

圖3

圖4

另外,別忘記當封裝WAR時,除了專案本體外,其餘引用的Library是不會一併封入的,所以必須額外設定。

圖5

圖6

圖7

完成後修改index.jsp來連結至SQL Azure並列出資料庫中的資料。


<%@ page language="java" contentType="text/html; charset=BIG5"
    pageEncoding="BIG5"%>
<%@ page import="java.util.*" %>
<%@ page import="java.sql.*" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=BIG5">
<title>Insert title here</title>
</head>
<body>
<%
try{ 
	Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver");
    Connection con = DriverManager.getConnection("jdbc:sqlserver://c95ouvaxn9.database.windows.net;DatabaseName=PersonData;"+
                                                 user=code6421@c95ouvaxn9;password=...;

    // Create and execute an SQL statement that returns some data.
    String SQL = "SELECT * FROM dbo.PERSONS";
    Statement stmt = con.createStatement();
    ResultSet rs = stmt.executeQuery(SQL);

    // Iterate through the data in the result set and display it.
    while (rs.next()) {
       out.print(rs.getString(1) + " " + rs.getString(2)+"<br/>");
    }

}catch(Exception e){ 
        out.print("Error message: "+ e.getMessage()); 
} 


%>
<b>Hello Azure</b>
</body>
</html>

執行後便可看到結果,為了測試,我事先在PERSONS資料表中添加了一筆資料。

圖8

當然,在Windows Azure模擬器上執行的結果也一樣。

圖9

 

Access SQL Azure with Hibernate

 

   能透過JDBC連結SQL Azure的話,有名的OR Mapping Framework:Hibernate自然也可以使用囉,但過程有些小細節需要注意一下。

  先將Hibernate所需要的Library加入。

圖10

別忘記,Deployment Assembly也要一併處理。

圖11

接著加入Hibernate Configuration檔案。

圖12

圖13

圖14

這裡要注意一下,Hibernate Plug-In(需額外安裝)產生的組態檔對於SQL Server的JDBC Driver描述有誤,需修改如下。


<?xmlversion="1.0"encoding="UTF-8"?>

<!DOCTYPEhibernate-configurationPUBLIC"-//Hibernate/Hibernate Configuration DTD 3.0//EN"

                                         "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">

<hibernate-configuration>

 <session-factory>

  <propertyname="hibernate.connection.driver_class">com.microsoft.sqlserver.jdbc.SQLServerDriver</property>

  <propertyname="hibernate.connection.url">jdbc:sqlserver://c95ouvaxn9.database.windows.net;DatabaseName=PersonData</property>

  <propertyname="hibernate.connection.password">.....</property> 

  <propertyname="hibernate.connection.username">code6421@c95ouvaxn9</property>

  <propertyname="hibernate.default_catalog">dbo</property>

  <propertyname="hibernate.dialect">org.hibernate.dialect.SQLServerDialect</property>

 </session-factory>

</hibernate-configuration>

最大的差異在於driver_class部分,Plug-In產生的是錯誤的。

組態檔修改完後便可以建立Mapping Class。


package com.myazure.mapping;

public class Person {
	private String PERSON_ID;
	
	public String getPERSON_ID() {
		return PERSON_ID;
	}
	public void setPERSON_ID(String pERSON_ID) {
		PERSON_ID = pERSON_ID;
	}
	public String getNAME() {
		return NAME;
	}
	public void setNAME(String nAME) {
		NAME = nAME;
	}
	private String NAME;
}

然後透過Plug-In來產生Mapping檔案。

圖15

最後修改Hibernate Configuration檔案來連結Mapping檔案。


<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
                                         "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
 <session-factory>
  <property name="hibernate.connection.driver_class">com.microsoft.sqlserver.jdbc.SQLServerDriver</property>
  <property name="hibernate.connection.url">jdbc:sqlserver://c95ouvaxn9.database.windows.net;DatabaseName=PersonData</property>
  <property name="hibernate.connection.password">.....</property>  
  <property name="hibernate.connection.username">code6421@c95ouvaxn9</property>
  <property name="hibernate.default_catalog">dbo</property>
  <property name="hibernate.dialect">org.hibernate.dialect.SQLServerDialect</property>
  <mapping resource="com/myazure/mapping/Person.hbm.xml"/>
 </session-factory>
</hibernate-configuration>

緊接著是重頭戲,修改index.jsp如下。


<%@ page language="java" contentType="text/html; charset=BIG5"
    pageEncoding="BIG5"%>
<%@ page import="java.util.*" %>
<%@ page import="java.sql.*" %>
<%@ page import="org.hibernate.Session" %>
<%@ page import="com.myazure.*" %>
<%@ page import="com.myazure.mapping.*" %>
<%@ page import="org.hibernate.Criteria" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=BIG5">
<title>Insert title here</title>
</head>
<body>
<%
try{ 		
	Session sess = HBSessionFactory.getSessionFactory().openSession();
	Criteria criteria = sess.createCriteria(Person.class);        
	Iterator persons = criteria.list().iterator();        
	while(persons.hasNext()) {            
		Person p = (Person)persons.next();
		out.print("ID: " + p.getPERSON_ID()+"<br/>");
		out.print("NAME: " + p.getNAME()+"<br/>"); 
    } 
}catch(Exception e){ 
        out.print("Error message: "+ e.getMessage()); 
} 

%>
<b>Hello Azure</b>
</body>
</html>

完成並執行後,你應該會看到Hibernate抱怨找不到對應的JDBC Driver,這是因為Hibernate 4.12讀取JDBC Driver的方式改變了,解決方法只要手動加上一行Class.forName就可。


<%@ page language="java" contentType="text/html; charset=BIG5"
    pageEncoding="BIG5"%>
<%@ page import="java.util.*" %>
<%@ page import="java.sql.*" %>
<%@ page import="org.hibernate.Session" %>
<%@ page import="com.myazure.*" %>
<%@ page import="com.myazure.mapping.*" %>
<%@ page import="org.hibernate.Criteria" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=BIG5">
<title>Insert title here</title>
</head>
<body>
<%
try{ 
	Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver"); //for hibernate 4.12
	
	Session sess = HBSessionFactory.getSessionFactory().openSession();
	Criteria criteria = sess.createCriteria(Person.class);        
	Iterator persons = criteria.list().iterator();        
	while(persons.hasNext()) {            
		Person p = (Person)persons.next();
		out.print("ID: " + p.getPERSON_ID()+"<br/>");
		out.print("NAME: " + p.getNAME()+"<br/>"); 
    } 
}catch(Exception e){ 
        out.print("Error message: "+ e.getMessage()); 
} 

%>
<b>Hello Azure</b>
</body>
</html>

完成後測試,沒問題的話應該可看到以下畫面。

圖16

在Windows Azure模擬環境下自然也是OK的。

圖17

 有圖有真相 在真實的Windows Azure環境下自然也是OK的。

圖18