mvc框架与增强

MVC全名是Model View Controller,是模型(model)-视图(view)-控制器(controller)的缩写,一种软件设计典范,用一种业务逻辑、数据、界面显示分离的方法组织代码,将业务逻辑聚集到一个部件里面,在改进和个性化定制界面及用户交互的同时,不需要重新编写业务逻辑。

编程模式

Model(模型)表示应用程序核心(比如数据库记录列表)

是应用程序中用于处理应用程序数据逻辑的部分,通常模型对象负责在数据库中cun存取数据。

View(视图)显示数据(数据库记录)

是应用程序中处理数据显示的部分,通常视图是依据模型数据创建的。

Controller(控制器)处理输入(写入数据库记录)

是应用程序中处理用户交互的部分,通常控制器负责从视图读取数据,控制用户输入,并向模型发送数据

自定义mvc工作原理图

自定义mvc原理实现

其中要用到xml的建模代码,请参考:

https://www.cnblogs.com/huxiaocong/p/11015593.html

定义子控制器接口Action 

用来直接处理浏览器发送过来的请求

package com.framework;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
 * 子控制器
 * @author 旧城
 *
 */
public interface Action {

    String execute(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException;
}

创建实体类:

package com.entity;

public class Cal {

    private String num1;
    private String num2;

    public String getNum1() {
        return num1;
    }

    public void setNum1(String num1) {
        this.num1 = num1;
    }

    public String getNum2() {
        return num2;
    }

    public void setNum2(String num2) {
        this.num2 = num2;
    }

    public Cal(String num1, String num2) {
        super();
        this.num1 = num1;
        this.num2 = num2;
    }

    public Cal() {
        super();
        // TODO Auto-generated constructor stub
    }

}

创建子控制器AddCalAction(加法):

package com.web;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.framework.Action;

public class AddCalAction implements Action{

    @Override
    public String execute(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        String num1=req.getParameter("num1");
        String num2=req.getParameter("num2");
        req.setAttribute("res", Integer.valueOf(num1)+Integer.valueOf(num2));
        req.getRequestDispatcher("calRes.jsp").forward(req, resp);
        return null;
    }

}

减乘除只需把Integer.valueOf(num1)+Integer.valueOf(num2)中的+改为—,*, / ,即可

创建中央控制器DispatchrServlet

接收请求,通过请求寻找对应的子控制器

package com.framework;

import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.web.AddCalAction;
import com.web.DelCalAction;
/**
 * 主控制器
 *     专门用来处理业务逻辑
 * @author 旧城
 *
 */
public class DispatcherServlet extends HttpServlet{

    
    private static final long serialVersionUID = 723689920988912828L;
//    private Map<String, Action> actionMap=new HashMap<>();
    private ConfigModel configModel=null;
    
    public void init() {
//        actionMap.put("/addCal", new AddCalAction());
//        actionMap.put("/delCal", new DelCalAction());
        try {
            configModel=ConfigModelFactory.build();
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    
    
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // TODO Auto-generated method stub
        doPost(req, resp);
    }
    
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

        init();
        String url=req.getRequestURI();
        
        url=url.substring(url.lastIndexOf("/"), url.lastIndexOf("."));
        ActionModel actionModel=configModel.pop(url);
        if(configModel==null) {
            throw new RuntimeException("你没有配置action标签");
        }
        try {
            Action action=(Action)Class.forName(actionModel.getType()).newInstance();
            action.execute(req, resp);
            
            
            
        } catch (InstantiationException | IllegalAccessException | ClassNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        
    }
}

 

xml文件如下:

<?xml version="1.0" encoding="UTF-8"?>
    
<config>
    
    <action path="/delCal" type="com.web.DelCalAction">
        <forward name="calRes" path="/calRes.jsp" redirect="false" />
    </action>
    
    <action path="/addCal" type="com.web.AddCalAction">
        <forward name="calRes" path="/calRes.jsp" redirect="false" />
    </action>
</config>

WEB-INF文件夹下的xml配置如下:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" id="WebApp_ID" version="2.5">
  <display-name>mvc_01</display-name>
 <servlet>
   <servlet-name>dispatcherServlet</servlet-name>
   <servlet-class>com.framework.DispatcherServlet</servlet-class>
 </servlet>
 <servlet-mapping>
   <servlet-name>dispatcherServlet</servlet-name>
   <url-pattern>*.action</url-pattern>
 </servlet-mapping>
</web-app>

 

创建jsp页面

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
<script type="text/javascript">
    function doSub(val) {
        if(val==1){
            calForm.action="${pageContext.request.contextPath }/addCal.action";
        }else if(val==2){
            calForm.action="${pageContext.request.contextPath }/delCal.action";
        }
        calForm.subimt();
    }

</script>
</head>
<body>

    <form id="calForm" action="${pageContext.request.contextPath }/addCal.action">
        num1:<input type="text" name="num1" /><br>
        num2:<input type="text" name="num2" /><br>
        <button onclick="doSub(1)">+</button>
        <button onclick="doSub(2)">-</button>
        <button onclick="doSub(3)">*</button>
        <button onclick="doSub(4)">/</button>
    </form>
</body>
</html>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
结果: ${res }
</body>
</html>

运行结果:

相加:

通过XML对自定义mvc框架进行增强

中央控制器:

package com.framework;

import java.io.IOException;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.beanutils.BeanUtils;

import com.qukang.web.Addction;
import com.qukang.web.Exceptaction;
import com.qukang.web.Minusction;
import com.qukang.web.Multiplication;
import com.sun.org.apache.xpath.internal.operations.Mult;
/**
 * 中央控制器
 * 作用:接受请求,通过请求的对应的子控制器
 * @author VULCAN
 *
 */
public class DispatcherServlet extends HttpServlet {


    private static final long serialVersionUID = 5304895244625871732L;
//    在configModel对象中包含了所有的子控制器
    private ConfigModel configModel;
//    一个子控制器的集合
    private Map<String,Action> actionMap=new HashMap<>();
//    每次访问Servlet执行
    public void init(){
//        actionMap.put("/addCal",new Addction());
//        actionMap.put("/delCal",new Minusction());
//        actionMap.put("/mluCal",new Multiplication());
//        actionMap.put("/excCal",new Exceptaction());
        
        try {
             String xmlPath=this.getInitParameter("xmlPath");
            if(xmlPath==null ||"".equals(xmlPath)) {
                configModel=ConfigModelFactory.newInstance();
            }else {
                configModel=ConfigModelFactory.newInstance(xmlPath);
            }
        } catch (Exception e) {
            // TODO: handle exception
            e.printStackTrace();
        }
    }
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // TODO Auto-generated method stub
        doPost(req, resp);
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // TODO Auto-generated method stub
        init();
        String url=req.getRequestURI();
        url=url.substring(url.lastIndexOf("/"),url.lastIndexOf("."));
//        Action action=actionMap.get(url);
//        action.execute(req, resp);
        ActionModel actionModel = configModel.get(url);
//        可能没有配置子控制器  所有我们需要抛一下子异常
        if(actionModel ==null ) {
            throw new RuntimeException("你没有配置action标签,找不到对应的子控制器");
        }
        try {
            String type=actionModel.getType();
            Action action=(Action)Class.forName(type).newInstance();
            if(action instanceof ModelDrivern) {
                ModelDrivern drivern=(ModelDrivern)action;
                Object model = drivern.getModel();

//                将jsp传过来的参数封装到实体类中的原理原理  
//                代码体现  源码
//                此时的model的所有属性值都是null  
//                我们可以将req.getParameterMap()的值通过反射将其塞进model实例中
//                Map<String, String[]> parameterMap = req.getParameterMap();
//                Set<Entry<String, String[]>> entrySet = parameterMap.entrySet();
//                Class<? extends Object> clz = model.getClass();
//                for (Entry<String, String[]> entry : entrySet) {
//                    Field field = clz.getField(entry.getKey());
//                    field.setAccessible(true);
//                    field.set(model, entry.getValue());
//                }

//                前任种树,后人乘凉  
                BeanUtils.populate(model, req.getParameterMap());
//                大大的减轻了代码量
            }
            String execute = action.execute(req, resp);
            
            ForwardModel forwardModel = actionModel.get(execute);
            if(forwardModel!=null) {
                String jspPath=forwardModel.getPath();
                if("false".equals(forwardModel.getRedirect())) {
                    req.getRequestDispatcher(jspPath).forward(req, resp);
                }else {
                    resp.sendRedirect(req.getContextPath()+jspPath);
                }
            }
        } catch (Exception e) {
            // TODO: handle exception
            e.printStackTrace();
        }
    }
}
模型驱动接口
package com.qukang.framework;
/**
 * 模型驱动接口
 *  作用是将jsp所有传递过来的参数都自动封装到浏览器所要操作的实体类型中
 * @author VULCAN
 *
 */
public interface ModelDrivern<T> {
    T getModel();
}

增强版的子控制器

package com.qukang.framework;

import java.lang.reflect.Method;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
 * 增强版的子控制器
 *     原来的子控制器只能处理一个用户的请求,有时候用户的请求时多个 ,但是都是操作同一张表,那么原有的子控制的代码编写繁琐
 *  增强版的作用就是将
 *  将一组的相关的操作放到一个Action中
 * @author VULCAN
 *
 */
public class ActionSupport implements Action {

    @Override
    public final String execute(HttpServletRequest req, HttpServletResponse resp) {
        String methodName=req.getParameter("methodName");
        String code ="";
        try {
            Method m=this.getClass().getDeclaredMethod(methodName, HttpServletRequest.class,HttpServletResponse.class);
            code =(String) m.invoke(this,req,resp);
        } catch (Exception e) {
            // TODO: handle exception
            e.printStackTrace();
        } finally {
        }
        return code;
    }

}

处理增强版子控制器传来的所有请求:

package com.qukang.web;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.qukang.entity.Cal;
import com.qukang.framework.ActionSupport;
import com.qukang.framework.ModelDrivern;
import com.sun.accessibility.internal.resources.accessibility;

public class CalAction extends ActionSupport implements ModelDrivern<Cal> {
    private Cal cal=new Cal();
    public String add(HttpServletRequest req, HttpServletResponse resp){
//        String num1=req.getParameter("num1");
//        String num2=req.getParameter("num2");
//        Cal cal=new Cal(Integer.valueOf(num1),Integer.valueOf(num2));
        req.setAttribute("sum",cal.getNum1()+cal.getNum2());
        return "rs";
    }
    public String min(HttpServletRequest req, HttpServletResponse resp){
//        String num1=req.getParameter("num1");
//        String num2=req.getParameter("num2");
//        Cal cal=new Cal(Integer.valueOf(num1),Integer.valueOf(num2));
        req.setAttribute("sum",cal.getNum1()-cal.getNum2());
        return "rs";
    }
    public String multip(HttpServletRequest req, HttpServletResponse resp){
//        String num1=req.getParameter("num1");
//        String num2=req.getParameter("num2");
//        Cal cal=new Cal(Integer.valueOf(num1),Integer.valueOf(num2));
        req.setAttribute("sum",cal.getNum1()*cal.getNum2());
        return "rs";
    }
    public String excep(HttpServletRequest req, HttpServletResponse resp){
//        String num1=req.getParameter("num1");
//        String num2=req.getParameter("num2");
//        Cal cal=new Cal(Integer.valueOf(num1),Integer.valueOf(num2));
        req.setAttribute("sum",cal.getNum1()/cal.getNum2());
        return "rs";
    }
    @Override
    public Cal getModel() {
        // TODO Auto-generated method stub
        return cal;
    }
}

xml配置:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <display-name>T226_mvc</display-name>
  <servlet>
      <servlet-name>dispatcherServlet</servlet-name>
      <servlet-class>com.qukang.framework.DispatcherServlet</servlet-class>
     <init-param>
         <param-name>xmlPath</param-name>
         <param-value>/mvc3.xml</param-value>
     </init-param>
  </servlet>
  <servlet-mapping>
      <servlet-name>dispatcherServlet</servlet-name>
      <url-pattern>*.action</url-pattern>
  </servlet-mapping>

 jsp 页面代码:

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
<script type="text/javascript">
function doSub(num){
    if(num == 1){
        calForm.action="${pageContext.request.contextPath}/Cal.action?menthodName=add";
    }
    else if(num==2){
        calForm.action="${pageContext.request.contextPath}/Cal.action?menthodName=minus";
    }
    else if(num==3){
        calForm.action="${pageContext.request.contextPath}/Cal.action?menthodName=multiply";
    }
    else if(num==4){
        calForm.action="${pageContext.request.contextPath}/Cal.action?menthodName=divided";
    }
    calForm.submit();
}

</script>
</head>
<body>
<form name="calForm" method="post" action="">
num1:<input type="text" name="num1" ><br>
num2:<input type="text" name="num2" ><br>
<button onclick="doSub(1)">+</button>
<button onclick="doSub(2)">-</button>
<button onclick="doSub(3)">*</button>
<button onclick="doSub(4)">/</button>
</form>
</body>
</html>

运行结果:

相加:

 

转载于:https://www.cnblogs.com/huxiaocong/p/11087107.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值