普通PC机,Windows 10系统,Java EE,Mysql数据库环境,Navicat for Mysql.
二、实验目的完成一个基于jsp+servlet+javabeen的学生课程成绩管理系统,熟悉且掌握中间件的集成功能。
三、实验内容(1)完成2个数据库
每一个数据库中有3张表,
stu1
course1
sc1
stu2:
course2:
sc2:
两个数据库中,表的属性不同,且学号和课程号的类型不同。
(2)完成针对数据库本身,表中的字段,属性,格式等的描述。
xml最终版:
DB1:
DB2:
student2 stu2 stid int ssname varchar course2 coid int coname varchar sc2 stid int coid int grade int Student.xml 将上面的两个数据库中属性的不同的字段名统一化。 //统一数据库名称 student1 student2 //统一不同数据库中相对应的表名 student course sc本系统有登录、查询、增加、删除和修改功能,旨在为系统管理员提供学生成绩信息的查询、增加、删除和修改功能,数据库中的数据并不是很多,有待改进,具体的功能展示如下:
1.登录页面(登录功能是所有的管理员有公共的账号和密码,有待改善)
2.功能界面:
3.显示学生成绩界面
4.可以通过学号、课程号查询数据库中学生的成绩。
5.添加学生课程成绩界面
6.修改指定数据库中的学生选课成绩信息(PS:本项目由于在删除和修改的时候需要首先通过查询方式查询指定cid或则sid的学生选课成绩的信息,然后再从查询所得列表中删除或则修改某个学生的课程信息,所有需要再表单中填写两次数据库的id,因此删除和修改有待完善)
7.删除指定学生的学生课程成绩信息
项目简介与中间件设计
bean、bean1是对student1、student2中实体类的属性的定义(get、set方法)。为了方便集成,将不同数据库中类的属性类型设置为统一的数据类型,譬如表stu1中的sid,sname的数据类型为String、stu2中的stid,ssname的数据类型也为String,由于数据库studnet2中表stu2的stid数据类型为int,所以在初始化stu2类的时候将stid强制转换为String.从而解决了从不同数据库中获得数据时的数据类型不一致的问题。
dao是对数据库的增删改、查询操作,controller是servlet方法的操作,与jsp协同。utils是对数据库的连接。
中间件的部分主要由分解合并器、查询器、元数据三部分构成。它不存储任何异构数据库中的实际数据。而是在用户提交了一个查询后,由分解器将用户查询翻译为一个或多个对数据库的查询。然后这些子查询由相关的查询器发送给后台数据库进行查询操作,分解合并器接着将查询器发送回来的各个数据源的查询结果进行综合处理,经由整合模式的设计,将相关的多条信息整合成一个记录,以相同的接口输出返回给用户。
接下来用一个具体的项目具体分析中间件的集成部分:
首先时xml部分,(实验内容的第二部分已给出),1.xml和2.xml分别表述数据库student1和student2中的各个表的属性,student.xml描述studnet1、studnet2中数据不一致的地方,比如将数据名整合为统一的标签。这样对用户显示的是student.xml中统一的标签名,在获取不同数据库中的数据时使用1.xml和2.xml中标签名。
DOMxml.java是对xml的解析,将1.xml和2.xml中的节点值放在allfields数组中,将student.xml中的节点值放在unfields数组中,将数据库名、表名放在db_table数中,从而可以通过数据获得数据名,表名和表中的列名,代码如下:
package xml;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import javax.xml.parsers.documentBuilder;
import javax.xml.parsers.documentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import org.w3c.dom.document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;
public class DOMxml {
ArrayList lists = new ArrayList();//统一的字段名
ArrayList unfields = new ArrayList();//统一的字段名标签
ArrayList> allfields = new ArrayList();
ArrayList db_table = new ArrayList();
public static int db_num;
static int table_num;
//获取数据库和表的数量
public void Num() throws Exception{
//创建DOM文档对象
documentBuilderFactory dFactory = documentBuilderFactory.newInstance();
documentBuilder builder = dFactory.newdocumentBuilder();
document doc;
doc = builder.parse(new File("E:\myjavaproject\data\src\xml\student.xml"));
NodeList nl = doc.getElementsByTagName("DBname");
db_num = nl.getLength();
//System.out.println(db_num);
nl = doc.getElementsByTagName("table_name");
table_num = nl.getLength();
//System.out.println(table_num);
}
//获取网页显示的统一 字段名 lists
public void CreateWeb(){
try {
documentBuilderFactory dbf = documentBuilderFactory.newInstance();
documentBuilder db = dbf.newdocumentBuilder();
document document = db.parse(new File(“E:myjavaprojectdatasrcxmlstudent.xml”));
NodeList users = document.getChildNodes();
for (int i = 0; i < users.getLength(); i++) {
//x
Node user = users.item(i);
//db table
NodeList userInfo = user.getChildNodes();
for (int j = 4; j < userInfo.getLength(); j++) {//由于要获取表名,标签是成对出现的所以不需要打印db和table,从4开始
if(userInfo.item(j).getNodeName()!= "#text") {
//获得第二级
Node node = userInfo.item(j);
//获得第三级
NodeList usermeta = node.getChildNodes();
//System.out.println(node.getNodeName());
ArrayList list = new ArrayList();
list.add(node.getNodeName());
for (int k = 0; k < usermeta.getLength(); k++) {
//System.out.println(usermeta.item(k).getNodeName());fanhui kong
if(usermeta.item(k).getNodeName() != "#text") {
list.add(usermeta.item(k).getTextContent());
//System.out.print(usermeta.item(k).getTextContent());
}
}
lists.add(list);
}
}
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
//获取统一的字段标签 unfields
public void UniformField(){
try {
documentBuilderFactory dbf = documentBuilderFactory.newInstance();
documentBuilder db = dbf.newdocumentBuilder();
document document = db.parse(new File("E:\myjavaproject\data\src\xml\student.xml"));
NodeList users = document.getChildNodes();
for (int i = 0; i < users.getLength(); i++) {
//x
Node user = users.item(i);
//db table
NodeList userInfo = user.getChildNodes();
for (int j = 4; j < userInfo.getLength(); j++) {
if(userInfo.item(j).getNodeName()!= "#text") {
//db
Node node = userInfo.item(j);
//dbname
NodeList usermeta = node.getChildNodes();
//System.out.println(node.getNodeName());
ArrayList field = new ArrayList();
field.add(node.getNodeName());
for (int k = 0; k < usermeta.getLength(); k++) {
if(usermeta.item(k).getNodeName() != "#text") {
//System.out.println(usermeta.item(k).getNodeName());
field.add(usermeta.item(k).getNodeName());
}
}
unfields.add(field);
}
}
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
//获取所有的字段名
public void AllFields() throws Exception {
//创建DOM文档对象
documentBuilderFactory dFactory = documentBuilderFactory.newInstance();
documentBuilder builder = dFactory.newdocumentBuilder();
document doc;
for(int i=1;i<=db_num;i++) {
ArrayList> t = new ArrayList();
doc = builder.parse(new File("E:\myjavaproject\data\src\xml\"+i+".xml"));
ArrayList db = new ArrayList();
NodeList nl = doc.getElementsByTagName("DBname");
Node classNode=nl.item(0).getFirstChild();
db.add(classNode.getNodevalue());
int count = 1;
for(ArrayList name:unfields) {
ArrayList f = new ArrayList();
nl = doc.getElementsByTagName("table"+count+"_name");
classNode=nl.item(0).getFirstChild();
db.add(classNode.getNodevalue());
count++;
for(int j=1;j getDbTable(){
return db_table;
}
public ArrayList>> getAllFiled() throws Exception{
return allfields;
}
public ArrayList> getUniformField(){
return unfields;
}
public ArrayList> getLists(){
return lists;
}
public static void main(String args[]) throws Exception {
DOMxml doc = new DOMxml();
doc.Num();
doc.CreateWeb();
doc.UniformField();
doc.AllFields();
for(int j=0;j
}
以查询界面为例具体分析中间件的设计,增加、删除、修改功能于此类似,不再赘述。
界面显示当前的数据库,然后由用户选择需要查询哪一个数据库的信息,
并且由用户选择查询成绩的方式,由于用户并不清楚当前可以通过什么方式查询,所以需要通过xml解析当前sc表中的属性有哪些并显示在页面上。
当servlet获得jsp中的数据后,就调用dao层的查询功能函数,并将查询功能函数返回的值传到jsp界面上。Servlet负责查询结果的合并。
//查询功能函数
通过传入的j获得是连接哪一个数据库,然后调用对应的xml中的标签值,从而获得返回的对象。因此,包controller和包dao也即中间件的查询分解合并器。
实验代码
dao:
CourseDao:(用于根据课程号查找课程是否存在)
ScCollction:(用于获得某个数据库中sc表中所有行)
ScDaoImpl(用于根据学号、课程号获得sc的某一行,增加、删除、修改sc中的某一行)
StudentDao(根据sid判断学生是否存在)
包controller:(核心代码)
deletesc(删除)
ScServlet(添加)
updatescore(更新)
showsore(查询)
message(显示两个数据库中的sc)
LoginServlet(登录):
exit(退出登录)



