昨天的listSelectCourse.jsp:
<body>
<form action="addCourseToStu.do" method="post">
<logic:iterate id="course" name="allCourses">
<c:set var="checked" value="" />
<c:if test="${my:contains(user.courses,course)}">
//这个my:contains(user.courses,course)是我们自定义的表达式函数,要求是公共且静态的
//并且要在tld中去配置!
<c:set var="checked" value="checked" />
</c:if>
//allCourses是上面请求作用域中的属性名
<input type="checkbox" name="course" value="${course.id}" ${checked}/>${course.coursename}
<br>
</logic:iterate>
<input type="submit" />
</form>
</body>
也就是说又需要一个接收addCourseToStu.do的Action了。这个Action没有Form
<action path="/addCourseToStu" type="cn.itcast.struts.action.AddCourseToStuAction" />
public class AddCourseToStuAction extends Action
{
public ActionForward execute()
{
String[] courseId = request.getParameterValues("course");
Set courses = new HashSet() ;
for(int i = 0 ; i < courseId.length ; i ++)
{
//根据主键创建cource,然后塞到课程集合里面
Course c = new Course() ;
c.setId(Integer.parseInt(courseId[i]));
courses.add(c);
}
//得到复选框中选中的那些课程ID
Student stu = (Student)request.getSession().getAttribute("user");
//从session中取出学生
//现在就是往数据关系表里面插入就可以了。
stu.setCourses(courses) ; //把学生原来选的课程全部都删掉,
//然后再加入那些新的课程就可以了。
//下面该插入数据库了……
SessionFactory factory = HibernateUtil.getSessionFactory(request);
Session session = null ;
try
{
session = factory.getCurrentSession() ;
session.beginTransaction();
session.update(stu); //更新对象!
//先删掉关系表中所有的记录,然后再一条一条的插入关系!同时更新学生……
session.getTransaction().commit() ;
}
catch(Exception ex)
{
if(session!=null&&session.getTransaction()!=null)
{
session.getTransaction().rollback();
}
ex.printStackTrace() ;
}
finally
{
session.close() ;
session = null ;
}
return mapping.findForward("success") ;
}
}
------------------------------------------------------------------
现在如果我们还要对课程进行增删改的话……
listCourseAction:(由listCourse.do地址可以到达它)
选出所有的课程并存入请求作用域:
public ActionForward execute()
{
request.setAttribute("courses",getList(request,Course.class));
return mapping.findForward("success");
}
public List getList(HttpServletRequest request ,Class clazz)
{
SessionFactory factory = HibernateUtil.getSessionFactory(request) ;
Session session = null ;
List l = null ;
try
{
session = factory.getCurrentSession() ;
session.beginTransaction();
Criteria c = session.createCriteria(clazz) ;
l = c.list() ;
session.getTransaction().commit();
}
catch(Exception e)
{
if(session!=null&&session.getTransaction()!=null)
{
session.getTransaction().rollback();
}
e.printStackTrace() ;
}
finally
{
if(session!=null)
{
session.close() ;
session = null ;
}
}
return l ;
}
这个Action选出所有的课程之后去listCourse.jsp页面:
<body>
<a href="addCourse.jsp">增加</a>
<table border="1">
<logic:iterate id="course" name="courses">
<tr>
<td>${course.id}</td>
<td>${course.coursename}</td>
<td>${course.period}</td>
<td><a href="modifyInput.do?id=${course.id}">修改</a>
<a href="delete.do?id=${course.id}">删除</a></td>
</tr>
</logic:iterate>
</table>
</body>
addCourse.jsp:(添加课程的名字、开课时间等)
要使用htmlform
<html:form action="/addCourseSubmit">
课程名称:<html:text property="coursename"/><br>
课程课时:<html:text property="period"/><br>
<html:submit />
</html:form>
使用动态表单:name是courseForm,类型是DynaActionForm
肯定还需要一个Action,path是/addCourseSubmit
success设为/listCourse.do
public class AddCourseSubmitAction extends Action
{
public ActionForward execute()
{
DynaActionForm courseForm = (DynaActionForm)form ;
Course c = new Course() ;
c.setCoursename(courseForm.get("coursename").toString());
c.setPeriod(Integer.parseInt(courseForm.get("period").toString()));
SessionFactory factory = HibernateUtil.getSessionFactory(request);
Session session = factory.getCurrentSession() ;
try
{
session.beginTransactin();
session.save(c);
session.getTransaction().commit() ;
}
catch()
{}
finally
{}
//save(request,Course.class,courseForm.getMap());
return mapping.findForward("success");
}
//也可以封装成:
public void save(HttpServletRequest request, Class clazz, Map map)
{
Object obj = null ;
SessionFactory factory = HibernateUtil.getSessionFactory(request);
Session session = null ;
try
{
obj = clazz.newInstance() ;
BeanUtils.populate(obj,map) ;//将map中的同名键设置obj中同名属性!
session = factory.getCurrentSession() ;
session.beginTransaction();
session.save(obj);
session.getTransaction().commit() ;
}
}
}
---------------------
为了解决乱码,必须重新实现ActionServlet的Process方法:
//必须在对请求里面的参数操作之前进行请求的转码,所以必须要在RequestProcessor
//处理之前去干这件事情!所以得重写ActionServlet的process方法!
//但是你也可以强行使用new String(str.getBytes("旧编码"),"新编码")的格式
//重新转码……
public class MyActionServlet extends ActionServlet
{
protected void process(HttpServletRequest request,HttpServletResponse response)
{
request.setCharacterEncoding("GBK");
super.process(request,response) ;
}
}
之后记得把web.xml中的ActionServlet的注册信息换成你自己重写的这个MyActionServlet!!
-----------------------------------------------------------------------
下午课程开始:
现在还剩下modifyInput.do和delete.do地址分别对应两个Action来处理修改和删除的
操作。
'
//成功后转到modify.jsp页面去,modify.jsp也要提交给一个Action,叫做
//modifySubmitAction,这两个Action都对应courseForm这个动态表单,
//modifySubmitAction修改后回到课程列表……
//利用ActionForm设置好默认值表单以供修改!
public class modifyInputAction extends Action
{
public ActionForward execute()
{
DynaActionForm courseForm = (DynaActionForm)form ;
SessionFactory factory = HibernateUtil.getSessionFactory(request) ;
Session session = null ;
//从超链接的get提交过来的参数id获取课程id
String courseIdStr = request.getParameter("id") ;
Integer courseId = null ;
if(courseIdStr != null)
{
//转换为整形id
courseId = new Integer(courseIdStr) ;
}
try
{
session = factory.getCurrentSession() ;
session.beginTransaction() ;
Course c = (Course)session.get(Course.class,courseId) ;
//用整型对象非延迟加载一条课程的记录!
courseForm.set("coursename",c.getCoursename());
courseForm.set("id",new Integer(c.getId()));
courseForm.set("period",new Integer(c.getPeriod()));
//这样设置完毕后,courseForm会自动被存储进作用域里,不用手工存了。
session.getTransaction().commit() ;
}
catch(HibernateException e)
{
if(session!=null&&session.getTransaction()!=null)
{
session.getTransaction().rollback() ;
}
}
finally
{
if(session!=null)
session.close() ;
}
return mapping.findForward("success");
}
}
//下面考虑一下怎么样能够让修改这一功能也能够变得通用
protected void populateForm(HttpServletRequest request ,
Class clazz, Serializable identifier,
ActionForm form)
//Serializable identifier代表主键,之所以定义为Serializable,
//是因为hibernate的get方法或是load方法加载主键的时候本来就要求
//主键实现Serializable接口
{
//现在ActionForm里面的属性不知道,你也不清楚是动态的form
//还是静态的form……所以要判断一下!
SessionFactory factory = HibernateUtil.getSessionFactory(request) ;
Session session = null ;
Map map = null ;
try
{
session = factory.getCurrentSession() ;
session.beginTransaction() ;
Object obj = session.get(clazz,identifier);
session.getTransaction().commit() ;
map = BeanUtils.describe(obj) ;//不要写成左边的样子
//这个describe方法是把obj中所有的属性都拿出来当字符串用了
//这样一来,map中就都存储的是字符串的数值了。
//应该写成下面这样子:
map = new PropertyUtilsBean().describe(obj);
//但是千万不要忘记describe会去找所有的getter方法,当然也包括那个
//getClass,所以后面迭代的时候要去除它!
}
catch(HibernateException e)
{
if(session!=null&&session.getTransaction()!=null)
{
session.getTransaction().rollback() ;
}
}
finally
{
if(session!=null)
session.close() ;
}
if(form instanceof DynaActionForm)
{
DynaActionForm dform = (DynaActionForm)form ;
Iterator it = map.entrySet().iterator() ;
while(it.hasNext())
{
if("class".equals(entry.getKey().toString()))
{
continue ;
}
Map.Entry entry = (Map.Entry)it.next() ;
dform.set(entry.getKey().toString(),entry.getValue()) ;
}
}
else
{
try
{
BeanUtils.populate(form,map) ;
}
catch()
{}
}
}
//像上面那么封装之后,底下一句话就可以满足修改要求了!
populateForm(request,courseForm,Course.class, new Integer(request.getParameter(id)))
========================================================================
现在来看modifySubmitAction:
//进行数据库的修改……也就是把form表单对象中的值送到一个实体中:
//BeanUtils.populate(c,courseForm.getMap()) ;
//如果是静态表单的话,应该先用describe方法取出一个map,然后再populate
//就可以了。
public ActionForward execute()
{
DynaActionForm courseForm = (DynaActionForm)form ;
SessionFactory factory = HibernateUtil.getSessionFactory(request);
Course c = new Course() ;
c.setId(new Integer(courseForm.get("id").toString()).intValue());
c.setCoursename(courseForm.get("coursename").toString()) ;
c.setPeriod(new Integer(courseForm.get("period").toString()));
//上面将页面中的表单值设置到实体中去。
Session sessin = factory.getCurrentSession() ;
session.beginTransaction();
session.update(c);
session.getTransaction().commit() ;
return mapping.findForward("success");
}
最后还剩下一个delete,就比较简单了……
http://ardownload.adobe.com/pub/adobe/reader/win/8.x/8.0/chs/AdbeRdr80_zh_CN.exe