-
2008年07月10日
《Spring In Action》second edtion - [互联网络]
又有新书可看了,2007年8月年出版的,讲的是Spring 2.0的技术
-
2008年07月04日
Struts 2.0与Spring整合 - [编程开发]
struts 2中整合Spring主要是用到Spring的IoC功能,struts 2中的所有的action,interceptor等对象都是由Spring的bean工厂来生成。
在web.xml里添加一个监听器
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener
</listener-class>
</listener>struts.xml
<constant name="struts.objectFactory" value="spring" />
<constant name="struts.devMode" value="true" />在WEB-INF目录下创建applicationContext.xml文件
-
2008年06月27日
Spring 2.0使用AspectJ - [编程开发]
Spring2.5很早就发布,当时下载Spring时,因为看到2.5只是beta版(测试版),而2.0后面标了GA(General Availability所谓的稳定版),所以只下载了2.0版,2.5跟2.0有什么变化和区别就不晓得,因为所有Spring学习都在2.0下面进行。
AspectJ不用多说了,一个AOP的实现,AOP领域的先锋。现在是要在spring 2.0中使用AspectJ中的注解方式编程,实现AOP功能。
不要用MyEclipse,一直使用它的话,就无法知道,我们项目有哪几个JAR包是需要的,哪几个又是不需要的。还有XML配置文件到底该怎么写,MyEclipse老是经常对XML动了一些错误的手脚。很多书上的例子都没有说要用到哪一些JAR包, 所以很多都是照书上代码打了一下,但还是运行错误,所以手工配置很重要。
在使用Spring时,如果是Web项目,直接把Spring的JAR包拷到lib文件夹里,如果是普通的Java项目,可以在项目下新建一个文件夹名称为lib或者其他,把JAR包拷到里面。
然后右键,add to build path,把JAR包加到项目的classpath中。当然还有其他很多方式,在这里不是重点。重点的是到底要加几个JAR包。

首先再强调一下,那些JAR包,不要拿MyEclipse提供的那些,而是要从spring官方下载的。
spring.jar这个是spring所有模块的集合JAR文件,commons-logging.jar,这个包不管是做spring的哪一个模块,不管是IOC还是AOP,MVC,如果没这个JAR包,运行马上就报错,这个是spring中输出错误信息的一个日志工具。log4j-1.2.14.jar这个也是缺一不可的,虽然不加这个包,程序照样可以运行,但程序中如果有错误就不知道哪里错,还有程序运行时,log4j还会打印整个运行流程。最后是aspectjrt.jar和aspectjweaver.jar要使用AspectJ的AOP功能就需要添加这两个。整个工程的结构如下:
spring.xml这个文件也是随意命名的,MyEclipse好像把它命名为ApplicationContext.xml,那么长!还有这xml配置文件所放的目录也是随意的,只要在程序中指明它的位置就可以了。而log4j.properties 这个文件只能放在src根目录下,log4j.properties这个文件可以在下载下来的压缩包中resources目录找到它,也可以自己写,但文件名只能是log4j.properties
按照上面项目的目录在代码中找到spring.xml文件应该是这样写ApplicationContext ac =
new FileSystemXmlApplicationContext("bin/spring.xml");其中"bin/spring.xml"前面出现"bin",是因为eclipse是把.java源文件和.class文件分开的。原本是在src目录下创建的spring.xml经过eclipse编译后,就会自动在bin目录下生成spring.xml,如果写成"src/spring.xml"也是可以,但前提是发布项目时,字节码连同源代码一起发布,要不然就不存在src这个目录了。还有要注意的一点是"bin\\spring.xml"写成反斜杠是要两杠,正斜杠只需一杠,反斜杠在String中是转义符。
再来看看spring.xml文件里的写法
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.0.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.0.xsd">
<aop:aspectj-autoproxy />
<bean id="stu" class="com.zhang.Student"></bean>
<bean id="aop" class="com.zhang.Aop"></bean>
</beans>
beans元素里面的xmlns、 xsi:schemaLocation等等,一个字都不得有误,稍微网址有错误都不行。最后用AspectJ注解方式创建一个切面,其他商业逻辑代码暂不说明,直接看那个切面的代码:
package com.zhang;
import org.aspectj.lang.annotation.*;
@Aspect
public class Aop {
@Pointcut("execution(* run*(..))")
public void somePointcut() {
}
@Before("somePointcut()")
public void asp() {
System.out.println("the before aop is running");
}
@After("somePointcut()")
public void asp1() {
System.out.println("the after aop is running");
}
}先说明一下那些通配符的意思,“*”星号,代表0个或多个字符,在方法的括号内"(..)"里面两点,代表有0个或多个参数。
* run*()是匹配所有类中所有以run开头的方法,比如public void run1();private int run2();注意第一个*后面是有空格的,有空格和没空格意义完全不同。有一本书上这样写:
"execution("execution("* springroad.demo.chap5.exampleB.Component.business*(..))")
它通配的是某个类的某一个方法,包名和类名都很长,真的会混淆人, 第一个“*”星号后一定要记得加空格,大部分情况下第一个“*”号都要写上去,也有不需要的,如
execution(public void run*(..));execution(int run*(..))等等,那些方法前加修饰符的就不需要
——————————
最后总结:
要在Spring中使用AspectJ,并不需要特定把AspectJ从官网上下载安装,而是只需到Spring官网下载相关的软件包即可,里面已经包含AspectJ相应的JAR包文件。
到底有哪几个包需要的要自己尝试,不要借助MyEclipse,因为它会导入一些根本用不到的包,而且数量还不少,要知道如果是在tomcat,JAR包越多启动时间就越长。
要搞懂execution的写法,在Spring参考文档里有说明
-
2008年06月22日
Struts 2 结果(Result) - [编程开发]
Result也是Struts的核心部分,在整个MVC中它所处的位置是视图(View),但它跟页面外观效果却没有直接联系,它的职责就是调度视图以哪种形式来体现。比如最常用的就是JSP,还可以是Freeemarker,Velocity and XSLT。
通过实现Result接口和方法可以自定义result类型,但一般很少自己专门定义,因为扩展struts-default,它里面就默认帮我们定义好了好几种result类型,这些类型已经足够使用了。最常用的比如有dispatcher,在配置文件中如果不写明哪一种类型,默认就是 dispatcher,它的实现机制来源于RequestDispatcher.forward()。再如Redirect重定向,使用 servlet&JSP开发时,经常使用的一种跳转方式。
写result配置文件时存在一个默认参数问题,
<result name="success" type="redirectAction">admin</result>
<result name="success" type="redirectAction">
<param name="actionName">admin</param>
</result>
这两种配置最后的结果都是一样,第一种并没有指名admin就是actionName这个参数,原因就是actionName就是一个默认参数,所以无需要专门指定。如果一个事先result的类,它有多个属性,这是就要专门写对它具体的属性参数进行配置。如果采用不带参数名的配置方法,可以实现org.apache.struts2.dispatcher.StrutsResultSupport这个类,然后实现doExecute(String finalLocation, ActionInvocation invocation) 这个方法。其中String finalLocation的值就是不带参数名的值在result配置中也可以带参数
<action name="SendUserToSearchEngineAction" class="myActionClass">
<result type='redirect' >
http://www.google.com/?myParam=${defaultUsername}
</result>
</action>${defaultUsername}是action中的属性
如果要在result中调出request,response这样的对象,可以使用org.apache.struts2.ServletActionContext里的静态方法来获得。在使用Ajax时,这时response返回的不再是一个JSP而是XML。但那些常用的result都是返回JSP页面,这样就有必要自定义一个result
-
2008年06月20日
JSP页面中导入标签库 - [编程开发]
1. 通过相对路径直接导入例如<%@ taglib uri="/WEB-INF/c.tld" prefix="c"%>,要先把c.tld文件复制到WEB-INF这个目录里2. 自定义link导入这是时候要在web.xml里面写上例如:<jsp-config>
<taglib>
<taglib-uri>/core</taglib-uri>
<taglib-location>/WEB-INF/c.tld</taglib-location>
</taglib>
</jsp-config>然后jsp文件里面加上<%@ taglib uri="/core" prefix="c"%>3. META-INF导入可以把tld文件放在META-INF文件夹里,然后在里面的tld文件要写清楚URI像JSTL或Struts标签都已经把相应的TLD文件放到META-INF文件里,打开那个tld文件可以看到里面的URI属性,比如Struts 2的 struts-tags.tld文件里写着 <uri>/struts-tags</uri>所以在JSP页面可以这样导入标签库<%@ taglib prefix="s" uri="/struts-tags" %>。另外JSTL的c.tld里是<uri>http://java.sun.com/jsp/jstl/core</uri>所以可以写成这样<%@ taglib uri="http://java.sun.com/jstl/core" prefix="c"%> -
2008年06月17日
Struts 2小结 - [编程开发]
那本《Struts 2 In Action》现在已经大致看了一遍,整个Struts的主要内容包括Action、Interceptor、Result、Taglib、Validation、I18N、conversion、OGNL、SSH integration。其中核心的部分是Action、Interceptor、Result。何谓核心部分,一个最简单的Struts程序从Client端发送一个请求,经过多层Interceptor最后到Action,再返回一个Result,整个过程分别对这三者对象操作,要使程序能跑通,这三者缺一不可。而那些经常要用到的Struts标签却不能称为核心组件,因为Struts 2在实现MVC中的View部分不再仅限于JSP,还可以以其他的Freeemarker,Velocity and XSLT形式来表现。
其他的像Validation一般也都是通过JavaScript来实现,只是用JavaScript还需要熟悉这门脚本语言。I18N估计也是很少用到,如果页面出现乱码,需要把这部分也考虑进去。和Spring、Hibernate的集成也很简单。
学习框架只需了解它的核心部分的原理,最重要的还是学习怎么用这个框架。说到学习怎么用,一般都是在以后实际项目开发中才会碰到,像Struts 2提供那么多标签,并不需要对每一个标签都熟悉,只有等用到的时候才去学它。
-
2008年06月17日
Google Web Toolkit - [编程开发]
GWT是一个以Java语言为工具,以类似Swing的方式编写UI组件,之后通过GWT Compiler编译为JavaScritp和HTML在客户端浏览器中运行的一个开发工具和编程模型。
书籍参考:
这本只有245页,但里面讲的并不是和基础的东西,而是几个实际应用的例子,显然不适合初学时用。

所以先看看这本了,现在大概知道怎么创建一个GWT项目和如何运行了

GWT版本更新非常快,上个月下载下来还是1.4版,这个月就升级到1.5了,看到最明显的变化就是创建默认模块。原来只有一个按钮,然后旁边显示Helloworld,现在变成是弹出一个对话框了
-
2008年06月14日
Struts 2 类型转换 - [编程开发]
在html表单中的文本框里输入的不管是数值类型还是字符类型,最后都是以String类传到后台。如果后台bean的属性是int、double、Date等,Struts就会自动把字符类型转换成相应的类型。
Struts2中默认提供了一些内置的转换器,包括8个基本类型,Date,array数组,List,Map类。也可以自定义转换器。通过实现ogln.TypeConverter接口实现它的方法就可以定义其他类型的转换,不过还要配置相应的资源文件。其实那几个内置的转换器已经足够使用了,很少会专门定义一个转换器。
基本数据类型转换器没有什么特殊要求,只要输入的值符合基本数据类型,它都会自动转换,否则会出现错误提示。比如对于int类型,前天就不能输入跟数字无关的字符。再来就是日期类型,默认好像是YY-MM-DD,比如2008-8-8,如果写成8-8-2008提交后就会出现错误提示。
对于Array数组,List,Map则需要配合OGNL表达式一起使用。比如后台有个属性是String [] name,在前台界面
<s:textfield name="names[0]" label="names"/>
<s:textfield name="names[1]" label="names"/>
<s:textfield name="names[2]" label="names"/>就会对这个数组赋值。List跟数组使用方式一样,但只针对不加泛型的基本数据类型的的List,如果加了泛型则是
<s:textfield name="users[0].username" label="Usernames"/>
<s:textfield name="users[1].username" label="Usernames"/>
<s:textfield name="users[2].username" label="Usernames"/>比如User类中有个username属性,List<User> users这个属性对应上面的写法。最后是Map的转换方式
<s:textfield name="maidenNames['beth']" label="Maiden Name"/>
<s:textfield name="maidenNames['sharon']" label="Maiden Name"/>
<s:textfield name="maidenNames['martha']" label="Maiden Name"/>[]里的值对应到Map中的Key
-
2008年06月12日
Struts 2文字编码问题 - [编程开发]
Struts2中的default.properties文件中默认设置的编码方式是struts.i18n.encoding=UTF-8。所以只要在新建的JSP页面设置charset=UTF-8就不会出现乱码问题,但前提是表单是通过post方法发送的。如果采用get方法仍然会产生乱码问题,不过只要在tomcat的server.xml文件中添加URIEncoding="UTF-8" 到<Connector connectionTimeout="20000" port="8080" protocol="HTTP/1.1" redirectPort="8443" URIEncoding="UTF-8" />就没问题了。无需添加任何过滤器,如果对UTF-8不满意,把所有编码相关的参数改为对应的编码就行了。 -
2008年06月12日
Struts 2中的拦截器(Interceptor) - [编程开发]
拦截器就是一种AOP的实现方式,传统的JSP&Servlet架构中,客户端发送一个请求,服务器端生成一个request对象,并执行相应的doget(),dopost()方法,最后由response返回一个响应到客户端,整个服务过程就结束了。所以所有的业务逻辑功能只能在doget(),dopost()里调用,这样整个业务就写死了,如果想增加新的功能,只能修改doget(),dopost方法,不符合开闭原则。
现在只要通过拦截器就可以添加新的功能而不修改原来的代码。

在Struts2中每发送一个请求都要经过好几层的拦截器最终才到达所调用的action。由多个拦截器组成的就是一个intercptor-stack,如果扩展了struts-default就默认集成了defaultstack。里面包含了许多常用的拦截器,比如文件上传时会用到fileUpload,要调出session对象由servletConfig来做。
因为defaultstack里的拦截器,默认已经配好了,所以无需要专门对这些拦截器进行配置。不过Struts2提供的拦截器还有许多需要专门配置的。比如timer,它是计算执行某个action所需要的时间。
比如在struts.xml文件中的某个action加入timer拦截器
<action name="upload" class="com.zhang.action.UploadAction" method="execute">
<result name="success">/pages/welcome.jsp</result>
<result name="input">/index.jsp</result>
<interceptor-ref name="timer"></interceptor-ref>
</action>最后会在控制台上打印
Executed action [/chapterFour/secure/ImageUpload!execute] took 123 ms.
servlet-config这个拦截器也是在defaultstack默认配置好了,它的作用的就是判断action看它是否实现了sessionaware等接口,并执行它的setSession方法







