一、前言
在實際開發中,我們經常面臨以下場景:
-
系統支持多種登錄方式(用戶名密碼、管理員登錄、OAuth 登錄、短信登錄等)
-
每種登錄方式的認證邏輯不同
-
我們希望對外提供一個統一的接口調用,而不暴露具體實現
這個時候,工廠設計模式(Factory Pattern)就是解決這種需求的最佳利器。
在本文中,我們通過一個模擬登錄系統的實際案例,帶你深入理解工廠模式的結構、優點和應用場景。
二、什么是工廠模式?
工廠模式是一種創建型設計模式,它通過定義一個用于創建對象的接口,讓子類決定實例化哪一個類。這樣,我們可以將對象的創建與使用解耦,實現更強的擴展性和可維護性。
通俗地說,工廠模式就像點外賣平臺——你只管下單(告訴工廠你想吃什么),工廠幫你創建對應的“菜品實例”,你不需要關心這些菜是怎么做的。
三、代碼結構總覽
我們使用一個模擬登錄系統的例子,分別支持:
-
普通用戶登錄(用戶名 + 密碼)
-
管理員登錄
-
第三方 OAuth 登錄
結構如下:
com.Factory_Pattern
├── LoginService.java // 抽象接口
├── UserLoginService.java // 普通用戶登錄實現
├── AdminLoginService.java // 管理員登錄實現
├── OAuthLoginService.java // OAuth 登錄實現
├── LoginFactory.java // 工廠類
└── Test.java // 測試入口
四、核心代碼詳解
1. 定義統一接口:LoginService
public interface LoginService {boolean login(String username, String credential);
}
所有登錄服務都必須實現這個接口,保證調用方使用統一的方式調用。
2. 三種登錄實現類
public class UserLoginService implements LoginService {@Overridepublic boolean login(String username, String password) {System.out.println("普通用戶登錄驗證中...");return "user".equals(username) && "123".equals(password);}
}
public class AdminLoginService implements LoginService {@Overridepublic boolean login(String username, String password) {System.out.println("管理員登錄驗證中...");return "admin".equals(username) && "adminpass".equals(password);}
}
public class OAuthLoginService implements LoginService {@Overridepublic boolean login(String username, String token) {System.out.println("OAuth 登錄驗證中...");return "oauth_token".equals(token);}
}
每個實現類各自處理自己的登錄邏輯,互不干擾,職責單一。
3. 工廠類 LoginFactory
public class LoginFactory {public static LoginService getLoginService(String userType) {switch (userType.toLowerCase()) {case "user":return new UserLoginService();case "admin":return new AdminLoginService();case "oauth":return new OAuthLoginService();default:throw new IllegalArgumentException("未知用戶類型: " + userType);}}
}
這個工廠類根據 userType
動態創建不同的登錄對象。調用方無需知道這些類的具體細節,只要提供一個標識即可。
4. 客戶端使用(Test 類)
這個客戶端代碼從頭到尾都沒有出現任何具體子類的名字,只跟接口 LoginService
打交道,完美體現了解耦。
public class Test {public static void main(String[] args) {String userType = "oauth";String username = "admin";String token = "oauth_token";LoginService loginService = LoginFactory.getLoginService(userType);boolean success = loginService.login(username, token);System.out.println(success ? "登錄成功!" : "登錄失敗!");}
}
這個客戶端代碼從頭到尾都沒有出現任何具體子類的名字,只跟接口 LoginService
打交道,完美體現了解耦。
五、工廠模式進階建議
在實際項目中,工廠模式可以結合以下設計理念使用:
-
策略模式:工廠只負責創建對象,具體邏輯交給策略執行
-
配置驅動工廠:通過配置文件動態注入類名,支持熱插拔
-
反射 + 注冊表:消除
switch
分支,提升擴展性
如果你想進一步封裝登錄邏輯,可以使用策略 + 工廠模式組合,寫成:
LoginStrategy strategy = LoginStrategyFactory.get(userType);
strategy.authenticate(request);
?完整代碼:
?
package com.Factory_Pattern;import java.util.HashMap;
import java.util.Map;public class Final {public static void main(String[] args) {String userType = "oauth";String username = "admin";String credential = "oauth_token";LoginStrategy strategy = LoginStrategyFactory.getStrategy(userType);boolean success = strategy.login(username, credential);System.out.println(success ? "? 登錄成功!" : "? 登錄失敗!");}
}interface LoginStrategy {boolean login(String username, String credential);
}class UserLoginStrategy implements LoginStrategy {@Overridepublic boolean login(String username, String password) {System.out.println("【普通用戶】登錄驗證...");return "user".equals(username) && "123".equals(password);}
}class AdminLoginStrategy implements LoginStrategy {@Overridepublic boolean login(String username, String password) {System.out.println("【管理員】登錄驗證...");return "admin".equals(username) && "adminpass".equals(password);}
}class OAuthLoginStrategy implements LoginStrategy {@Overridepublic boolean login(String username, String token) {System.out.println("【OAuth】登錄驗證...");return "oauth_token".equals(token);}
}class LoginStrategyFactory {private static final Map<String, LoginStrategy> STRATEGY_MAP = new HashMap<>();static {STRATEGY_MAP.put("user", new UserLoginStrategy());STRATEGY_MAP.put("admin", new AdminLoginStrategy());STRATEGY_MAP.put("oauth", new OAuthLoginStrategy());}public static LoginStrategy getStrategy(String userType) {LoginStrategy strategy = STRATEGY_MAP.get(userType.toLowerCase());if (strategy == null) {throw new IllegalArgumentException("未知用戶類型: " + userType);}return strategy;}
}
六、結語
工廠模式作為 Java 最常用的設計模式之一,真正的精髓在于解耦與擴展性。尤其在業務不斷演進、需求不斷變化的環境中,工廠模式提供了一種優雅的應對方式。學會了工廠模式,你將能更從容地面對對象創建、邏輯分發和模塊擴展等挑戰。如果你覺得本文對你有幫助,歡迎點贊、評論和分享,讓更多人了解并掌握設計模式的魅力!