----------------v1.0---------------
1、用户添加
2、用户查询
3、用户修改
4、用户删除
5、用户登录
6、filter解决字符集问题
7、Ajax应用
----------------v1.1---------------
1、分销商树的读取:client_tree.jsp
<%=ClientManager.getInstance().getClientTreeString()%>
2.分步骤的写出树形结构:
第一步:1. 用加号“+”表示非叶子节点,用减号“-”表示叶子节点
/**
* 递归读取分销商树
*
* 1. 用加号“+”表示非叶子节点,用减号“-”表示叶子节点
* @param conn
* @param id
* @param level 控制层次的
*/
private void read(Connection conn, int id, int level) {
level++;
String sql="select * from t_client where pid=?";
PreparedStatement pstmt=null;
ResultSet rs=null;
try {
pstmt=conn.prepareStatement(sql);
pstmt.setInt(1,id );
rs=pstmt.executeQuery();
while(rs.next()){
for(int i=0;i<level-1;i++){
sbTree.append(" ");
}
if("N".equals(rs.getString("is_leaf"))){
sbTree.append("+"+rs.getString("name"))
.append("<br>");
read(conn,rs.getInt("id"),level);
}else{
sbTree.append("-"+rs.getString("name"))
.append("<br>");
}
}
} catch (SQLException e) {
e.printStackTrace();
}finally{
DB.close(rs);
DB.close(conn);
}
}
}
第二步:加上<div>嵌套,将加号“+”,减号“-”改为图片,然后在其后面加上打开或者关闭的文件夹图片,
/**
* 递归读取分销商树
*
* 1.用加号“+”表示非叶子节点,用减号“-”表示叶子节点
* 2.加上<div>嵌套,将加号“+”,减号“-”改为图片,然后在其后面加上打开或者关闭的文件夹图片,
* @param conn
* @param id
* @param level 控制层次的
* @throws SQLException
*/
private void read(Connection conn, int id, int level) throws SQLException {
level++;
String sql="select * from t_client where pid=?";
PreparedStatement pstmt=null;
ResultSet rs=null;
try {
pstmt=conn.prepareStatement(sql);
pstmt.setInt(1,id );
rs=pstmt.executeQuery();
while(rs.next()){
sbTree.append("<div>");
for(int i=0;i<level-1;i++){
sbTree.append("<img src=\"../images/white.gif\" />");
}
if("N".equals(rs.getString("is_leaf"))){
sbTree.append("<img src=\"../images/plus.gif\"/>")
.append("<img src=\" ../images/closedfold.gif\"/>")
.append(rs.getString("name"));
//递归
sbTree.append("<div>");
read(conn,rs.getInt("id"),level);
sbTree.append("</div>");
}else{
sbTree.append("<img src=\"../images/minus.gif\"/>")
.append("<img src=\" ../images/openfold.gif\"/>")
.append(rs.getString("name"));
}
sbTree.append("</div>");
}
} finally{
DB.close(rs);
DB.close(pstmt);
}
}
第三步:在图片"+"和"-"上添加鼠标事件,使树能实现收缩和关闭同时图片也做改变;在图片"打开的文件夹"和"关闭的文件夹"上添加鼠标事件;
/**
* 递归读取分销商树
*
* 1.用加号“+”表示非叶子节点,用减号“-”表示叶子节点
* 2.加上<div>,将加号“+”,减号“-”改为图片,然后在其后面加上打开或者关闭的文件夹图片,
* 3.在图片"+"和"-"上添加鼠标事件,使树能实现收缩和关闭同时图片也做改变;在图片"打开的文件夹"和"关闭的文件夹"上添加鼠标事件;
*
* @param conn
* @param id
* @param level 控制层次的
* @throws SQLException
*/
private void read(Connection conn, int id, int level) throws SQLException {
level++;
String sql="select * from t_client where pid=?";
PreparedStatement pstmt=null;
ResultSet rs=null;
try {
pstmt=conn.prepareStatement(sql);
pstmt.setInt(1,id );
rs=pstmt.executeQuery();
while(rs.next()){
sbTree.append("<div >");
for(int i=0;i<level-1;i++){
sbTree.append("<img src=\"../images/white.gif\" />");
}
if("N".equals(rs.getString("is_leaf"))){
sbTree.append("<img id=\"img"+rs.getInt("id")+"\" src=\"../images/plus.gif\" onClick=\"display("+rs.getInt("id")+");\" />")
.append("<img id=\"im"+rs.getInt("id")+"\" src=\" ../images/closedfold.gif\" onClick=\"display("+rs.getInt("id")+");\" />")
.append(rs.getString("name"));
//递归
sbTree.append("<div style=\"display:none;\" id=\"div"+rs.getInt("id")+"\">");
read(conn,rs.getInt("id"),level);
sbTree.append("</div>");
}else{
sbTree.append("<img src=\"../images/minus.gif\"/>")
.append("<img src=\" ../images/openfold.gif\"/>")
.append(rs.getString("name"));
}
sbTree.append("</div>");
}
} finally{
DB.close(rs);
DB.close(pstmt);
}
}
/第四步:在文字上添加链接,使得在某个地方显示对应的内容
Java代码
/**
* 递归读取分销商树
*
* 1.用加号“+”表示非叶子节点,用减号“-”表示叶子节点
* 2.加上<div>,将加号“+”,减号“-”改为图片,然后在其后面加上打开或者关闭的文件夹图片,
* 3.在图片"+"和"-"上添加鼠标事件,使树能实现收缩和关闭同时图片也做改变;在图片"打开的文件夹"和"关闭的文件夹"上添加鼠标事件;
* 4.在文字上添加链接,使得在某个地方显示对应的内容
*
* @param conn
* @param id
* @param level 控制层次的
* @throws SQLException
*/
private void read(Connection conn, int id, int level) throws SQLException {
level++;
String sql="select * from t_client where pid=?";
PreparedStatement pstmt=null;
ResultSet rs=null;
try {
pstmt=conn.prepareStatement(sql);
pstmt.setInt(1,id );
rs=pstmt.executeQuery();
while(rs.next()){
sbTree.append("<div >");
for(int i=0;i<level-1;i++){
sbTree.append("<img src=\"../images/white.gif\" />");
}
if("N".equals(rs.getString("is_leaf"))){
sbTree.append("<img id=\"img"+rs.getInt("id")+"\" src=\"../images/plus.gif\" onClick=\"display("+rs.getInt("id")+");\" />")
.append("<img id=\"im"+rs.getInt("id")+"\" src=\" ../images/closedfold.gif\" onClick=\"display("+rs.getInt("id")+");\" />")
.append("<a href=\"client_node_crud.html?id="+rs.getInt("id")+"\" target=\"clientDispAreaFrame\">"+rs.getString("name")+"</a>");
//递归
sbTree.append("<div style=\"display:none;\" id=\"div"+rs.getInt("id")+"\">");
read(conn,rs.getInt("id"),level);
sbTree.append("</div>");
}else{
sbTree.append("<img src=\"../images/minus.gif\"/>")
.append("<img src=\" ../images/openfold.gif\"/>");
//叶子节点分2类:一类是分销商,一类是区域
if ("Y".equals(rs.getString("is_client"))) {
sbTree.append("<a href=\"client_crud.html?id=" + rs.getInt("id") + "\" target=\"clientDispAreaFrame\">" + rs.getString("name") + "</a>");
}else {
sbTree.append("<a href=\"client_node_crud.html?id=" + rs.getInt("id") + "\" target=\"clientDispAreaFrame\">" + rs.getString("name") + "</a>");
}
}
sbTree.append("</div>");
}
} finally{
DB.close(rs);
DB.close(pstmt);
}
}
----------------v1.2---------------
1、树节点的查询
----------------v1.3---------------
添加分销商
添加区域
修改区域
删除区域(递归删除)
修改分销商
查看分销商
删除分销商(递归删除)
----遇到unable to load class xxx的错误时候,是jsp编译成的class文件不存在
解决方法:重新启动web服务
----接收的字符串参数如果是为null,则无法进行格式转换:
例:--错 误:
int id = Integer.parseInt(request.getParameter("id"));//如果接收到的字符串为空字符串,则无法进行格式转换
--正确修改:
int id = 0;
if (request.getParameter("id") != null) { //非空判断
id = Integer.parseInt(request.getParameter("id")); //进行格式转换
}
----接收的字符串参数如果是为null,则无法进行equals判断:
例:client_modify.jsp
--错误:
List clientLevelList = DataDictManager.getInstance().getClientLevelList();
for (Iterator iter = clientLevelList.iterator(); iter.hasNext();) {
ClientLevel cl = (ClientLevel)iter.next();
String selectStr = "";
//cl是从数据字典查上来的分销商等级,不为空,但是client.getClientLevel().getId()可能为空,所以应该进行非空判断
if ( cl.getId().equals(client.getClientLevel().getId())) {
selectStr = "selected";
}
}
--正确:
//非空判断client.getClientLevel().getId()!=null
if (client.getClientLevel().getId()!=null && cl.getId().equals(client.getClientLevel().getId())) {
selectStr = "selected";
}
----刷新框架:在删除分销商和区域之后刷新左边树形展示的框架,
即在右边子框架clientDispAreaFrame所包含的页面中写代码,实现刷新左边clientTreeFrame所包含的页面client_tree.jsp
<frameset rows="*" cols="267,*" framespacing="0" frameborder="yes" border="1">
<frame src="client_tree.jsp" name="clientTreeFrame"scrolling="scroll" id="clientTreeFrame" />
<frame src="client_display_area.html" name="clientDispAreaFrame" id="clientDispAreaFrame" />
</frameset>
例如:删除区域页面client_node_crud.jsp,调用删除代码删除节点成功之后调用刷新代码刷新左边的树;
备注:其实刷新的目的,就是重新查询数据库,重新展示这棵树,因为刚才做了删除节点操作
<%
if (command != null && "delete".equals(command)) {
ClientManager.getInstance().deleteTreeNodeById(id);//删除节点代码
//输出刷新树的js
out.print ("<script>");
out.print("parent.clientTreeFrame.location.href='client_tree.jsp'");//刷新
out.print("</script>");
out.print("删除成功!");
}
%>
----定时刷新某个页面,例如每一分钟刷新一个页面:
setTimeout("self.location.reload();",1000);//将代码放到<script type="text/javascript">...</script>块内即可。
----刷新本页:
out.print("<script>window.location.href=window.location.href;</script>")
----刷新父页:
out.print("<script>opener.location.href=opener.location.href;</script>")
----转到指定页:
out.print("<script>window.location.href='yourpage.jsp';</script>")
1. 添加分销商:
client_add.jsp
DataDictManager.java (查分销商等级列表)
ClientIdValidateServlet.java(Ajax验证涉及的servlet)
2、添加区域:client_node_add.jsp
3、修改区域:client_node_modify.jsp
4. 删除区域:client_node_crud.jsp?command=delete&id=<%=id%>
删除区域节点时,得同时删除下面的分销商和区域等子节点;
==具体步骤:
a>.如果是mySQL,则需要将事务的自动提交设置为false ,conn.setAutoCommit(false);
b>.通过当前节点的id得到当前节点对象client,先递归删除子节点,然后删除该节点;
c>.提交设置为false,所以在执行删除节点的sql之后,没有真正删除节点,
--通过client.getPid(),然后得到父节点对象,检查该父亲是否还有孩子(也就是该节是否有兄弟节点);
--如果没有孩子节点,则将父节点的属性is_leaf设置为true;
--如果有孩子节点,则将父节点的属性is_leaf不变,还是false;
d>.事务提交:conn.commit();
/**
* 递归删除树节点
* @param conn
* @param id
* @throws SQLException
*/
private void recursionDeleteTreeNodeById(Connection conn, int id)
throws SQLException {
String sql = "select * from t_client where pid=?";
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
pstmt = conn.prepareStatement(sql);
pstmt.setInt(1, id);
rs = pstmt.executeQuery();
while (rs.next()) {
if ("N".equals(rs.getString("is_leaf"))) {
recursionDeleteTreeNodeById(conn, rs.getInt("id"));
}
//删除子节点
deleteTreeNodeById(conn, rs.getInt("id"));
}
//删除自身
deleteTreeNodeById(conn, id);
}finally {
DB.close(rs);
DB.close(pstmt);
}
}
1.修改分销商:client_modify.jsp
2.查看分销商:client_detail.jsp
3.删除分销商:client_crud.jsp?command=delete&id=<%=id%>
========drp1.4 递归删除子节点================
删除区域节点时,得同时删除下面的分销商和区域等子节点;
==具体步骤:
a>.如果是mySQL,则需要将事务的自动提交设置为false ,conn.setAutoCommit(false);
b>.通过当前节点的id得到当前节点对象client,先递归删除子节点,然后删除该节点;
c>.提交设置为false,所以在执行删除节点的sql之后,没有真正删除节点,
--通过client.getPid(),然后得到父节点对象,检查该父亲是否还有孩子(也就是该节是否有兄弟节点);
--如果没有孩子节点,则将父节点的属性is_leaf设置为true;
--如果有孩子节点,则将父节点的属性is_leaf不变,还是false;
d>.事务提交:conn.commit();
/**
* 递归删除树节点
* @param conn
* @param id
* @throws SQLException
*/
private void recursionDeleteTreeNodeById(Connection conn, int id)
throws SQLException {
String sql = "select * from t_client where pid=?";
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
pstmt = conn.prepareStatement(sql);
pstmt.setInt(1, id);
rs = pstmt.executeQuery();
while (rs.next()) {
if ("N".equals(rs.getString("is_leaf"))) {
recursionDeleteTreeNodeById(conn, rs.getInt("id"));
}
//删除子节点
deleteTreeNodeById(conn, rs.getInt("id"));
}
//删除自身
deleteTreeNodeById(conn, id);
}finally {
DB.close(rs);
DB.close(pstmt);
}
}
----------------v1.5---------------
1、修改密码
a>.输入旧密码,当鼠标离开之后onblur,通过ajax验证输入的旧密码是否正确(其中需要从session中取出当前用户,得到当前用户的密码)
b>.提交输入的新密码
c>.调用业务逻辑方法对当前用户进行密码修改;
d>.移除session中user,
f>.修改User对象,然后再放入session中;
2、会计核算期间维护
----------------v1.6添加物料-------------
1.添加代码
2.添加物料后返回到初始化页面:out.println("<script type=\"text/javascript\">history.go(-2)</script>");
物料维护
步骤:
a.添加dao层:添加com.bjsxt.drp.database.dao 给出dao层接口,然后给出MySQL和Oracle的具体的实现;
b.添加工厂类:com.bjsxt.drp.database.factory.ItemDao4MySqlFactory
和com.bjsxt.drp.database.factory.ItemDao4OracleFactory
分别生产ItemDao4MySqlImpl和ItemDao4OracleImpl
c.添加分页类:PageModel
页面大小,pageSize
当前页号,pageNo
总页数, getTotalPages()
下一页, getNextPageNo()
上一页, getNextPageNo()
首 页, getTopPageNo()
末 页, getBottomPageNo()
d.添加ItemManager.java物料管理
e.添加DataDictManager.java , ItemCategory.java
f.添加AppException.java
----------------v1.7---------------
1、根据id查询物料
当查询框clientIdOrName内输入物料编号或者物料名称后,表单自身提交给自身,
同时接收查询字符串queryStr,再次查询数据库得到相应的PageModel,然后展示页面即可!
--------v1.8-物料分页查询--------
a.添加分页类:PageModel
页面大小,pageSize
当前页号,pageNo
总页数, getTotalPages()
下一页, getNextPageNo()
上一页, getNextPageNo()
首 页, getTopPageNo()
末 页, getBottomPageNo()
b.ItemManager.java物料管理类
--根据条件分页查询:
PageModel pageModel = ItemManager.getInstance().findAllItem(pageNo, pageSize, queryStr);
其中,页面编号pageNo,查询字符串queryStr是变化的,pageSize是可以不变的
--重点查询语句:select a.item_no, a.item_name, a.spec, a.pattern, a.category as category_id,
(select b.name from t_data_dict b where a.category=b.id) as category_name,
a.unit as unit_id, (select c.name from t_data_dict c where a.unit=c.id) as unit_name
from t_items a
order by a.item_no
limit 0,3
----------------v1.9---------------
1、采用动态代理为Dao层加入日志
ItemDao4MySqlFactory.java
LogHandler.java
----------------v2.0文件上传---------------
1、通过<init-param>配置保存上传文件的目录,该目录也是加载图片的目录
<servlet>
<servlet-name>FileUpload</servlet-name>
<servlet-class>com.bjsxt.drp.util.servlet.FileUpload</servlet-class>
<init-param>
<param-name>upload_path</param-name>
<param-value>C:\\workspace\\drp2.7\\WebRoot\\images\\item\</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>FileUpload</servlet-name>
<url-pattern>/servlet/FileUpload</url-pattern>
</servlet-mapping>
2.上传代码,参考: FileUpLoad.java
----------------v2.1---------------
1、物料修改
重点1:选中一条记录之后进行修改,如何用js判断选中了一条记录
function modifyItem() {
var count=0;
var j=0;
for(var i=0;i<document.getElementsByName("selectFlag").length;i++){
if(document.getElementsByName("selectFlag")[i].checked){
j=i; //最后一个被选中复选框的下标
count++; //选中的个数
}
}
if(count==0){
alert("请选择需要修改的物料!");
return ;
}
if(count>1){
alert("一次只能修改一个物料!");
return ;
}
window.self.location = "item_modify.jsp?itemNo=" + document.getElementsByName("selectFlag")[j].value;
}
重点2:
如果有下拉列表,则要有一个默认选中状态;
<td>
<select name="unit" class="select1" id="unit">
<%
for(Iterator unitIter= itemUnitList.iterator();unitIter.hasNext(); ){
ItemUnit iu= (ItemUnit)unitIter.next();
String selected="";
if(iu.getId().equals(item.getUnit().getId() )){
selected="selected";
}
%>
<option value="盒" value="<%=iu.getId() %>" <%=selected%>><!--默认选中-->
<%=iu.getName() %>
</option>
<%} %>
</select>
</td>
2、物料删除
function deleteItem() {
var count=0;
for(var i=0;i<document.getElementsByName("selectFlag").length;i++){
if(document.getElementsByName("selectFlag")[i].checked){
count++;
}
}
if(count<=0){
alert("请选择需要删除的物料!");
return;
}
if(window.confirm("确认删除吗?")){
with(document.getElementById("itemForm")){
action="item_maint.jsp?command=delete&clientIdOrName=<%=queryStr%>"
method="post";
submit();
}
}
}
3、物料详细信息
重点:查询SQL
select a.item_no, a.item_name, a.spec, a.pattern, a.category as category_id,
(select b.name from t_data_dict b where a.category=b.id) as category_name,
a.unit as unit_id,
(select c.name from t_data_dict c where a.unit=c.id) as unit_name
from t_items a
where a.item_no=?
----------------v2.2---------------
1、流向单添加
2、重点:采用JDK动态代理为FlowCardManager接口添加事务管理,
参考:FlowCardManagerFactory.java,TransactionHandler.java
3、流向单查询
4、流向单删除
5、流向单送审
6、流向单明细查询
---------------------------------------------------------------------------------------------------------
采用 ThreadLocal封装Connection(解决线程安全)参见:ConnectionManager.java :
DrpUtil.java
ErrorInfo.java
TransactionHandler.java
1、流向单添加
a.ClientManager.java添加查找所有分销商,返回分页模型PageModel:
--public PageModel findAllClient(int pageNo, int pageSize, String queryStr);
b.用js添加一行表格:flow_card_add.jsp
function addOneLineOnClick() {
var row=tblFlowCardDetail.insertRow(tblFlowCardDetail.rows.length);
var col = row.insertCell(0);
col.innerHTML = "<input readonly=\"true\" maxLength=6 size=6 name=aimId><input type=button value =... name=btnSelectAimClient index=\""+ rowIndex +"\" onclick=\"selectAimClient(this.index)\">";
col = row.insertCell(1);
col.innerHTML = "<tr><input id=aimName name=aimName size=25 maxlength=25 readonly=\"true\">";
col = row.insertCell(2);
col.innerHTML = "<input readonly=\"true\" maxLength=6 size=6 name=itemNo><input type=button value =... name=btnSelectItem index=\""+ rowIndex +"\" onclick=\"selectItem(this.index)\">";
col = row.insertCell(3);
col.innerHTML = "<input id=itemName name=itemName size=25 maxlength=25 readonly=\"true\">";
col = row.insertCell(4);
col.innerHTML = "<input id=spec name=spec size=10 maxlength=10 readonly=\"true\">";
col = row.insertCell(5);
col.innerHTML = "<input id=pattern name=pattern size=10 maxlength=10 readonly=\"true\">";
col = row.insertCell(6);
col.innerHTML = "<input id=unit name=unit size=4 maxlength=4 readonly=\"true\">";
col = row.insertCell(7);
col.innerHTML = "<input id=qty name=qty size=6 maxlength=6>";
col = row.insertCell(8);
col.innerHTML = "<input type='button' value='删除' id=btnDeleteLine name=btnDeleteLine onclick=\"return DeleteRow('row" + rowIndex + "')\"></tr>";
row.setAttribute("id", "row" + rowIndex);
//row.setAttribute("name", "row" + rowIndex);
rowIndex++;
}
--------------------------------------------------------------------------------
//选择需方客户窗口:aim_client_select.jsp
function selectAimClient(index) {
window.open('aim_client_select.jsp?index=' + index, '请选择需方客户', 'width=700, height=400, scrollbars=no');
}
//在子窗口aim_client_select.jsp中选择需方客户后将其添加到父窗口flow_card_add.jsp中
function doubleclick(aimId, aimName) {
var rowLength = window.opener.document.all.tblFlowCardDetail.rows.length
if (rowLength == 2) {
window.opener.document.all.aimId.value = aimId;
window.opener.document.all.aimName.value = aimName;
} else {
window.opener.document.all.aimId[<%=index%>].value = aimId;
window.opener.document.all.aimName[<%=index%>].value = aimName;
}
window.close();
}
-----------------------------------------------------------
//选择物料窗口
function selectItem(index) {
window.open('item_select.jsp?index=' + index, '请选择物料', 'width=700, height=400, scrollbars=no');
}
//在子窗口item_select.jsp中选择一个物料之后将其添加到父窗口flow_card_add.jsp中
function doubleclick(itemNo, itemName, spec, pattern, unit) {
var rowLength = window.opener.document.all.tblFlowCardDetail.rows.length;
if (rowLength == 2) {
window.opener.document.all.itemNo.value = itemNo;
window.opener.document.all.itemName.value = itemName;
window.opener.document.all.spec.value = spec;
window.opener.document.all.pattern.value = pattern;
window.opener.document.all.unit.value = unit;
}else {
window.opener.document.all.itemNo[<%=index%>].value = itemNo;
window.opener.document.all.itemName[<%=index%>].value = itemName;
window.opener.document.all.spec[<%=index%>].value = spec;
window.opener.document.all.pattern[<%=index%>].value = pattern;
window.opener.document.all.unit[<%=index%>].value = unit;
}
window.close();
}
2、DRP采用JDK动态代理为FlowCardManager接口添加事务管理
一个业务逻辑类ManagerImpl的方法A中可能要包含DAO层类DaoImpl中多个的方法B,C,...的调用;
在业务逻辑类ManagerImpl上通过JDK动态代理添加事务,动态代理的职能如下:
a. 假如在指定的add*,delete*,modify*,方法执行前打开连接;
b. 将事务的自动提交设置为false;
c. 业务逻辑方法执行(其中多次调用DAO层的方法B,C,....,)
多次调用DAO层的方法B,C,....,其中得注意2点:
1.我们使用的ConnectionManager.getConnection();得到的是一个放入ThreadLocal的连接,也就是同一线程共同使用的一个连接,
因为在A方法中调用方法B,C...所以B,C得到的数据库连接都是同一个连接
2.Dao方法B,C...的执行只是执行SQL语句,并没有提交事务,也没有关闭连接...以及失败的回滚等,这些操作都由A方法执行完毕后,由动态代理来做;
e. 出错的情况下,让事务回滚;
f. 最后关闭连接;
如果想理解上面的这些话,请这么做:
1.在ConnectionManager.java 的方法public static Connection getConnection() 中的下面一句上设断点
Connection conn = (Connection)connectionHolder.get();
2.启动web服务;
3.点击分销商库存管理中的流向单维护,会执行业务逻辑方法findAllFlowCard,
其中包括2个DAO层方法的调用findAllFlowCard和addFlowCardDetail
4.F6--可一观察到动态代理和业务逻辑方法和dao层方法的执行流程,以及ThreadLocal的Connection的创建次数(就一次)
事务加入请参见:FlowCardManagerFactory.java
/**
* 创建FlowCardManager,动态加入事务
* @return
*/
public FlowCardManager createFlowCardManager() {
FlowCardManager flowCardManager = new FlowCardManagerImpl(this.flowCardDao);
TransactionHandler transactionHandler = new TransactionHandler();//动态加入事务
return (FlowCardManager)transactionHandler.newProxyObject(flowCardManager);
}
3、流向单查询
a.双击子窗口窗口的某一行记录;将子窗口中某条记录的值传递到父窗口;然后关闭子窗口;父窗口显示刚才选择的信息;
//双击单选钮
function doubleclick(clientId, clientName) {
window.opener.document.getElementById("clientId").value = clientId; //给父窗口的元素赋值
window.opener.document.getElementById("clientName").value = clientName; //给父窗口的元素赋值
window.close(); //关闭当前窗口
}
4、流向单删除
5、流向单送审
6、流向单明细查询
----------------v2.4---------------
1、Jfreechart的使用
2、采用Ajax实现html下拉列表联动
----------------v2.5---------------
1、验证码的生成
----------------v2.6---------------
1、采用filter解决session为空
----------------v2.7---------------
1、<context-param> 测试test_context_param.jsp
2、taglib 测试test_tag.jsp
3、Listener
4、tomcat连接池配置 DB.java
5.web.xml配置错误处理:
类型一:自定义异常处理
<error-page>
<exception-type>com.bjsxt.drp.exceptions.AppException</exception-type>
<location>/error.jsp</location>
</error-page>
1.定义异常类AppException.java,通过super(msg);将异常信息传到父类RuntimeException中,
public class AppException extends RuntimeException {
private int errorCode;
public AppException(String msg) {
super(msg);
}
public AppException(int errorCode) {
this.errorCode = errorCode;
}
public int getErrorCode() {
return errorCode;
}
}
2.在使用的地方向上抛出异常
例如:
try {
..............
} catch (SQLException e) {
throw new AppException("删除物料失败");
} finally {
...............
}
3.根据web.xml文件配置,抛出异常com.bjsxt.drp.exceptions.AppException后转向error.jsp页面
4.在错误处理页面error.jsp中通过以下代码得到错误信息
<%=exception.getMessage()%>
(注意:错误页面开头部分要注明是错误页面:<%@ page isErrorPage="true" %> )
类型二:错误码处理
1. <!--如果错误码是404或者500则转向error.jsp页面 ,做相应处理 -->
<error-page>
<error-code>404</error-code>
<location>/http_error.jsp</location>
</error-page>
<error-page>
<error-code>500</error-code>
<location>/http_error.jsp</location>
</error-page>
2.http_error.jsp
<%
//得到错误码request.getAttribute("javax.servlet.error.status_code")
Integer statusCode = (Integer)request.getAttribute("javax.servlet.error.status_code");
if (statusCode.intValue() == 404) {
response.sendRedirect(request.getContextPath() + "/404.html");
}else if (statusCode.intValue() == 500) {
response.sendRedirect(request.getContextPath() + "/500.html");
}
%>
分享到:
相关推荐
**分布式资源规划(DRP)**是企业运营中的一种重要管理工具,主要用于优化供应链管理和生产计划。本资料集“DRP完整版_资料_DRP培训日志”专注于讲解DRP系统的概念、实施方法以及实际应用案例,旨在帮助读者深入理解...
DRP,全称为Distribution Requirements Planning,即分销需求计划,是一种集成的企业管理方法,主要用于协调企业内部和外部资源,以满足客户订单的需求。这个压缩包文件“DRP完整版_资料_DRP_HTML演示版本”可能包含...
分销资源计划(DRP,Distributed Resource Planning)是一种先进的企业管理策略,它整合了供应链上的生产和分销环节,旨在优化库存管理,提高订单满足率,并确保及时配送。DRP项目通常涉及多个方面,包括需求预测、...
《医疗DRP管理系统详解》 在信息技术飞速发展的今天,医疗行业也开始逐步向数字化转型,DRP(Drug Resource Planning)管理系统就是其中的关键一环。本文将深入探讨“医疗DRP管理系统”的核心概念、技术实现以及它...
在本项目“drp.rar_DRP_drp sql”中,我们看到的是一个与营销相关的DRP系统,尽管功能尚未完全开发完毕,但已经足够让我们探讨DRP系统和SQL在实际应用中的关键作用。 首先,让我们深入了解DRP系统。DRP系统是基于...
分销资源计划(DRP,Distributor Resource Planning)是一种先进的企业管理理念和信息技术应用,它主要用于优化分销商或零售商的库存管理、订单处理、物流规划以及销售预测等环节,以提高运营效率,降低运营成本,...
DRP,全称为Distribution Resource Planning,即分销资源计划,是一种集成的企业管理软件系统,主要用于优化企业的分销和物流管理。在企业运营中,DRP能够帮助规划、协调和控制从生产到销售的所有分销活动,包括库存...
"drp-webserver"是一个可能代表分布式资源平台(DRP,Distributed Resource Platform)的Web服务器组件。在IT行业中,Web服务器是用于处理HTTP请求并返回网页内容的软件。DRP通常涉及到系统间的资源管理和协调,它...
【DRP尚学堂培训日志】是一份详细记录DRP(分销资源计划)系统开发过程的日志,旨在分享每日的学习和工作内容。日志中涵盖了从项目开发流程、技术选型到具体业务流程的多个方面。 首先,Web项目开发的一般流程包括...
这是一个基于SSH的DRP系统,已经实现了基础数据管理,分销商库存管理,系统管理等功能,可以直接运行,使用的工具是myeclipse8.5,mySql等,有sql文件,还有关于DRP的ppt,和html模版,需要的朋友可以下载下来参考
DRP(Distribution Requirements Planning)分销管理系统是一种用于优化企业供应链管理的软件系统,它结合了预测、库存管理和订单分配等功能,以提高企业的运营效率和决策能力。在Java技术的支持下,DRP分销管理系统...
IEC 62439-6-2010 drp 分布式环网协议
根据给定的文件信息,以下是对DRP系统关键知识点的详细阐述: ### DRP系统概述 DRP(Distribution Resource Planning)即分销资源计划系统,是一种专门用于管理企业分销网络的软件解决方案,旨在优化企业的订单...
DRP,全称为Distribution Resource Planning,即资源分销管理,是一种集成化的管理信息系统,主要用于规划、组织和控制企业的分销和资源分配活动。在IT领域,尤其是Web开发中,DRP项目通常是一个挑战性的实践任务,...
Xilinx FPGA GTX的DRP的时序配置模块,有如下特性: 1)使用verilog hdl语言编写; 2)对DRP动态可重配置,可读可写; 3)地址数据可根据需求自己更改 4)用户端口与GT*端口分开,互补干扰
DRP项目总结,仅此个人意见。DRP项目总结,仅此个人意见。
分销资源计划(DRP,Distributed Resource Planning)是一种先进的企业管理策略,它整合了销售、库存、生产和运输等关键环节,以优化供应链效率。本模板提供了一个全面的DRP管理系统框架,适用于商业项目,旨在帮助...
DRP(Disaster Recovery Plan)通常指的是灾难恢复计划,它在IT行业中用于确保在系统故障或灾难发生时,能够快速恢复关键业务功能。然而,在这个特定的上下文中,"DRP"似乎指的是一个特定的技术组件或者算法,即...
王勇老师的DRP系统源码解析 在信息技术领域,DRP(Distribution Resource Planning,分销资源计划)系统是一种用于企业管理的软件工具,它整合了企业内部的销售、库存、采购、生产等多个环节,以优化资源分配,提高...
DRP,全称为Distribution Resource Planning,即分销资源计划系统,是一种用于优化企业分销网络的管理工具。在IT行业中,DRP系统通常由专业的软件开发人员使用编程语言如Java来实现,以便为企业提供高效的销售、库存...