設計模式之委派模式,大名鼎鼎的Spring都在用
- 2020 年 3 月 15 日
- 筆記
什麼是委派模式
雖然說委派模式不屬於Gof23中設計模式,但這並不影響它成為一種經典的設計模式。
「委派」字面意思就是指派一件事情給某人。類比到生活中的場景,比如項目leader指派開發任務給下面的猿猿們。這聽起來有點像靜態代理,不過還是不一樣的,你品,你細品!代理強調的是過程,主要是要在代理過程中加入一些動作的,而委派主要是分配和分發。
代碼實現
我們先新建一個業務處理接口BusinessService
public interface BusinessService { void doService(); }
新建兩個實現類LoginService和OrderService
public class LoginService implements BusinessService{ public void doService() { System.out.println("處理登錄相關業務"); } } public class OrderService implements BusinessService{ public void doService() { System.out.println("訂單業務模塊"); } }
新建一個枚舉類,表示不同的業務類型,這裡假設就兩個,login和order
public enum ServerType { LOGIN,ORDER; }
新建一個業務查找類,主要是用於根據不用的業務類型選擇不同的業務組件提供服務。
public class BussinessLookup { private OrderService orderService; private LoginService loginService; /** * 查找對應的服務 * @param serverType * @return */ public BusinessService getBusinessService(ServerType serverType){ if(serverType.equals(ServerType.LOGIN)){ return loginService; }else{ return orderService; } } public void setOrderService(OrderService orderService) { this.orderService = orderService; } public void setLoginService(LoginService loginService) { this.loginService = loginService; } }
接下來,關鍵的類來了,委派類。做的工作主要是分發。
public class BusinessDelegate { private BussinessLookup bussinessLookup; private BusinessService businessService; private ServerType serverType; public void setBussinessLookup(BussinessLookup bussinessLookup) { this.bussinessLookup = bussinessLookup; } public void setServerType(ServerType serverType) { this.serverType = serverType; } /** * 委派方法,其實最終調用的是業務類的方法 */ public void doTask(){ businessService = bussinessLookup.getBusinessService(serverType); businessService.doService(); } }
我們再來個客戶端類,也就是請求類,它通過委派類完成工作。就是說我不需要知道在幕後到底是哪個業務組件在處理,我只需要給你請求,你幫我完成好任務就OK.。說明白點,委派類就是做了一層封裝和抽象,不將業務處理的大量組件暴露給請求層或者說是視圖層。
public class Client { private BusinessDelegate businessDelegate; public Client(BusinessDelegate businessDelegate) { this.businessDelegate = businessDelegate; } public void doTask(){ businessDelegate.doTask(); } }
好了,我們寫個Main測試一下。
public class AppMain { public static void main(String[] args) { BusinessDelegate businessDelegate = new BusinessDelegate(); BussinessLookup bussinessLookup = new BussinessLookup(); bussinessLookup.setLoginService(new LoginService()); bussinessLookup.setOrderService(new OrderService()); businessDelegate.setBussinessLookup(bussinessLookup); businessDelegate.setServerType(ServerType.LOGIN); Client client = new Client(businessDelegate); client.doTask(); // businessDelegate.setServerType(ServerType.ORDER); // client.doTask(); } }
結果:
處理登錄相關業務
在這裡,非常有必要看下類圖
在Spring源碼中應用
在Spring源碼中我們可以搜索一下,使用delegate關鍵詞模糊查找下,但凡以Delegate結尾的都是委派模式的應用。
比如:BeanDefinitionParserDelegate、ConstructorDelegate、MultipartResolutionDelegate、TypeConverterDelegate等。
當然了,我們熟知的DispatcherServlet 雖然沒帶delegate,但也是委派模式的一種實現。
前端請求都統一走到DispatcherServlet 的doService()方法中,然後在doService()方法中調用doDispatch()方法,在doDispatch()方法中,會獲取業務處理的handler,執行handle()方法處理請求。
doDispatch()方法核心源碼截圖
應用場景
- 當你要實現表現層和業務層之間的松耦合的時候。
- 當你想要編排多個服務之間的調用的時候。
- 當你想要再封裝一層服務查找和調用時候
公眾號:二營長的筆記
免費領資料:公眾號內回復「二營長」