委派设计模式概念

  • 什么是委派设计模式

​ 首先委派设计模式,不属于23例设计模式中的,它的基本作用就是负责任务调度和分配任务,跟上篇的代理模式很相似,可以看作是一种特殊情况下的静态代理的全权代理,委派设计模式和代理设计模式的侧重点不同,代理模式注重过程,委派模式注重结果。

  • 举例说明委派模式

​ 比如现在公司需要开发一个项目,要完成这个项目需要产品设计人员、后端人员、前端人员、测试人员等,老板只知道要做哪些工作,但是公司老板不知道每个人具体是负责完成哪个模块的,这个时候,老板就可以找来部门主管,由主管来进行任务分配和调度。

  • 图示说明

image-20210610215103183

代码实现委派模式

1)定义一个boss类,用于boss发送指令

public class Boss {
    /**
     * boss发送指令的方法
     * @param command 发送指令的内容
     * @param leader 引入leader对象
     */
    public void command(String command,Leader leader){
        leader.manage(command);
    }
}

2)定义Leader类,相当于主管,boss调用主管,主管根据指令调配人员

public class Leader {
    //在这个场景下,Leader应该是知道每个员工的职责的,这里先设定一个
    private Map<String,Employee> map = new HashMap<String,Employee>();
    //构造方法初始化
    public Leader(){
        map.put("后端",new JavaEmployee());
        map.put("前端",new WebEmployee());
    }

    /**
     * Leader管理分配任务的方法
     * @param command 根据boss传递过来的指令,再找指定的员工完成
     */
    public void manage(String command){
        map.get(command).doing(command);
    }
}

3)定义员工接口,定义员工做工作的方法

public interface Employee {
    /**
     * 负责的工作
     * @param thing 负责模块名称,比如:后端,前端等
     */
    public void doing(String thing);
}

4)定义JavaEmployee类,实现员工接口

public class JavaEmployee implements Employee{
    /**
     * 负责的工作
     *
     * @param thing 负责模块名称,比如:后端,前端等
     */
    @Override
    public void doing(String thing) {
        System.out.println("我正在使用Java进行开发"+thing);
    }
}

5)定义WebEmployee类,实现员工接口

public class WebEmployee implements Employee{
    /**
     * 负责的工作
     *
     * @param thing 负责模块名称,比如:后端,前端等
     */
    @Override
    public void doing(String thing) {
        System.out.println("我使用vue开发"+thing);
    }
}

6)测试类

public class App {
    public static void main(String[] args) {
        new Boss().command("后端",new Leader());
        new Boss().command("前端",new Leader());
    }
}

7)上述代码测试结果

image-20210610225712739

  • 对上述代码进行解释说明

​ 从委派模式的关系图,以及代码来看,在测试类中,boss实例发送指令内容及传入Leader实例,在Leader类中,通过传入的指令,找到完成这个指令的员工,最后再由对应的员工完成指令的内容。

  • 上述事例的类图

image-20210610231723021

委派模式运用在SpringMVC中

  • 以Delegate结尾或者包含了Dispatcher的一般都是委派,

  • 举例说明

用过基础的Servlet都应该清楚,一个Servlet发送请求并响应,有了委派模式,可以编写一个Servlet,请求到Servlet之后,由这一个Servlet根据请求资源,进行调度对应的Controller相关执行方法,下面简单举例,只是模拟,不是真实的SpringMVC源码

1)编写UserController类,相当于控制层代码

public class UserController {
	//执行查询所有的方法
    public void queryAllUser(){
        System.out.println("查询所有的用户");
    }
}

2)编写OrderController类

public class OrderController {

    public void queryAllOrder(){
        System.out.println("查询所有的订单");
    }
}

3)编写一个接收请求的Servlet,相当于控制器,模拟出根据不同的请求资源,执行响应的controller方法

public class DispatcherServlet extends HttpServlet {
    @Override
    public void service(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {
        todo(req,res);
    }

    public void todo(HttpServletRequest req, HttpServletResponse res){
        //获取请求资源
        String uri = req.getRequestURI();

        //根据uri资源名,执行不同controller方法,这里只是模拟
        if("queryAllUser".equals(uri)){
            //执行用户的controller
            new UserController().queryAllUser();
        }else if("queryAllOrder".equals(uri)){
            new OrderController().queryAllOrder();
        }else{
            throw new RuntimeException("404 "+uri+" not found");
        }
    }
}

4)web.xml响应配置

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <servlet>
        <servlet-name>dispatcherServlet</servlet-name>
        <servlet-class>com.javayyds.mvc.DispatcherServlet</servlet-class>
    </servlet>
    
    <servlet-mapping>
        <servlet-name>dispatcherServlet</servlet-name>
        <url-pattern>/*</url-pattern>
    </servlet-mapping>
</web-app>
  • 说明:

根据web.xml配置,那么请求分别是:http://localhost:8080/queryAllUser和http://localhost:8080/queryAllOrder,在DispatcherServlet类中获取到了请求资源,根据请求资源,可以执行到响应的controller中的代码,那么这样就可以一个Servlet接收请求,进行委派到其他的controller即可。

关注公众号:源码说