分享
 
 
 

dynafuse 1.0 在sourceforge上发布!

王朝java/jsp·作者佚名  2006-01-09
窄屏简体版  字體: |||超大  

1. 概述

DynaFuse类似Appfuse,是一套整合目前主流J2EE技术的新构架,使用到的技术有struts,springframework,hibernate,groovy等,提出了Evertything be Dynamic的理念,从DAO到WEB层提供了全新的动态建模,动态编程的方案。

2. 运行例子

下载并安装mysql-4.0,建立数据库dynafuse,建立用户username/password为admin/admin。

下载并解压dynafuse-xx.zip,在mysql中执行data/create-tables.sql中的语句。

下载jakarta-tomcat-5.0.28,将dynafuse\lib\mysql-connector-java-3.0.14-production\mysql-connector-java-3.0.14-production-bin.jar和dynafuse\lib\jta-1.0\jta.jar拷贝到jakarta-tomcat-5.0.28\common\lib下,将dynafuse\dynafuse.xml拷贝到jakarta-tomcat-5.0.28\conf\Catalina\localhost下,

下载dynafuse.war拷贝到jakarta-tomcat-5.0.28\webapps下。

启动tomcat,打开浏览器http://localhost:8080/dynafuse进入例子程序。

3. 包结构说明

下载并解压dynafuse包,会得到如下的目录结构:

build:编译后文件

config:配置文件

data:试验数据

dist:打包后的发布文件

docs:文档

lib:使用到的jar文件

metadata:xdoclet需要的配置文件片断

script:groovy脚本

src:源码

test:测试源码

web:例子程序的jsp等文件

4. 构架说明

dynafuse最主要的特征是提倡Everything be Dynamic,从dao到service到web三个层面,每个层面都提供了对groovy新型server端srcipt语言的整合,使得web应用中基本所有的逻辑代码都能够以动态的形式编写,维护,构架分为三层: DAO层 - 这个层面中,dynafuse提供了两个interface:DAO 和 DynaDAO ,DAO是一个通用的数据访问(增、删、改、查)接口,DynaDAO在DAO的基础上提供了对DAO层面脚本的调用功能。这两个interface目前只提供了hibernate的实现。 DAO和DynaDAO分别作为springframewok中的bean在IOC容器中进行配置,详细请参考config\applicationContext-hibernate.xml。 Service层 - 这个层面中,dynafuse提供了两个interface:Manager 和 DynaManager,完成对DAO的封装并提供对service层面中业务逻辑脚本的调用功能,调用service层面脚本有两个方法,一是在事务环境中执行脚本(invokeScriptInTransaction),一个是不需要事务(invokeScript)。Manager和DynaManager分别作为springframewok中的bean在IOC容器中进行配置,详细请参考config\applicationContext-service.xml。 Web层 - 这个层面中,dynafuse提供了DynaAction,完成对web层面脚本的调用。

5. 构架使用

下面的文字将描述如何利用dynafuse进行web应用程序的开发。

1.构建hibernate的动态模型

hibernate在正式发布的3.0版本中,提供了动态模型,关于动态模型,可以查阅hibernate的相关资料,下面给出的是dynafuse示例程序的动态模型,文件参见dynafuse\model\Example.hbm.xml

<?xml version="1.0"?>

<!DOCTYPE hibernate-mapping PUBLIC

"-//Hibernate/Hibernate Mapping DTD 3.0//EN"

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

<hibernate-mapping default-lazy="false">

<class entity-name="Dept" table="t_dept">

<id

name="id"

column="dept_id"

type="java.lang.Integer"

unsaved-value="null"

>

<generator class="native">

</generator>

</id>

<property

name="name"

type="java.lang.String"

update="true"

insert="true"

column="dept_name"

not-null="true"

unique="false"

/>

<property

name="description"

type="java.lang.String"

update="true"

insert="true"

column="dept_description"

not-null="false"

unique="false"

/>

<bag

name="persons"

lazy="true"

inverse="true"

cascade="delete"

>

<key

column="deptid"

>

</key>

<one-to-many

class="Person"

/>

</bag>

</class>

<class entity-name="Person" table="t_person">

<id

name="id"

column="person_id"

type="java.lang.Integer"

unsaved-value="null"

>

<generator class="native">

</generator>

</id>

<property

name="name"

type="java.lang.String"

update="true"

insert="true"

column="person_name"

not-null="true"

unique="false"

/>

<property

name="age"

type="java.lang.Integer"

update="true"

insert="true"

column="person_age"

not-null="true"

unique="false"

/>

<property

name="description"

type="java.lang.String"

update="true"

insert="true"

column="person_description"

not-null="false"

unique="false"

/>

<many-to-one

name="dept"

class="Dept"

cascade="none"

update="true"

insert="true"

column="deptId"

/>

</class>

</hibernate-mapping>

这里没有静态的POJO持久类,所有的持久数据都通过Map结构来存放。

2.DAO层面的脚本,如果DAO接口中提供的方法不能满足需要,那么可以在DAO层面加入脚本,然后在service层通过DynaDAO完成对DAO脚本的调用,下面是示例程序中的dynafuse\script\PersonDAO.groovy

import org.hibernate.Session;

import org.hibernate.Query;

public class PersonDAO {

public Session session;

public Object getAvgAgeOfDept(Integer deptId) {

String hsql = "select avg(t.age) from Person t where t.dept.id=:deptId";

Query query = session.createQuery(hsql);

query.setInteger("deptId", deptId.intValue());

return query.uniqueResult();

}

}

这里需要说明的是session这个成员变量,它是必须要在DAO层面的脚本中申明的,在dao层面的脚本被执行的时候,dynafuse将会自动对这个session赋值,在脚本中,你不用关心session是怎么得到,你只管放心使用。

3.service层面的脚本,在实际的应用中,业务逻辑是千变万化的,所以service层面加入脚本支持是非常有用的,service层的脚本将在web层通过DynaManager被调用,下面是示例程序中的dynafuse\script\DeptManager.groovy

import org.robusta.dynafuse.dao.DynaDAO;

import java.util.List;

public class DeptManager {

public DynaDAO dynaDao;

public List getDepts() {

return dynaDao.getObjects("Dept", null, null, null);

}

public Object getAvgAgeOfDept(Integer deptId) {

return dynaDao.invokeScript("PersonDAO.groovy", "getAvgAgeOfDept", new Object[]{deptId});

}

}

这里需要说明的是dynaDao这个类成员变量,和dao层面脚本中的session一样,是在service层面的脚本中执行的时候,由dynafuse自动赋值,你只管放心使用它。

还需要注意的是,在service层面的脚本中可以利用dynaDao去调用DAO层面的脚本,如上面的getAvgAgeOfDept。

4.构建web层的动态模型,struts提供了DynaValidatorActionForm这种构造动态模型的机制,请参考示例中的dynafuse\metadata\web\struts-forms.xml。

5.web层面的脚本,跟业务逻辑一样,页面逻辑也是千变万化的,所以web层的脚本非常有用,下面是示例程序中的dynafuse\script\DeptAction.groovy

public class DeptAction extends BaseAction {

....

public DynaManager dynaManager;

....

public ActionForward editDept(ActionMapping mapping, ActionForm form,

HttpServletRequest request, HttpServletResponse response) {

if (log.isDebugEnabled()) {

log.debug("Entering 'editDept' method");

}

String deptId = request.getParameter("deptId");

if (deptId != null && !"".equals(deptId)) {

Map data = dynaManager.getObject("Dept", new Integer(deptId));

Long avgAge = (Long) dynaManager.invokeScript("DeptManager.groovy", "getAvgAgeOfDept", new Object[]{new Integer(deptId)});

DynaValidatorActionForm deptForm = (DynaValidatorActionForm) form;

deptForm.set("id", data.get("id"));

deptForm.set("name", data.get("name"));

deptForm.set("description", data.get("description"));

deptForm.set("avgAge", avgAge);

updateFormBean(mapping, request, deptForm);

}

return mapping.findForward("edit");

}

....

和servcie和dao层的脚本一样,web层脚本中有一个dynaManager成员变量。

6.将web层的脚本配置到action中,可以参考dynafuse\metadata\web\struts-actions.xml

....

<action

path="/depts"

type="org.robusta.dynafuse.web.action.DynaAction"

parameter="DeptAction.groovy/listDepts"

unknown="false"

validate="false"

>

<forward

name="list"

path="/WEB-INF/pages/deptList.jsp"

redirect="false"

/>

</action>

....

需要注意的是这里的parameter,指定了web层某个脚本中的某个method。

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
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- 王朝網路 版權所有