Oracle8i中EJB组件的开发和使用.docx
《Oracle8i中EJB组件的开发和使用.docx》由会员分享,可在线阅读,更多相关《Oracle8i中EJB组件的开发和使用.docx(43页珍藏版)》请在冰点文库上搜索。
Oracle8i中EJB组件的开发和使用
Oracle8i中EJB组件的开发和使用
EnterpriseJavaBeans(EJB)是由SUN公司所推出的开发分布式组件的一个标准,Oracle8i不仅支持在数据库中开发CORBA组件,而且也支持开发EJB组件。
本篇文章将详细介绍这方面的知识,具体内容如下:
∙EJB组件简介;
∙手工开发EJB应用;
∙使用JDeveloper开发EJB应用。
比较CORBA与EJB组件
EnterpriseJavaBeans(EJB)是一种基于分布式计算组件的事务体系。
当使用EJB进行开发时,组件开发人员和客户应用程序员将无需关心事务支持、安全性、远程对象访问等细节问题。
1.EJB是基于Java语言的组件模型,所以开发人员只能使用Java语言来开发EJB组件;而编写CORBA组件不仅需要掌握编程语言(JAVA、C、COBOL),而且还需要掌握IDL语言。
2.CORBA使用IIOP作为传输协议,而EJB则是基于RMI(RemoteMethodInvocationinterface)开发的一种概念。
但SUN公司没有规定要使用RMI协议,所以Oracle8i仍是通过IIOP协议来实现EJB组件。
EJB组件的组成元素
1.宿主接口(BeanHomeInterface)
宿主接口指定了一或多个create()方法,该方法既可带有参数,也可以没有任何参数。
对于宿主接口中的每个create()方法,必须在远程接口中指定一个相应的ejbCreate()方法。
二者的唯一不同是create()方法返回组件类型,而ejbCreate()方法返回为空(void)。
2.远程接口(BeanRemoteInterface)
远程接口用于说明组件所要实现的企业规则,并且客户要访问的方法必须在远程接口中存在。
远程接口类必须是公用的(public),并且必须是javax.ejb.EJBObject的子类。
3.组件(Bean)
组件用于实现远程接口中所声明的方法,客户应用正是通过调用组件方法来访问组件的。
4.配置说明(deploymentdescriptor)
配置说明用于说明EJB组件的属性,包括指定宿主接口、远程接口、组件实现类名、组件JNDI名、事务、安全等属性。
开发EJB组件的方法
1.编写宿主接口(HomeInterface)程序
当客户要访问EJB组件时,必须创建组件实例,这是通过宿主接口来完成的,编写宿主接口程序的方法如下:
2.编写远程接口(RemoteInterface)程序
远程接口用于声明组件所要实现的方法,编写远程接口程序的方法如下:
3.编写组件(JavaBeans)程序
组件用于实现远程接口中所声明的方法,编写组件程序的方法如下:
4.编写配置说明(DeploymentDescriptor)
配置说明用于指定组件的属性,编写配置说明的方法如下:
5.编译/打包EJB
在编写了远程接口、宿主接口以及组件程序之后,首先编译这些程序,然后将所生成的二进制文件(.class)打包。
如下所示:
6.配置并发行EJB
在打包了组件程序之后,就可以将其装载到Oracle8i数据库,并发行该组件了。
如下所示:
当开发了EJB组件之后,客户应用就可以访问该组件了。
如下图所示:
实现EJB服务器组件
下面以创建在表AUTHS上执行查询、插入、更新、删除操作的EJB组件为例,介绍开发EJB组件的方法。
如下图所示:
具体步骤如下:
1.编写宿主接口程序,程序清单如下(author\AuthorHome.java):
packageauthor;
/*导入Java类*/
importjavax.ejb.*;
importjava.rmi.RemoteException;
/*定义接口authorHome*/
publicinterfaceAuthorHomeextendsEJBHome{
publicAuthorcreate()throwsCreateException,RemoteException;
}
2.编写远程接口程序,程序清单如下(author\Author.java):
packageauthor;
importjavax.ejb.EJBObject;
importjava.rmi.RemoteException;
publicinterfaceAuthorextendsEJBObject{
publicStringqueryAuthor(Stringauthor_code)
throwsjava.sql.SQLException,RemoteException;
publicvoidinsertAuthor(Stringauthor_code,Stringname,
intsex,doublesalary,Stringbirthdate,Stringentry_date_time)
throwsjava.sql.SQLException,RemoteException;
publicvoidupdateAuthor(Stringauthor_code,doublesalary)
throwsjava.sql.SQLException,RemoteException;
publicvoiddeleteAuthor(Stringauthor_code)
throwsjava.sql.SQLException,RemoteException;
}
3.编写组件程序,程序清单如下(authorServer\AuthorBean.java):
packageauthorServer;
importjava.sql.*;
importjava.rmi.RemoteException;
importjavax.ejb.*;
importoracle.jdbc.driver.*;
/*主类authorBean:
用于实现会话组件*/
publicclassAuthorBeanimplementsSessionBean{
SessionContextctx;
/*方法queryAuthor():
用于获取作者信息*/
publicStringqueryAuthor(Stringauthor_code)
throwsSQLException,RemoteException{
/*声明并初始化变量*/
Stringauthorinfo=newString();
/*建立缺省的数据库连接*/
Connectionconn=newOracleDriver().defaultConnection();
/*构造动态SQL语句*/
Stringsql="SELECTname,sex,salary,birthdate,entry_date_time"+
"FROMauthsWHEREauthor_code=?
";
/*准备动态SQL语句*/
PreparedStatementps=conn.prepareStatement(sql);
/*设置宿主变量的值*/
ps.setString(1,author_code);
/*执行动态SQL语句*/
ResultSetrset=ps.executeQuery();
if(!
rset.next())
thrownewRemoteException("代码为"+author_code+"的作者不存在!
");
/*返回作者信息*/
authorinfo="代码为"+author_code+"的作者信息\n"+
"-----------------------------------"+
"\n作者姓名:
"+rset.getString
(1)+
"\n作者性别:
"+rset.getInt
(2)+
"\n作者工资:
"+rset.getDouble(3)+
"\n出生日期:
"+rset.getString(4)+
"\n录入日期:
"+rset.getString(5);
/*关闭结果集*/
rset.close();
/*关闭动态SQL语句*/
ps.close();
returnauthorinfo;
}
/*方法insertAuthor():
用于插入作者记录*/
publicvoidinsertAuthor(Stringauthor_code,Stringname,
intsex,doublesalary,Stringbirthdate,Stringentry_date_time)
throwsSQLException,RemoteException{
/*建立缺省的数据库连接*/
Connectionconn=newOracleDriver().defaultConnection();
/*构造动态SQL语句*/
Stringsql="INSERTINTOauths(author_code,name,sex,salary,"+
"birthdate,entry_date_time)VALUES(?
?
?
?
?
?
)";
/*准备动态SQL语句*/
PreparedStatementps=conn.prepareStatement(sql);
/*设置宿主变量的值*/
ps.setString(1,author_code);
ps.setString(2,name);
ps.setInt(3,sex);
ps.setDouble(4,salary);
ps.setString(5,birthdate);
ps.setString(6,entry_date_time);
/*执行动态SQL语句*/
ps.executeUpdate();
/*关闭动态SQL语句*/
ps.close();
}
/*方法updateAuthor():
用于修改作者工资*/
publicvoidupdateAuthor(Stringauthor_code,doublesalary)
throwsSQLException,RemoteException{
/*建立缺省的数据库连接*/
Connectionconn=newOracleDriver().defaultConnection();
/*构造动态SQL语句*/
Stringsql="UPDATEauthsSETsalary=?
WHEREauthor_code=?
";
/*准备动态SQL语句*/
PreparedStatementps=conn.prepareStatement(sql);
/*设置宿主变量的值*/
ps.setDouble(1,salary);
ps.setString(2,author_code);
/*执行动态SQL语句*/
ps.executeUpdate();
/*关闭动态SQL语句*/
ps.close();
}
/*方法deleteAuthor():
删除作者记录*/
publicvoiddeleteAuthor(Stringauthor_code)
throwsSQLException,RemoteException{
/*建立缺省的数据库连接*/
Connectionconn=newOracleDriver().defaultConnection();
/*构造动态SQL语句*/
Stringsql="DELETEFROMauthsWHEREauthor_code=?
";
/*准备动态SQL语句*/
PreparedStatementps=conn.prepareStatement(sql);
/*设置宿主变量的值*/
ps.setString(1,author_code);
/*执行动态SQL语句*/
ps.executeUpdate();
/*关闭动态SQL语句*/
ps.close();
}
publicvoidejbCreate()throwsCreateException,RemoteException{}
publicvoidejbActivate(){}
publicvoidejbPassivate(){}
publicvoidejbRemove(){}
publicvoidsetSessionContext(SessionContextctx){
this.ctx=ctx;
}
}
4.编写配置说明,清单如下(author.ejb):
SessionBeanauthorServer.AuthorBean{
/*组件名称*/
BeanHomeName="test/author";
/*远程接口类名*/
RemoteInterfaceClassName=author.Author;
/*HOME接口类名*/
HomeInterfaceClassName=author.AuthorHome;
AllowedIdentities={ACA};
StateManagementType=STATEFUL_SESSION;
RunAsMode=CLIENT_IDENTITY;
TransactionAttribute=TX_REQUIRED;
}
5.编译并打包EJB组件
编译宿主接口、远程接口、EJB组件程序,然后将所生成的二进制程序(.class文件)打包。
如下所示:
6.配置并发行EJB组件
配置并发行EJB组件是通过deployejb工具来完成的,如下所示:
实现EJB客户应用
下面以开发访问EJB组件的客户应用为例,介绍开发EJB客户应用的方法。
如下图所示:
1.编写与服务器端完全相同的宿主接口、远程接口代码。
2.编写客户应用程序
下表列出了该应用程序中所包含的各个程序及相应功能:
程序
功能
EJBClient.java
显示用户界面
connectDialog.java
连接EJB组件
queryDialog.java
访问queryAuthor()方法,执行检索操作
insertDialog.java
访问updateAuthor()方法,执行插入操作
updateDialog.java
访问updateAuthor()方法,执行修改工资操作
deleteDialog.java
访问deleteAuthor()方法,执行删除操作
helpDialog.java
显示帮助信息
1)程序清单(EJBClient.java)
/*导入Java类*/
importjava.awt.*;
publicclassEJBClientextendsFrame{
/*
*声明构件(如菜单、对话框等)
*/
connectDialogc1;
MenuItemm_connect=newMenuItem("连接到EJB组件");
MenuItemm_query=newMenuItem("查询");
MenuItemm_insert=newMenuItem("插入");
MenuItemm_update=newMenuItem("更新");
MenuItemm_delete=newMenuItem("删除");
MenuItemm_helptopic=newMenuItem("帮助主题");
MenuItemm_helpabout=newMenuItem("关于EJB客户应用");
/*
*类构造方法
*/
EJBClient(){
/*继承父类属性设置*/
super("EJB客户应用");
/*
*在窗口中放置菜单
*/
MenuBarmb=newMenuBar();
Menum1=newMenu("连接");
m1.add(m_connect);
m1.add("退出");
Menum2=newMenu("数据操作");
m2.add(m_query);
m2.add(m_insert);
m2.add(m_update);
m2.add(m_delete);
m_query.disable();
m_insert.disable();
m_update.disable();
m_delete.disable();
mb.add(m1);
mb.add(m2);
Menum3=newMenu("帮助");
m3.add(m_helptopic);
m3.add(m_helpabout);
m_helptopic.disable();
mb.setHelpMenu(m3);
setMenuBar(mb);
/*
*调整窗口位置及大小,并显示窗口
*/
reshape(100,100,600,400);
show();
}
/*
*方法action():
用于处理在窗口中所发生的事件
*/
publicbooleanaction(Eventevt,Objectwhat){
/*
*单击“连接到EJB组件”菜单,执行连接操作
*/
if("连接到EJB组件".equals(what)){
c1=newconnectDialog(this,"连接EJB组件",true);
newconnectMessageDialog(this,"消息框",true,c1.return_message());
if(c1.return_message()=="连接成功!
"){
m_connect.disable();
m_query.enable();
m_insert.enable();
m_update.enable();
m_delete.enable();
}
returntrue;
}
/*
*单击“查询”菜单,打开查询对话框执行查询操作
*/
elseif("查询".equals(what)){
newqueryDialog(this,"查询作者信息",true,c1.return_bean());
returntrue;
}
/*
*单击“插入”菜单,打开插入对话框执行插入操作
*/
elseif("插入".equals(what)){
newinsertDialog(this,"插入作者记录",true,c1.return_bean());
returntrue;
}
/*
*单击“更新”菜单,打开修改对话框执行修改操作
*/
elseif("更新".equals(what)){
newupdateDialog(this,"修改作者工资",true,c1.return_bean());
returntrue;
}
/*
*单击“删除”菜单,打开删除对话框执行删除操作
*/
elseif("删除".equals(what)){
newdeleteDialog(this,"删除作者记录",true,c1.return_bean());
returntrue;
}
/*
*单击“关于EJB客户应用”菜单,显示版本信息
*/
elseif("关于EJB客户应用".equals(what)){
newhelpDialog(this,"帮助",true);
returntrue;
}
/*
*单击“退出”菜单,关闭应用
*/
if("退出".equals(what)){
dispose();
System.exit(0);
returntrue;
}
returnfalse;
}
publicstaticvoidmain(String[]args){
newEJBClient();
}
}
2)程序清单(connectDialog.java)
/*导入Java类*/
importauthor.*;
importauthor.Author;
importauthor.AuthorHome;
importoracle.aurora.jndi.sess_iiop.ServiceCtx;
importjavax.naming.Context;
importjavax.naming.InitialContext;
importoracle.aurora.jts.client.AuroraTransactionService;
importoracle.aurora.jts.util.TS;
importjava.util.Hashtable;
importjava.awt.*;
publicclassconnectDialogextendsDialog{
/*
*声明构件(如文本框、按钮等)、宿主接口变量
*/
TextFieldusername_field=newTextField(40);
TextFieldpassword_field=newTextField(40);
TextFieldserviceURL_field=newTextField(40);
TextFieldobjectName_field=newTextField(40);
Buttonok=newButton("确定");
Buttoncancel=newButton("取消");
Labellb_username=newLabel("输入用户名:
");
Labellb_password=newLabel("输入口令:
");
Labellb_serviceURL=newLabel("输入服务名:
");
Labellb_objectName=newLabel("输入对象名:
");
GridBagLayoutgb1=newGridBagLayout();
GridBagConstraintsc=newGridBagConstraints();
protectedStringmessage=newString();
protectedAuthorHomehome;
/*
*对话框构造方法
*/
connectDialog(Frameframe,Stringtitle,booleanmodal){
super(frame,title,modal);
setLayout