JAVAWEB框架学习文章索引点这里
项目流程:
模拟struts2,首先自己写个struts.xml,然后解析这个文档将得到的内容封装到javabean中,这里使用了两个javabean,一个是用来装action节点的MyActionNode,一个是用来装result节点的MyResultNode。然后针对于自己写xml中的class路径,自己写对应的action类,和对应的方法。最后写过滤器过滤*.action,获取到访问的ServletPath,拿去于MyActionNode中的路径进行匹配,匹配成功后取出这个javabean中的class路径和方法名,然后通过反射实例化对象并调用该方法。拿到方法执行结束返回的字符串result,在拿到MyResultNode中匹配result,匹配成功后拿到要跳转的路径,在后在过滤器中转发到该路径。
注意事项:
1,会用到dom4j.jar和jaxen-1.1-beta-6.jar
2,struts.xml放到src路径下,如果放到别的地方,在读配置文件的地方需要改路径
3,过滤器注解可以填 /*、*.action等内容,但是不可以/*.action,这样找不到资源,甚至可能导致tomcat启动失败
action类:
package com.mini;
public class MiniAction {
public String execute() {
System.out.println("正在执行execute()");
return "success";
}
}
配置文件
<?xml version="1.0" encoding="UTF-8"?>
<struts>
<action name="MiniAction" class="com.mini.MiniAction" method="execute">
<result name="success">/mini.jsp</result>
</action>
</struts>
action和result节点的javabean对象
package com.bean;
import java.util.*;
public class MyActionNode {
private String name;
private String className;
private String method;
private Map<String,MyResultNode> resultMap;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getClassName() {
return className;
}
public void setClassName(String className) {
this.className = className;
}
public String getMethod() {
return method;
}
public void setMethod(String method) {
this.method = method;
}
public Map<String, MyResultNode> getResultMap() {
return resultMap;
}
public void setResultMap(Map<String, MyResultNode> resultMap) {
this.resultMap = resultMap;
}
@Override
public String toString() {
return "MyActionNode [name=" + name + ", className=" + className + ", method=" + method + ", resultMap="
+ resultMap + "]";
}
}
package com.bean;
public class MyResultNode {
private String name;
private String target;
public MyResultNode() {
super();
}
public MyResultNode(String name, String target) {
super();
this.name = name;
this.target = target;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getTarget() {
return target;
}
public void setTarget(String target) {
this.target = target;
}
@Override
public String toString() {
return "MyResultNode [name=" + name + ", target=" + target + "]";
}
}
XML解析类:
package com.mini;
import static org.junit.Assert.*;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import org.dom4j.*;
import org.dom4j.io.SAXReader;
import org.junit.Test;
import com.bean.MyActionNode;
import com.bean.MyResultNode;
public class XMLConfig{
public static Map<String, MyActionNode> getMyActionNodes() throws DocumentException{
Map<String, MyActionNode> map = new HashMap<>();//key是action节点的name,value是action节点
//创建解析器
SAXReader reader = new SAXReader();
//加载xml文件
InputStream in = XMLConfig.class.getResourceAsStream("/ministruts.xml");
Document doc = reader.read(in);
//获取xml中的action元素
List<Node> actions = doc.selectNodes("//action");
for (Node acion : actions) {
//将action节点的内容装到javabean中
MyActionNode an = new MyActionNode();
an.setName(acion.valueOf("@name"));
an.setClassName(acion.valueOf("@class"));
an.setMethod(acion.valueOf("@method"));
//获取result元素
List<Node> results = acion.selectNodes("//result");
Map<String, MyResultNode> mapp = new HashMap<>();//key是rusult节点的name,value是rusult节点
for (Node result : results) {
//将result节点的内容装到javabean中
String name = result.valueOf("@name");
String text = result.getText();
MyResultNode rn = new MyResultNode(name,text);
mapp.put(name, rn);
}
an.setResultMap(mapp);
map.put(an.getName(), an);
}
return map;
}
@Test
public void test() throws Exception {
Map<String, MyActionNode> map = getMyActionNodes();
Set<Entry<String, MyActionNode>> entrySet = map.entrySet();
for (Entry<String, MyActionNode> entry : entrySet) {
System.out.println(entry.getKey()+".."+entry.getValue().toString());
}
}
}
过滤器:
package com.filter;
import java.io.IOException;
import java.lang.reflect.Method;
import java.util.Map;
import java.util.Set;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.dom4j.DocumentException;
import com.bean.MyActionNode;
import com.bean.MyResultNode;
import com.mini.XMLConfig;
@WebFilter("*.action")
public class MiniFilter implements Filter {
public void init(FilterConfig fConfig) throws ServletException {
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
System.out.println("拦截");
try {
//拿到请求的名字
HttpServletRequest req = (HttpServletRequest)request;
HttpServletResponse resp = (HttpServletResponse)response;
String path = req.getServletPath();//MiniAction.action
String actionName = path.substring(1, path.indexOf("."));//MiniAction
//获取配置文件信息
Map<String, MyActionNode> acMap = XMLConfig.getMyActionNodes();
//匹配访问路径和配置路径
for (String xmlActionName : acMap.keySet()) {
if(xmlActionName.equals(actionName)) {
//获取对应的action的bean对象
MyActionNode actionNode = acMap.get(xmlActionName);
//获取action的class对象
String className = actionNode.getClassName();
Class miniAcClass = Class.forName(className);
//反射生成action实例
Object miniAc = miniAcClass.newInstance();
//获取method,并调用方法获取返回值
Method method = miniAcClass.getMethod(actionNode.getMethod());
String result = (String)method.invoke(miniAc);
//System.out.println(actionName);
//将方法返回值拿到xml中result进行对比
Map<String, MyResultNode> resultMap = actionNode.getResultMap();
for (String xmlResult : resultMap.keySet()) {
if(xmlResult.equals(result)) {
//匹配成功则获取需要跳转的路径
MyResultNode resultNode = resultMap.get(xmlResult);
String target = resultNode.getTarget();
//转发路径
System.out.println(target);
req.getRequestDispatcher(target).forward(req, resp);
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
//chain.doFilter(request, response);
}
public void destroy() {
}
}
jsp:
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
mini.jsp
</body>
</html>
执行效果:
打开浏览器输入:http://localhost:8080/StrutsDemo/MiniAction.action
控制台输出内容:
拦截
正在执行execute()
/mini.jsp
页面效果:
显示出mini.jsp