分享
 
 
 

简化对数据库的访问

王朝other·作者佚名  2008-05-19
窄屏简体版  字體: |||超大  

改进的Oracle Jpublisher可以将数据库实体映射到Java和Web服务。

编写客户端和中间层的Java与J2EE应用程序来表示数据库实体,如用户定义的SQL对象类型和集合类型时,如果你需要手工完成所有编码,这将是非常具有挑战性和易于出错的工作。另一种办法则是你可以使用Oracle JPublisher工具来完成,该工具自动根据你输入的命令行(或根据在Oracle JDeveloper集成开发环境下的鼠标点击)自动产生相应的Java类。

本文中,我将概要介绍JPublisher并描述它是如何简化将数据库实体映射到Java的过程,包括你无法从Java Database Connectivity (JDBC)直接使用的类型。然后我将展示如何通过一或两个JPublisher命令将数据库的操作和商务逻辑映射到你的Java客户端、J2EE组件和Web服务客户端。最后,我将描述JPublisher如何简化从数据库内部调用外部Web服务的过程。

Jpublisher概述

Oracle JPublisher是一个用于在Java和SQL之间转换和交换结构化对象数据的工具,它还可以访问其他的数据库资源,如PL/SQL包和Java存储过程。它生成Java类来表示数据库实体,如SQL对象和操作、PL/SQL包和过程以及服务器端Java类。你可以通过JDBC在你的Java客户端、servlet、JavaServer Pages (JSP)、Enterprise JavaBeans (EJB)和Web服务中使用这些生成的类。

JPublisher 可以生成表示以下数据库实体的类:

用户定义的SQL对象类型。对于每个对象类型,JPublisher为表示该对象的类生成一个type.java文件。它提供访问程序方法,用以获取和设置该对象类型的每个属性。还有,如果你的对象类型包含了作为存储过程而实现的方法,则JPublisher将生成封装器方法在对象实例上调用这些方法。

对象引用类型(REF 类型)。 对于一个SQL对象引用类型,JPublisher生成一个typeRef.java文件来建立该Java对象类型的引用模型。它包括通过一个对象引用来访问实际的对象值的方法。

用户定义的SQL集合类型。对于每个集合类型,JPublisher为表示该集合的类生成一个type.java文件。对于嵌套的数据表,生成的类具有作为整个数组来获取和设置嵌套的数据表的一些方法,以及用于获取和设置该数据表中各个元素的一些方法。

用户定义的OPAQUE类型。每当JPublisher遇到一个没有提供其相应类型的SQL OPAQUE类型时,它都会生成一个type.java文件来发布一个Java封装器类。OPAQUE的有效负荷以字节数组(byte array)来表示,可以从生成的封装器的子类中进行处理。

PL/SQL BOOLEAN PL/SQL BOOLEAN被映射到Java Boolean类型。这要求有SYS.SQLJUTL包,该包是由数据库(JPublisher生成的代码要在其中运行)中的sqljutil.sql脚本来安装的。这个脚本默认安装在Oracle Database 10g中。

PL/SQL RECORD和TABLE类型。对于RECORD和TABLE类型,JPublisher生成相应的SQL对象(对于RECORD类型)或SQL VARRAY类型(对于TABLE类型),以及用于在PL/SQL和SQL类型之间进行映射的转换函数。

PL/SQL INDEXED-BY数据表。如果你使用Oracle Database 10g 的JDBC Oracle Call Interface (OCI)驱动程序并且需要发布已有索引的标量数据表,那么你可以直接在Java和这些类型(以Java数组表示)之间进行映射。

运行JPublisher实用工具

要在数据库中你想转换为Java类的用户定义的数据类型和PL/SQL包上运行JPublisher,你必须建立一个数据库连接,以便能对你映射的SQL类型和PL/SQL包进行访问。为此,可以使用-user和-url选项,如下例所示:

% jpub -user=scott/tiger -url=jdbc:oracle:oci:@ ...

% jpub -user=scott/tiger -url=jdbc:oracle:thin:@host:port/

servicename ...

第一个例子使用了Oracle JDBC OCI驱动程序,第二个使用了Oracle JDBC Thin驱动程序。下面的例子建立在Order Entry (OE)模式的基础上,该模式是Oracle Database 10g中一些示例模式的一种。假设OE模式的口令是OE,使用以下命令来发布SQL对象类型CATEGORY_TYP,其中CategoryTyp是相应Java类的名字:

% jpub -user=OE/OE -url=jdbc:oracle:oci:@

-sql=CATEGORY_TYP:CategoryTyp

-sql选项指定将要发布的类型和类包。

Oracle JPublisher生成并编译相应的Java类。

映射数据库操作

在这一部分,我将对PL/SQL包到Java的手工映射与JPublisher方法进行比较和对照。我的例子中使用了一个PL/SQL特有的类型,该类型无法从Java (本例中是PL/SQL RECORD)直接访问,而JPublisher则提供了附加支持。

create or replace package action

as type emprec

is record (name varchar2(10),

age number);

procedure foo (hired timestamp,

emp in out emprec);

end;

/

假设你想将ACTION包映射到一个Java类的Action。JDBC支持从TIMESTAMP到java.sql.TimeStamp的映射,然而,你并不想使用JDBC支持的映射,而是想从TIMESTAMP映射到Date。相应的Java foo方法将有如下定义:

public void foo(java.util.Date hired, EmpRecSql[] emp_inout)

手工方法。下面的一些步骤概括了你可以如何为这个ACTION包示例手工设置PL/SQL到Java的映射:

为PL/SQL RECORD类型EMPREC创建一个SQL对象类型,例如EMPREC_SQL。

为你创建的SQL类型创建一个Java类型。例如,为SQL类型EMPREC_SQL创建Java类型EmpRecSql。

在Java中,将每个参数转换为一个对应的Java类型。例如,将SQL TIMESTAMP转换为Java Date。

通过JDBC将每个IN或IN OUT参数传递给一个PL/SQL块。例如,将EmpRecSql和TimeStamp传递给foo。

在PL/SQL块中,将每个IN和IN OUT参数转换为PL/SQL存储过程的正确类型。例如,将EMPREC_SQL转换为EMPREC。

调用PL/SQL存储过程。

在PL/SQL中,将每个OUT参数、IN OUT参数或函数结果从JDBC不支持的类型转换为JDBC支持的相应类型。例如,将EMPREC转换为EMPREC_SQL。

从PL/SQL块返回每个OUT参数、IN OUT参数或函数结果。

在Java中,将每个OUT参数、IN OUT参数或函数结果从JDBC支持的类型转换为它不支持的类型。例如,从TimeStamp转换为Date。

Oracle JPublisher方法。以下的JPublisher命令直接发布ACTION包:

%

jpub -u scott/tiger -s action:Action

-style=webservices9

-outarguments=array

-plsqlfile=actionWrap.sql

请注意,-style=webservices9选项指定从TimeStamp到Date的映射。-outarguments= array表示OUT参数通过只有一个元素的数组来传递。

JPublisher产生你必须在使用JPublisher生成的代码之前要执行的PL/SQL封装器脚本。这个脚本包含了对应PL/SQL EMPREC类型的SQL类型EMPREC_SQL的定义,以及EMPREC和EMPREC_SQL之间的转换函数。同时,该脚本还包含了一个针对PL/SQL存储过程foo的封装器。

以下命令将执行生成的脚本:

% sqlplus scott/tiger @actionWrap.sql

这就算完成了。两相比较,JPublisher只需两个命令就可以完成ACTION包的PL/SQL到Java映射,而手工方法中却需要很多个命令。

以下是对JPublisher为ACTION PL/SQL包到Java映射生成的每个文件的简单描述:

Action.java, 为ACTION包生成的Java基类

ActionBase.java,从ActionBase扩展来的Java用户子类

ActionUser.java, 从ActionBase扩展来的Java类,包含Java类型映射,如从TimeStamp到Date

ActionEmprec.java, 为EMPREC_SQL生成的Java接口

ActionEmprecBase.java,为EMPREC_SQL生成的Java基类

ActionEmprecUser.java, 提供ActionEmprecBase的Java用户子类

ActionEmprecUserRef.java, EMPREC_SQL的REF类型的Java类型

actionWrap.sql,定义了EMPREC的SQL类型的SQL和PL/SQL脚本以及EMPREC和SQL类型之间的转换函数

数据库作为Web服务提供者

Oracle Database 10g提供了一个新的JPublisher特性,用以支持数据库Web服务。Oracle Database 10g与Oracle Application Server 10g的结合允许你将PL/SQL包和存储过程、SQL查询、SQL数据操作语言(DML)语句、以及服务器端Java类发布为Web服务。JPublisher生成的类可以通过Oracle Application Server Web Services Assembler工具作为Web服务而公布。

发布SQL查询或DML语句。JPublisher可以将具体的SELECT、UPDATE、INSERT或DELETE语句发布为一个Java类的方法。这个类也可以作为Web服务而发布。

样式文件。在发布服务器端Java类时,JPublisher使用说明Java到Java类型映射的样式文件来确保生成的类可用于Web服务。

生成Java接口。JPublisher可以生成Java接口和类。这就避免了手工生成Java接口来表示用以生成Web服务描述语言(WSDL)内容的API。

所支持的SQL类型。以下的SQL类型可以在数据库Web服务签名中发布:各种简单SQL类型,包括DATE,SQL对象类型,SQL VARRAY类型,SYS.XMLTYPE和REF CURSOR。

数据库作为Web服务消费者

当数据库作为Web服务消费者时,Web服务客户端代码采用SQL、PL/SQL或Java编写并在数据库中运行,用以调用外部Web服务。对于在数据库中运行以访问其他Web服务的代码,你必须能够调用这些服务。你可以使用手工方法进行简单对象访问协议(SOAP)的编程,或者通过JPublisher。以下步骤将帮助你通过JPublisher来构建你的第一个数据库Web服务消费者。

第一步:确认数据库的安装。在Oracle Database 10g中,在数据库安装时应该装入了[Oracle_Home]/sqlj/lib的sqljutl.jar库和utl_dbws_jserver.jar库、以及SYS.UTL_DBWS包。

第二步:生成并装入客户端代理以及Java和PL/SQL封装器。JPublisher将生成Web服务客户端代理代码的任务完全自动化,将其编译、放入Java归档(JAR)文件并装入到数据库中。 使用以下格式来生成代理代码:

% jpub

-proxywsdl=URL_of_Web_Service_WSDL

-user=username/password

另外,如果它与WSDL本身所提供的不相同,则你可以指定

-endpoint=external_Web_Services_URL

如果与通过JDBC OCI驱动程序访问的默认数据库实例不相同,则你还可以指定-url=JDBC_database_URL。以下例子使用了多个选项:

% jar xvf dist/javacallout.jar

META-INF/HelloServiceEJB.wsdl

% jpub -proxywsdl=META-INF/

HelloServiceEJB.wsdl

-dir=genproxy

-package=javacallout

-user=scott/scott

-endpoint=http://localhost:8888/

javacallout/javacallout

-proxywsdl选项指定了WSDL文件,JPublisher将为它生成静态Java代理类、Java和PL/SQL封装器,以及PL/SQL脚本。

-dir选项为生成的代码和脚本指定了根目录。

-package选项为生成的Java代码指定了包的名字。

代码生成后,JPublisher自动将以下文件装入数据库中:

genproxy/javacallout。这个目录下的Java类由JPublisher调用的Web服务WSDL编译工具生成。

genproxy/HelloServiceEJBJPub.java。HelloServiceEJBJPub.java类将方法sayHello()定义为一个静态的Java方法。

genproxy/plsql_wrapper.sql。这是Web服务客户端(HelloServiceEJBJPub.java)的PL/SQL封装器。

genproxy/plsql_dropper.sql。它用来删除plsql_wrapper.sql定义的PL/SQL类型和包。

genproxy/plsql_grant.sql。它(运行在SYS下)用来为Java客户端代理分配必要的权限以调用Web服务。

genproxy/plsql_revoke.sql。它用来取消plsql_grant.sql所分配的权限。

genproxy/jpub_proxyload.log。这是用于装入生成的Java文件和安装plsql_wrapper.sql脚本的日志文件。

为了禁止JPublisher将生成的代码装入到数据库中,你可以指定选项-proxyopts =noload。使用静态客户端代理的优点是你可以简化在你的Java代码中引用端口类型实例方法,而无需担心如何编排(marshal)或反编排(unmarshal)来自SOAP消息的个别参数。 下一步

第三步:分配权限。脚本plsql_grant.sql用于SYS给SCOTT分配执行装入的客户端代理时所必需的权限:

SQL conn / as sysdba

SQL @genproxy/plsql_grant.sql

第四步:调用外部Web服务。要从数据库调用外部Web服务,声明和运行run_plsql_proxy.sql脚本,或运行以下的PL/SQL块:

SQL set serveroutput on

SQL declare x varchar2(100);

begin

x:=JPUB_PLSQL_WRAPPER.sayHello(

'Hello from database');

dbms_output.put_line(x);

end;

/

第五步:清除。使用SQL*PLUS删除PL/SQL封装器并取消分配的权限。

SQL conn scott/tiger

SQL @genproxy/plsql_dropper.sql

SQL conn / as sysdba

SQL @genproxy/plsql_revoke.sql

使用dropjava工具从数据库中删除装入的Java类:

dropjava -u scott/tiger

genproxy/wsdlGenerated.jar

结论

JPublisher使Java开发人员免于复杂的学习、以及掌握手工创建Java数据库访问程序的很多逻辑细节和麻烦。此外,Jpublisher还简化了将数据库操作作为Web服务发布的过程和从数据库内部使用外部Web服务的过程。

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有