1、 實現自定義MVC的體系結構圖java
一、ModelI模式開發Web應用時,分兩種狀況:web
純JSP技術方式開發設計模式
JSP+JavaBean方式開發app
二、ModelI模式開發的不足:框架
JSP頁面中嵌入大量的Java代碼,可讀性差。dom
大量代碼在JSP中難以複用。jsp
後期維護及擴展的難度大。ide
三、爲了克服ModelI模式的缺陷,引入了ModelII的模式開發this
ModelII模式體現了基於MVC(Model-View-Controller,模型-視圖-控制器)的設計模式,簡單的說,ModelII模式就是將數據顯示、流程控制和業務邏輯處理分離,使之相互獨立。url
四、MVC設計模式由3個部分組成各部分的做用。
Model:模型,主要用於數據和業務的處理。
View:視圖,用於數據顯示。
Controller:控制器,用於流程控制。
五、MVC設計模式的特色
一個模型能夠對應多個視圖。
顯示與邏輯控制分離。
分層控制,減低了代碼間的耦合。
2、 咱們如何建立一個本身的MVC框架??
(一)咱們要在lib裏面準備一個夾包
dom4j-1.6.1.jar主要做用:解析xml文件
(二)準備配置文檔(在src下)
<!DOCTYPEmyframework[
<!ELEMENTmyframework(actions)>
<!ELEMENTactions(action*)>
<!ELEMENTaction(result*)>
<!ATTLISTactionnameCDATA#REQUIRED
classCDATA#REQUIRED
>
<!ATTLISTresultnameCDATA#IMPLIED
redirect(true|false)"false"
>
]>
解釋:
解釋:根據上述約束完成的「*」表明該節點能夠出現屢次
<myframework>
<actions>
<actionname="LoginAction"class="cn.action.LoginAction">
<resultname="success">success.jsp</result>
<resultname="login">login.jsp</result>
</action>
</actions>
</myframework>
(三)本身準備一個Action接口,用於放入結果集和執行方法
packagecn.framework;
importjavax.servlet.http.HttpServletRequest;
importjavax.servlet.http.HttpServletResponse;
publicinterfaceAction{
publicfinalStringSUCCESS="success";
publicfinalStringERROR="error";
publicfinalStringLOGIN="login";
publicfinalStringINPUT="input";
publicStringexecute(HttpServletRequestrequest,
HttpServletResponseresponse);
}
(四)定義一個ResultMapping用來存放result節點
packagecn.framework;
publiccla***esultMapping{
//result節點名字
privateStringname;
//是否重定向
privatebooleanredirect;
//跳轉的頁面
privateStringurl;
publicResultMapping(){
}
publicResultMapping(Stringname,booleanredirect,Stringurl){
this.name=name;
this.redirect=redirect;
this.url=url;
}
publicStringgetName(){
returnname;
}
publicvoidsetName(Stringname){
this.name=name;
}
publicbooleanisRedirect(){
returnredirect;
}
publicvoidsetRedirect(booleanredirect){
this.redirect=redirect;
}
publicStringgetUrl(){
returnurl;
}
publicvoidsetUrl(Stringurl){
this.url=url;
}
}
(五)定義一個ActionMapping用來存放Action節點
packagecn.framework;
importjava.util.HashMap;
importjava.util.Map;
publicclassActionMapping{
//Action名稱
privateStringname;
//Action名稱對應的Action的類的全稱
privateStringclassName;
//result集合
privateMap<String,ResultMapping>results=newHashMap<String,ResultMapping>();
publicActionMapping(){
}
publicActionMapping(Stringname,StringclassName,Map<String,ResultMapping>results){
super();
this.name=name;
this.className=className;
this.results=results;
}
publicStringgetName(){
returnname;
}
publicvoidsetName(Stringname){
this.name=name;
}
publicStringgetClassName(){
returnclassName;
}
publicvoidsetClassName(StringclassName){
this.className=className;
}
publicMap<String,ResultMapping>getResults(){
returnresults;
}
publicvoidsetResults(Map<String,ResultMapping>results){
this.results=results;
}
}
(六)準備一個ActionMappingManager是用來管理ActionMapping的
packagecn.framework;
importjava.io.InputStream;
importjava.util.HashMap;
importjava.util.List;
importjava.util.Map;
importorg.dom4j.Attribute;
importorg.dom4j.Document;
importorg.dom4j.Element;
importorg.dom4j.io.SAXReader;
publicclassActionMappingManager{
Map<String,ActionMapping>actionMapping=newHashMap<String,ActionMapping>();
publicActionMappingManager(){
init();
}
publicActionMappinggetActionMapping(StringactionName){
returnactionMapping.get(actionName);
}
publicActionMappingManager(StringfileName){
}
publicMap<String,ActionMapping>getActionMapping(){
returnactionMapping;
}
publicvoidsetActionMapping(Map<String,ActionMapping>actionMapping){
this.actionMapping=actionMapping;
}
publicstaticvoidmain(String[]args){
newActionMappingManager().init();
}
publicvoidinit(){
InputStreamis=this.getClass().getResourceAsStream("/myframework.xml");
SAXReadersr=newSAXReader();
try{
Documentdoc=sr.read(is);
ElementelRoot=doc.getRootElement();
List<Element>listActions=elRoot.elements();
for(ElementelActions:listActions){
List<Element>listAction=elActions.elements();
for(ElementelAction:listAction){
ActionMappingaMapping=newActionMapping();
AttributeattName=elAction.attribute("name");
AttributeattClass=elAction.attribute("class");
aMapping.setName(attName.getValue());
aMapping.setClassName(attClass.getValue());
List<Element>listResult=elAction.elements();
for(ElementelResult:listResult){
ResultMappingrMapping=newResultMapping();
AttributeattResultName=elResult.attribute("name");
AttributeattResultRedirect=elResult.attribute("redirect");
rMapping.setName(attResultName.getValue());
rMapping.setRedirect(Boolean.parseBoolean(attResultRedirect.getValue()));
rMapping.setUrl(elResult.getTextTrim());
aMapping.getResults().put(rMapping.getName(),rMapping);
}
actionMapping.put(aMapping.getName(),aMapping);
}
}
}catch(Exceptione){
e.printStackTrace();
}
}
}
(七)利用反射機制找到本身的實列
packagecn.framework;
publicclassActionManager{
publicstaticActioncreateAction(StringclassName){
Class<?>clz=null;
try{
clz=Thread.currentThread().getContextClassLoader().loadClass(className);
}catch(Exceptionex){
ex.printStackTrace();
}
try{
if(clz==null){
clz=Class.forName(className);
}
}catch(Exceptionex){
ex.printStackTrace();
}
Actionaction=null;
try{
action=(Action)clz.newInstance();
}catch(Exceptionex){
ex.printStackTrace();
}
returnaction;
}
}
(八)寫一個業務邏輯
packagecn.action;
importjavax.servlet.http.HttpServletRequest;
importjavax.servlet.http.HttpServletResponse;
importcn.framework.Action;
publicclassLoginActionimplementsAction{
@Override
publicStringexecute(HttpServletRequestrequest,HttpServletResponseresponse){
return"success";
}
}
(九)核心控制器Servlet
packagecn.framework;
importjava.io.IOException;
importjavax.servlet.ServletConfig;
importjavax.servlet.ServletException;
importjavax.servlet.annotation.WebServlet;
importjavax.servlet.http.HttpServlet;
importjavax.servlet.http.HttpServletRequest;
importjavax.servlet.http.HttpServletResponse;
publicclassMVCServletextendsHttpServlet{
privatestaticfinallongserialVersionUID=1L;
protectedvoiddoGet(HttpServletRequestrequest,HttpServletResponseresponse)
throwsServletException,IOException{
}
ActionMappingManageramanager=null;
@Override
publicvoidinit(ServletConfigconfig)throwsServletException{
amanager=newActionMappingManager();
}
protectedvoiddoPost(HttpServletRequestrequest,HttpServletResponseresponse)
throwsServletException,IOException{
ActionMappingam=amanager.getActionMapping(getActionName(request));
Actionaction=ActionManager.createAction(am.getClassName());
Stringr=action.execute(request,response);
ResultMappingrm=am.getResults().get(r);
if(rm.isRedirect()){
response.sendRedirect(rm.getUrl());
}else{
request.getRequestDispatcher(rm.getUrl()).forward(request,response);
}
}
publicStringgetActionName(HttpServletRequestrequest){
StringactionName=null;
Stringuri=request.getRequestURI();
StringcontentPath=request.getContextPath();
StringactionPath=uri.substring(contentPath.length());
actionName=actionPath.substring(1,actionPath.indexOf(".")).trim();
returnactionName;
}
}
(十)修改web.xml
<servlet>
<servlet-name>MVCServlet</servlet-name>
<servlet-class>cn.framework.MVCServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>MVCServlet</servlet-name>
<url-pattern>*.action</url-pattern>
</servlet-mapping>
(十一)準備一個login.jsp頁面
(十二)發佈到Tomcat運行