这个文章说的很详细,很值得一看.
Maven + SpringMVC + Mybatis【绝非原创,单纯整理】【四】: http://playgod1984.iteye.com/blog/984113 最后面提示说id和映射关系.
考虑到MyBatis注解方式比较麻烦,可能都还没有xml来的方便,易读.所以就没有加上去.如有兴趣,自行参考 http://panyongzheng.iteye.com/blog/1604067
spring+springmvc+ibatis整合注解方式实例(附带数据库) http://blog.csdn.net/mgb18986349193/article/details/8494494
这个例子也很详细,但是并没有对Mapper接口和xml里面的sql id做映射.不过这是否是必须的?可以适当考虑.
Spring MVC 3.0.5+Spring 3.0.5+MyBatis3.0.4全注解实例详解三
http://www.2cto.com/kf/201108/98937.html
基于namespace接口与公用dao的区别,从MyBatis3.0开始,对mapper中的namespace属性新增了一个特性:可以指定具体的接口来作为持久化操作类,在接口中定义与映射文件中id属性值相同的方法,MyBatis会自动去绑定和执行对应的SQL语句。这种接口实现方式,需要为每个Mapper创建一个接口,如果系统做大了,维护这些类会比较麻烦,大象个人倾向于基础服务式的Dao实现类.
if exists (select 1
from sysobjects
where id = object_id('Users')
and type = 'U')
drop table Users
go
/*==============================================================*/
/* Table: Users */
/*==============================================================*/
create table Users (
id int not null,
name varchar(50) null,
password varchar(50) null,
email varchar(50) null,
remarks varchar(500) null,
constraint PK_USERS primary key nonclustered (id)
)
go
SpringMVC
----------------------------------------------------------------------
jars of SpringMVC
com.springsource.com.mchange.v2.c3p0-0.9.1.2.jar
com.springsource.net.sf.cglib-2.2.0.jar
com.springsource.org.aopalliance-1.0.0.jar
com.springsource.org.apache.commons.fileupload-1.2.0.jar
com.springsource.org.apache.commons.httpclient-3.1.0.jar
com.springsource.org.apache.commons.lang-2.4.0.jar
com.springsource.org.apache.commons.logging-1.1.1.jar
com.springsource.org.apache.commons.pool-1.5.3.jar
com.springsource.org.apache.log4j-1.2.15.jar
com.springsource.org.aspectj.weaver-1.6.8.RELEASE.jar
com.springsource.org.codehaus.jackson.mapper-1.0.0.jar
commons-dbcp.jar
jotm.jar
org.springframework.aop-3.0.5.RELEASE.jar
org.springframework.asm-3.0.5.RELEASE.jar
org.springframework.aspects-3.0.5.RELEASE.jar
org.springframework.beans-3.0.5.RELEASE.jar
org.springframework.context-3.0.5.RELEASE.jar
org.springframework.core-3.0.5.RELEASE.jar
org.springframework.expression-3.0.5.RELEASE.jar
org.springframework.instrument-3.0.5.RELEASE.jar
org.springframework.instrument.tomcat-3.0.5.RELEASE.jar
org.springframework.jdbc-3.0.5.RELEASE.jar
org.springframework.orm-3.0.5.RELEASE.jar
org.springframework.oxm-3.0.5.RELEASE.jar
org.springframework.transaction-3.0.5.RELEASE.jar
org.springframework.web-3.0.5.RELEASE.jar
org.springframework.web.portlet-3.0.5.RELEASE.jar
org.springframework.web.servlet-3.0.5.RELEASE.jar
org.springframework.web.struts-3.0.5.RELEASE.jar
persistence.jar
xapool.jar
-----------------------------------------------------------------------------------
web.xml 设定applicationContext.xml,SpringMVCIbatis-servlet.xml默认位置
======================================
<?xml version="1.0" encoding="UTF-8"?> <web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"> <display-name></display-name> <context-param> <param-name>contextConfigLocation</param-name> <!-- 设定applicationContext.xml的默认路径 --> <param-value>/WEB-INF/classes/applicationContext.xml</param-value> </context-param> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <servlet> <servlet-name>SpringMVCIbatisSmartClient</servlet-name> <servlet-class> org.springframework.web.servlet.DispatcherServlet </servlet-class> <load-on-startup>1</load-on-startup> <init-param> <param-name>contextConfigLocation</param-name> <!-- 设定servlet.xml的默认路径 --> <param-value>/WEB-INF/classes/SpringMVCIbatis-servlet.xml</param-value> </init-param> </servlet> <servlet-mapping> <servlet-name>SpringMVCIbatisSmartClient</servlet-name> <url-pattern>*.do</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app>
SpringMVCIbatis-servlet.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:context="http://www.springframework.org/schema/context" xmlns:mvc="http://www.springframework.org/schema/mvc" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd"> <mvc:annotation-driven /> <!-- 排除Service注解扫描 --> <context:component-scan base-package="com"> <context:include-filter type="annotation" expression="org.springframework.stereotype.Controller" /> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Service" /> </context:component-scan> <bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"></bean> <bean class="org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter"></bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/pages/"></property> <property name="suffix" value=".jsp"></property> </bean> </beans>
applicationContext.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:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:jdbc="http://www.springframework.org/schema/jdbc" xmlns:p="http://www.springframework.org/schema/p" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:mvc="http://www.springframework.org/schema/mvc" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd" default-autowire="byName" default-lazy-init="true"> <!-- 排除Controller注解扫描 --> <context:component-scan base-package="com"> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller" /> </context:component-scan> </beans>
HelloController.java
==========================================
package com.controller; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.servlet.ModelAndView; @Controller public class HelloController { @RequestMapping(value="sayHello") public ModelAndView sayHello(){ ModelAndView view = new ModelAndView("sayHello"); view.addObject("helloworld", "Hello World From Server."); return view; } }
index.jsp
===========================================
<%@ page language="java" import="java.util.*" pageEncoding="ISO-8859-1"%> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>My JSP 'index.jsp' starting page</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> <meta http-equiv="description" content="This is my page"> <!-- <link rel="stylesheet" type="text/css" href="styles.css"> --> </head> <body> <a href="sayHello.do">sayHello</a> </body> </html>
WebRoot/pages/sayHello.jsp
=====================================
<%@ page language="java" import="java.util.*" pageEncoding="ISO-8859-1"%> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>helloworld</title> </head> <body> <h1>${helloworld}</h1> </body> </html>
增加MyBatis3.0功能
jars of Project
========================================
cglib-2.2.2.jar
com.springsource.com.mchange.v2.c3p0-0.9.1.2.jar
com.springsource.net.sf.cglib-2.2.0.jar
com.springsource.org.aopalliance-1.0.0.jar
com.springsource.org.apache.commons.fileupload-1.2.0.jar
com.springsource.org.apache.commons.httpclient-3.1.0.jar
com.springsource.org.apache.commons.lang-2.4.0.jar
com.springsource.org.apache.commons.logging-1.1.1.jar
com.springsource.org.apache.commons.pool-1.5.3.jar
com.springsource.org.apache.log4j-1.2.15.jar
com.springsource.org.aspectj.weaver-1.6.8.RELEASE.jar
com.springsource.org.codehaus.jackson.mapper-1.0.0.jar
commons-dbcp.jar
commons-logging-1.1.1.jar
jotm.jar
junit-4.8.1.jar
log4j-1.2.15.jar
mybatis-3.0.4.jar
mybatis-spring-1.0.0.jar
ognl-2.6.9.jar
org.springframework.aop-3.0.5.RELEASE.jar
org.springframework.asm-3.0.5.RELEASE.jar
org.springframework.aspects-3.0.5.RELEASE.jar
org.springframework.beans-3.0.5.RELEASE.jar
org.springframework.context-3.0.5.RELEASE.jar
org.springframework.core-3.0.5.RELEASE.jar
org.springframework.expression-3.0.5.RELEASE.jar
org.springframework.instrument-3.0.5.RELEASE.jar
org.springframework.instrument.tomcat-3.0.5.RELEASE.jar
org.springframework.jdbc-3.0.5.RELEASE.jar
org.springframework.orm-3.0.5.RELEASE.jar
org.springframework.oxm-3.0.5.RELEASE.jar
org.springframework.transaction-3.0.5.RELEASE.jar
org.springframework.web-3.0.5.RELEASE.jar
org.springframework.web.portlet-3.0.5.RELEASE.jar
org.springframework.web.servlet-3.0.5.RELEASE.jar
org.springframework.web.struts-3.0.5.RELEASE.jar
persistence.jar
spring-test-3.0.5.RELEASE.jar
sqljdbc4.jar
xapool.jar
src/config/database.properties
======================================
driver=com.microsoft.sqlserver.jdbc.SQLServerDriver url=jdbc:sqlserver://localhost:1433; DatabaseName=SmartClientDemos username=sa password=sa
Users.java
==================================
package com.pojo; public class Users { private long id; private String name; private String password; private String email; private String remarks; public long getId() { return id; } public void setId(long id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String getEmail() { return email; } public void setEmail(String email) { this.email = email; } public String getRemarks() { return remarks; } public void setRemarks(String remarks) { this.remarks = remarks; } }
两种方式:
1.DAO方式,直接在dao里面调用xml的sql id.
IUsersDao.java
========================================
package com.dao; import java.util.List; public interface IUsersDao { public abstract List queryUsersByName(String name); }
UsersDao.java
=================================
package com.dao.impl; import java.util.List; import org.mybatis.spring.support.SqlSessionDaoSupport; import org.springframework.stereotype.Repository; import com.dao.IUsersDao; import com.pojo.Users; @Repository public class UsersDao extends SqlSessionDaoSupport implements IUsersDao{ @Override public List queryUsersByName(String name){ System.out.println("Users.queryUsersByName()"); // com.mapper.IUsersMapper.queryUsersByName = (namespace+select/insert/update/delete)id return getSqlSession().selectList("com.mapper.IUsersMapper.queryUsersByName", name); } }
2.Mapper方式:A,实现类在实现接口的时候,直接封装和使用接口; b,接口的方法跟xml里面的sql id一定要一样.
IUsersMapper.java
=====================================
package com.mapper; import com.pojo.Users; public interface IUsersMapper { public abstract Users queryUsersById(int id); public abstract void insertUser(Users user); public abstract void updateUser(Users user); }
UsersMapper.java
==================================
package com.mapper.impl; import com.mapper.IUsersMapper; import com.pojo.Users; public class UsersMapper implements IUsersMapper { private IUsersMapper usersMapper; @Override public Users queryUsersById(int id) { return usersMapper.queryUsersById(id); } @Override public void insertUser(Users user) { System.out.println("UsersMapper insertUser"); usersMapper.insertUser(user); } @Override public void updateUser(Users user) { System.out.println("UsersMapper updateUser"); usersMapper.updateUser(user); } public IUsersMapper getUsersMapper() { return usersMapper; } public void setUsersMapper(IUsersMapper usersMapper) { this.usersMapper = usersMapper; } }
注意:
public class UsersMapper implements IUsersMapper {
private IUsersMapper usersMapper;
}
实现接口的同时,又使用它自己,并且这个方法名字又对应xml里面的ID.
service->mapper->DAO
http://www.idashu.me/Mybatis-development.html 这里的说法又是不一样,不知道能否运行不(还没尝试)?
service->mapper, 它少了DAO,其实mapper就是DAO.
注意文件的存放位置.
http://www.2cto.com/kf/201108/98937.html
基于namespace接口与公用dao的区别,从MyBatis3.0开始,对mapper中的namespace属性新增了一个特性:可以指定具体的接口来作为持久化操作类,在接口中定义与映射文件中id属性值相同的方法,MyBatis会自动去绑定和执行对应的SQL语句。这种接口实现方式,需要为每个Mapper创建一个接口,如果系统做大了,维护这些类会比较麻烦,大象个人倾向于基础服务式的Dao实现类.
同时使用两种方式的例子:
IUsersService.java
=======================================================
package com.service; import com.pojo.Users; public interface IUsersService { public abstract Users queryUsersById(int id); public abstract Users queryUsersByName(String name); public abstract void saveUser(Users user); }
UsersServiceImpl.java
=======================================================
package com.service.impl; import java.util.List; import javax.annotation.Resource; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Propagation; import org.springframework.transaction.annotation.Transactional; import com.dao.IUsersDao; import com.mapper.IUsersMapper; import com.pojo.Users; import com.service.IUsersService; @Service(value="usersService") @Transactional(rollbackFor=Exception.class) public class UsersServiceImpl implements IUsersService { @Resource(name="usersMapper") private IUsersMapper usersMapper; @Resource(name="usersDao") private IUsersDao usersDao; @Override @Transactional(propagation=Propagation.REQUIRED, readOnly=true) public Users queryUsersById(int id){ return usersMapper.queryUsersById(id); } @Override @Transactional(propagation=Propagation.REQUIRED, readOnly=true) public Users queryUsersByName(String name){ List list = usersDao.queryUsersByName(name); System.out.println("list = "+list==null?"0":list.size()); if(list!=null&&list.size()>0) return (Users)list.get(0); return null; } @Override @Transactional(propagation=Propagation.REQUIRED) public void saveUser(Users user){ if(user.getId()<=0){ System.out.println("insertUser"); usersMapper.insertUser(user); }else{ System.out.println("updateUser"); usersMapper.updateUser(user); } //throw new RuntimeException("@@ Rollback for Debug.........."); } }
HelloController.java
===========================================
package com.controller; import javax.annotation.Resource; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.servlet.ModelAndView; import com.pojo.Users; import com.service.IUsersService; @Controller public class HelloController { @Resource(name="usersService") private IUsersService usersService; @RequestMapping(value="sayHello") public ModelAndView sayHello(){ ModelAndView view = new ModelAndView("sayHello"); view.addObject("helloworld", "Hello World From Server."); //insert Users user = new Users(); user.setName("Pandy"); user.setPassword("pandy"); user.setEmail("[email protected]"); user.setRemarks("nothing"); usersService.saveUser(user); Users user1 = usersService.queryUsersByName(user.getName()); //Users user1 = usersService.queryUsersById(0); if(user1!=null){ System.out.println(user1.getName()); view.addObject("userName", user1.getName()); }else{ System.out.println("Noting"); view.addObject("userName", "Noting"); } return view; } }
com/mapper/xml/Users.xml
==================================================
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.mapper.IUsersMapper"> <select id="queryUsersById" parameterType="int" resultType="Users"> select id, name,password,email, remarks from Users where id = #{id} </select> <select id="queryUsersByName" parameterType="string" resultType="Users"> select id, name,password,email, remarks from Users where name = #{name} </select> <insert id="insertUser" parameterType="Users"> insert into Users(id, name,password,email, remarks) values(#{id}, #{name},#{password},#{email}, #{remarks}) </insert> <update id="updateUser"> update Users set name=#{name},password=#{password},email=#{email},remarks=#{remarks} where id=#{id} </update> </mapper>
mybatis-config.xml
========================================
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <!-- 设定别名 --> <typeAliases> <typeAlias alias="Users" type="com.pojo.Users"/> </typeAliases> <!-- 增加mapper.xml文件 --> <mappers> <mapper resource="com/mapper/xml/Users.xml"/> </mappers> </configuration>
applicationContext.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:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:jdbc="http://www.springframework.org/schema/jdbc" xmlns:p="http://www.springframework.org/schema/p" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:mvc="http://www.springframework.org/schema/mvc" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd" default-autowire="byName" default-lazy-init="true"> <context:component-scan base-package="com"> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller" /> <!-- <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Service" /> --> </context:component-scan> <!-- 增加数据库配置文件 --> <context:property-placeholder location="classpath:config/database.properties"/> <!-- DataSource --> <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="${driver}"/> <property name="url" value="${url}"/> <property name="username" value="${username}"/> <property name="password" value="${password}"/> </bean> <!-- 事务处理 --> <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource" /> </bean> <tx:annotation-driven transaction-manager="transactionManager"/> <!-- sqlSessionFactory配置 --> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="configLocation" value="classpath:mybatis-config.xml" /> <property name="dataSource" ref="dataSource" /> </bean> <!-- Mapper的配置 --> <bean id="usersMapper" class="org.mybatis.spring.mapper.MapperFactoryBean"> <property name="mapperInterface" value="com.mapper.IUsersMapper"/> <property name="sqlSessionFactory" ref="sqlSessionFactory"/> </bean> </beans>
SpringMVCIbatis-servlet.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:context="http://www.springframework.org/schema/context" xmlns:mvc="http://www.springframework.org/schema/mvc" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd"> <mvc:annotation-driven /> <context:component-scan base-package="com"> <context:include-filter type="annotation" expression="org.springframework.stereotype.Controller" /> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Service" /> </context:component-scan> <bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"></bean> <bean class="org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter"></bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/pages/"></property> <property name="suffix" value=".jsp"></property> </bean> </beans>
log4j.properties
=================================
#logger level default is INFO log4j.rootLogger=info,console,file #append to console log4j.appender.console=org.apache.log4j.ConsoleAppender log4j.appender.console.layout=org.apache.log4j.PatternLayout log4j.appender.console.layout.ConversionPattern=%d %p - %m%n #append to file log4j.appender.file=org.apache.log4j.RollingFileAppender log4j.appender.file.File=/demo.log log4j.appender.file.MaxFileSize=1MB log4j.appender.file.MaxBackupIndex=10000 log4j.appender.file.layout=org.apache.log4j.PatternLayout log4j.appender.file.layout.ConversionPattern=%d %p - %m%n #ibatis logger config log4j.logger.com.ibatis=debug log4j.logger.com.ibatis.common.jdbc.SimpleDataSource=debug log4j.logger.com.ibatis.common.jdbc.ScriptRunner=debug log4j.logger.com.ibatis.sqlmap.engine.impl.SqlMapClientDelegate=debug log4j.logger.java.sql.Connection=debug log4j.logger.java.sql.Statement=debug log4j.logger.java.sql.PreparedStatement=debug,stdout
WebRoot/pages/sayHello.jsp
=================================================
<%@ page language="java" import="java.util.*" pageEncoding="ISO-8859-1"%> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>helloworld</title> </head> <body> <h1>${helloworld}</h1> <br> <h3>${userName}</h3> </body> </html>