《HTML教程》-12.5.3-12.6教学材料_第1页
《HTML教程》-12.5.3-12.6教学材料_第2页
《HTML教程》-12.5.3-12.6教学材料_第3页
《HTML教程》-12.5.3-12.6教学材料_第4页
《HTML教程》-12.5.3-12.6教学材料_第5页
已阅读5页,还剩44页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

首先,根据学生对课程的选择,构造请求参数字符串。学生选修一门课程,就是把该课程ID对应的复选框选中。要确定学生选修了哪几门课程,只需要看一下选中状态的复选框有几个即可。回想一下DOM操作中节点的引用(查找)方法(见6.3节表6-4),自HTML5以后新增了一个querySelectorAll()方法,可以按照CSS的选择器选择指定的元素。CSS提供了属性选择器和伪类(或伪元素),可以用来选择某些网页元素。在这里,我们需要查找所有type=’checkbox’,且checked属性为checked的input元素,根据这个要求,我们可以构造一个以下的选择器:input[type='checkbox']:checked然后,可以使用document对象的querySelectorAll()方法查找所有符合这一选择器的所有复选框,得到一个NodeList类型的集合。注意这个NodeList不是普通的数组,不能使用遍历数组的办法(for…in)遍历这个集合。只能使用最原始的for循环来遍历它,找到选择的所有课程,获取所有选中课程的代码如下:varselectedCourses=document.querySelectorAll("input[type='checkbox']:checked");把所有选择的课程构造成以下格式的请求参数字符串:courseId=200807006&courseId=200807008&courseId=200907016请注意,最后一个课程ID(200907016)的后面没有&符号,而其他课程ID后均有一个&符号,所以最后一个课程ID要进行特殊处理。构造请求参数的代码如下:vardata=""; for(vari=0;i<selectedCourses.length;i++){ data+="courseId="+selectedCourses[i].value; if(i!=selectedCourses.length-1){ data+="&"; } }最后一个课程ID为selectedCourseNodeList中下标为selectedCourse.length–1的课程对象的ID。所以每次循环中都要判定是否为最后一个元素,如果不是,则在其后添加&符号。如果是最后一个元素,则不添加&。这就保证了最后一个ID后面不会添加&,从而保证请求参数的最后不会加上&。构造请求参数字符串以后,就是创建异步对象、初始化请求——这里请求的URL是studentServlet?method=selectCourse,即StudentServlet中的selectCourse方法,注册事件处理程序处理服务器响应结果,最后是发送数据,也就是这里的请求参数字符串。这里需要强调的是:这个操作会对服务器产生影响(在服务器上保存数据),所以使用POST请求方式;以POST方式发送请求时,在发送请求之前(即调用send()方法之前)设置请求头Content-Type,其值为application/x-www-form-urlencoded。这一点是必须的,否则服务器收不到客户端发送的数据。用到的代码如下:req.setRequestHeader("Content-Type","application/x-www-form-urlencoded"); req.send(data);提交选课请求的完整代码如清单12-13所示。12.5.4显示选课结果——selectResult函数

这个函数十分简单,只是负责把服务器的响应显示在提示框中(即清单12-4中的<divid="tip"/>)。完整代码如清单12-14所示,12.5.5控制层选课功能的实现——selectCourse控制层所有关于学生的功能都在StudentServlet类中实现,选课功能也不例外。在StudentServlet.java中添加selectCourse方法,由于这个方法签名比较长,难于记住,我们还是采用老办法——复制+改名就可以了。在这个方法中,首先要做的是接收客户端传来的参数。在12.5.3节,我们已经注意到请求参数字符串的格式为:courseId=200807006&courseId=200807008&courseId=200907016也就是说相同名字的参数courseId有多个,而不是只有一个。在JSP中接收这种“多值”参数用的是request对象(也就是形式参数req)的getParameterValues()方法,它返回一个String类型的数组,代码如下:String[]courseIds=req.getParameterValues("courseId");第二步,接下来要做的就是从Session对象中(这也就是为什么要求选课之前必须登录的原因)取出保存的学生ID(学号),并对响应信息进行初始化:Stringmsg="你还没有登录,请登录后再选!"; StringstudentId=(String)req.getSession().getAttribute(Constants.USER_NAME);如果取出的studentId为null,也就是说学生尚未登录,则直接提示"你还没有登录,请登录后再选!",然后直接返回。if(null==studentId){ showTip(resp,msg); return; }这里的showTip方法就是BaseServlet中用于向客户端发送文本消息的方法。它的完整代码请参见12-2。如果学生已经登录,则调用业务逻辑层StudentLogic的saveSelectedCourse方法,并把学生的学号和已经选择的课程号传递给它,代码如下:booleanflag=studentLogic.saveSelectedCourse(studentId,courseIds); if(flag){ msg="选课成功!"; }else{ msg="选课信息保存失败"; } showTip(resp,msg); return;然后,根据saveSelectedCourse方法的返回值,如果为true,则表示选修课程保存成功,则向客户端响应“选课成功!”,否则向客户端响应“选课信息保存失败”。saveSelectedCourse方法的完整代码如清单12-15所示。12.5.6选修课程的业务层实现——saveSelectedCourse方法

这里主要的任务是构造一个SQL的insert语句,将选择的内容(课程)保存到数据库中。选课是向selcourse表中插入一条数据,构造的SQL语句如下:Stringsql="insertintoselcourse(selcurId,stuId,courseId,"+"selTerm,grade)values(?,?,?,?,?)";然后,调用BaseDao中的saveSelCourseBatch()方法,并将sql语句、学生的学号和选择的课程作为参数传递给它,并返回它的返回值即可,代码如下:booleanflag=baseDao.saveSelCourseBatch(sql,studentId,courseIds); returnflag;完整的代码如清单12-16所示。12.5.7选修课程的DAO层实现——saveSelCourseBatch方法

虽然项目的框架实现了项目所需要的大部分功能,但DAO层并没提供这个批处理保存的功能,所以需要我们来专门实现。要进行数据库操作,首先要创建Connection类型的对象conn和PreparedStatement类型的对象stmt,分别代码Java的数据库连接和预编译的SQL语句。代码如下:Connectionconn=null;PreparedStatementstmt=null;然后,获取数据库连接,构造预处理语句,并对SQL语句中的参数(即清单12-16中构sql中的?号所表示的参数)进行赋值,并把构造好的每条SQL语句添加到批处理中,代码如下:conn=getConnection();stmt=conn.prepareStatement(sql);for(inti=0;i<params.length;i++){stmt.setString(1,IDProducer.getId());stmt.setString(2,studentId);stmt.setString(3,params[i]);stmt.setString(4,null);stmt.setInt(5,0);stmt.addBatch();}其中,stmt.setString(1,IDProducer.getId())中的1表示SQL语句中的第1个?号,第二个参数IDProducer.getId()框架中产生ID(即数据库主键的类,getId()是返回产生ID的方法)。stmt.setInt(5,0)与之类似,就是对第5个?号赋值,这个?号代表的是成绩字段,这里赋初值为0。与之类似的还有setFloat()、setDouble()等等,每个Java的原始类型都有相应的set方法。Stmt.addBatch()方法是将当前生成的SQL语句放到批处理中,等待执行。批处理语句添加完成后,就是执行批处理,把其的SQL语句全部执行一次,代码如下:int[]rows=stmt.executeBatch();方法executeBatch()进行批处理语句的执行,并返回一个整型的数组,如果数组中的每个元素都为1,则表示批处理执行成功,否则执行失败。下面的代码是对执行结果的判断:if(null!=params&&null!=rows){if(params.length==rows.length){booleanflag=true;for(inti=0;i<rows.length;i++){if(rows[i]<=0){flag=false;break;}

}returnflag;}}这里的params是String类型的数组,为saveSelCourseBatch()方法的最后一个参数,它表示学生一次选课所选择的所有课程。每门课程在selcourse表中保存为一条记录,所以要验证params数组的长度和rows整型数组(executeBtach()方法的返回值)的长度是否相等,if(params.length==rows.length)。若不相等,则批处理一定执行失败(说明有某门课程没有保存到数据库中)。只有二者相等的情况下,才进行进一步的判断:先假定批处理执行结果是成功的,即booleanflag=true;再遍历这个rows数组,看是否每个元素都是1(即大于0)。如果有一个元素不是1,则表示批处理执行失败,剩下的没有进一步判断的必要,把flag置为false,然后直接退出循环,返回flag标志,对应的代码如下:booleanflag=true;for(inti=0;i<rows.length;i++){if(rows[i]<=0){flag=false;break;}}returnflag;如果rows数组的每个元素都是1,数据库批处理执行成功,则flag保持最初的值true,表示批处理执行成功。完整的代码如清单12-17所示。经过了很长一段时间的埋头苦干,你已经完成了选课功能的编写,从视图层到控制层,再到业务层,最后是DAO层。来回顾一下编写代码的历程,整理一下自己的思路,你会得到如下的编写/调用路径,如图12-8所示。图12-8选课功能实现流程好了,有了这幅图代码编写思路就十分清晰了。还有一个“查询成绩”的功能,请大家比照12.5节“选课功能的实现”,自己完成,锻炼大家学以致用的能力。如果实在有困难的读者,可以参照随书源码,该部分的源码在第12章目录下。为了大家学习方便,还在第12章目录中放置了一个只有项目框架的“空项目”AjaxSyn_Empty,大家可以在这个“空项目”的基础上进行学习开发,避免因叙述不周而造成的某些组件的缺失,造成项目无法运行。

在不同的Eclipse中导入项目可能会产生错误,解决办法参见附录A2.7。12.6总结

本章主要以学生选课系统实例描述了Ajax在JavaWeb项目中的实际应用,实际上Ajax不只仅仅应用于JavaWeb项目中,也可用于其他语言的Web系统。Ajax是独立于任何Web平台的,即可用于J

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论