package week02.litestruts;
import java.io.*;
import java.lang.reflect.*;
import java.util.*;
import javax.xml.parsers.*;
import org.w3c.dom.*;
import org.xml.sax.SAXException;
import week01.datastructure.LinkedList;
import week01.datastructure.List;
/**
* @author Hui Zhou
* @version 1.0 2017-02-28
*/
public class Struts {
public static View runAction(String actionName, Map<String,String> parameters) {
/*
0. 读取配置文件struts.xml
1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象)
据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是
("name"="test" , "password"="1234") ,
那就应该调用 setName和setPassword方法
2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success"
3. 通过反射找到对象的所有getter方法(例如 getMessage),
通过反射来调用, 把值和属性形成一个HashMap , 例如 {"message": "登录成功"} ,
放到View对象的parameters
4. 根据struts.xml中的 <result> 配置,以及execute的返回值, 确定哪一个jsp,
放到View对象的jsp字段中。
*/
//读取配置文件struts.xml
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder;
Document doc = null;
View view = new View(); //实例化View(后面调用view,存储parameters以及jsp,最后return view)
try {
builder = factory.newDocumentBuilder();
File f = new File("src/week02/litestruts/struts.xml");
doc = builder.parse(f);
} catch (ParserConfigurationException|SAXException|IOException e) {
e.printStackTrace();
}
//根据actionName找到相对应的action
Element root = doc.getDocumentElement();
NodeList actionNode = root.getElementsByTagName("action");
Element action = null;
for(int i=0;i<actionNode.getLength();i++){
NamedNodeMap attributes = actionNode.item(i).getAttributes();
for(int j=0;j<attributes.getLength();j++){
Node attribute = attributes.item(j);
String value = attribute.getNodeValue();
if(value.equals(actionName)){
action = (Element) actionNode.item(i);
}
}
}
//根据action找到相对应的class
String actionClass = action.getAttribute("class");
try {
Class<?> cls = Class.forName(actionClass);
Object obj = cls.newInstance();
Method setName = cls.getMethod("setName", String.class);
Method setPassword = cls.getMethod("setPassword", String.class);
setName.invoke(obj, parameters.get("name"));
setPassword.invoke(obj, parameters.get("password"));
//通过反射调用对象的exectue 方法,并获得返回值
Method execute = cls.getMethod("execute");
String exe_val = (String) execute.invoke(obj);
//通过反射找到对象的所有getter方法,通过反射来调用
Method[] met = cls.getDeclaredMethods();
List list = new LinkedList();
for(int i=0;i<met.length;i++){
if(met[i].getName().startsWith("get")){
list.add(met[i]);
}
}
Method[] getter = new Method[list.size()];
for(int i=0;i<list.size();i++){
getter[i] = (Method) list.get(i);
}
//通过反射来调用,把值和属性形成一个HashMap,例如 {"message","login successful"}
Map<String ,String> param = new HashMap<>();
for(int i=0;i<getter.length;i++){
if(getter[i].equals(cls.getMethod("getMessage")))
param.put("message",(String) getter[i].invoke(obj));
}
//放到View对象的parameters
view.setParameters(param);
//根据struts.xml中的 <result> 配置,以及execute的返回值,确定哪一个jsp,放到View对象的jsp字段中
if(exe_val.equals("success"))
view.setJsp("/jsp/homepage.jsp");
else view.setJsp("/jsp/showLogin.jsp");
} catch (ClassNotFoundException|InstantiationException|IllegalAccessException
|NoSuchMethodException|SecurityException|IllegalArgumentException|InvocationTargetException e) {
e.printStackTrace();
}
return view;
}
}