架构设计-总控
架构设计的核心是总控,本文参考Struts框架,撰写简单的MVC模型。
先看配置信息,该配置信息描述每个请求所使用的Action及响应的视图。
<requests>
<request path="/default.do" action="org.heroking.web.action.DefaultAction" view="/default.jsp"/>
</requests>
<request path="/default.do" action="org.heroking.web.action.DefaultAction" view="/default.jsp"/>
</requests>
在web.xml中配置总控Servlet配置信息
Code
<servlet>
<servlet-name>default-servlet</servlet-name>
<servlet-class>org.heroking.web.servlet.DefaultServlet</servlet-class>
<init-param>
<param-name>config-file</param-name>
<param-value>/WEB-INF/request.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>default-servlet</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>
<servlet>
<servlet-name>default-servlet</servlet-name>
<servlet-class>org.heroking.web.servlet.DefaultServlet</servlet-class>
<init-param>
<param-name>config-file</param-name>
<param-value>/WEB-INF/request.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>default-servlet</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>
在总控的Servlet的init()函数中,我们要加载该配置文件,代码如下:
Code
@Override
public void init() throws ServletException {
// TODO Auto-generated method stub
super.init();
log.debug("into DefaultServlet init()");
SAXBuilder builder = new SAXBuilder(false);
try {
Document doc = builder.build(this.getServletContext().getRealPath(this.getInitParameter("config-file")));
Element e = doc.getRootElement();
List requestList=e.getChildren("request");
for (Iterator iter = requestList.iterator(); iter.hasNext();) {
Element request = (Element)iter.next();
RequestConfig r = new RequestConfig();
r.setPath(request.getAttributeValue("path"));
r.setAction(request.getAttributeValue("action"));
r.setView(request.getAttributeValue("view"));
if (!requests.containsKey(r.getPath()))
{
requests.put(r.getPath(), r);
}
}
} catch (JDOMException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
}
}
@Override
public void init() throws ServletException {
// TODO Auto-generated method stub
super.init();
log.debug("into DefaultServlet init()");
SAXBuilder builder = new SAXBuilder(false);
try {
Document doc = builder.build(this.getServletContext().getRealPath(this.getInitParameter("config-file")));
Element e = doc.getRootElement();
List requestList=e.getChildren("request");
for (Iterator iter = requestList.iterator(); iter.hasNext();) {
Element request = (Element)iter.next();
RequestConfig r = new RequestConfig();
r.setPath(request.getAttributeValue("path"));
r.setAction(request.getAttributeValue("action"));
r.setView(request.getAttributeValue("view"));
if (!requests.containsKey(r.getPath()))
{
requests.put(r.getPath(), r);
}
}
} catch (JDOMException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
}
}
servlet的请求解析函数如下:
Code
/** *//**
* 请求解析
* @param req
* @param resp
*/
private void execute(HttpServletRequest req, HttpServletResponse resp)
{
if (requests.containsKey(req.getServletPath())) {
try {
RequestConfig rc = requests.get(req.getServletPath());
IAction action = (IAction)Thread.currentThread().getContextClassLoader().loadClass(rc.getAction()).newInstance();
action.execute(req, resp);
RequestDispatcher rd = this.getServletContext().getRequestDispatcher(rc.getView());
rd.forward(req, resp);
return;
} catch (InstantiationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (ServletException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
}
}
}
/** *//**
* 请求解析
* @param req
* @param resp
*/
private void execute(HttpServletRequest req, HttpServletResponse resp)
{
if (requests.containsKey(req.getServletPath())) {
try {
RequestConfig rc = requests.get(req.getServletPath());
IAction action = (IAction)Thread.currentThread().getContextClassLoader().loadClass(rc.getAction()).newInstance();
action.execute(req, resp);
RequestDispatcher rd = this.getServletContext().getRequestDispatcher(rc.getView());
rd.forward(req, resp);
return;
} catch (InstantiationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (ServletException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
log.debug(e.getMessage());
}
}
}
为了便于统一管理,我们定义统一的IAction接口,代码如下:
Code
/** *//**
*
* @author Hero King
*
*/
public interface IAction {
/** *//**
* 执行Action
* @param request
* @param response
*/
void execute(HttpServletRequest request, HttpServletResponse response);
}
/** *//**
*
* @author Hero King
*
*/
public interface IAction {
/** *//**
* 执行Action
* @param request
* @param response
*/
void execute(HttpServletRequest request, HttpServletResponse response);
}