intentions
Define the skeleton of an algorithm in an operation, defer some steps to subclasses, and Template Method allows subclasses to redefine specific steps of an algorithm without changing the structure of the algorithm
Birth of the template method pattern
The template method pattern provides an important technique for code reuse by defining algorithmic steps and deferring the implementation of those steps to subclasses
In human language:
[Product] : Development brother, can you cook?
[Development] : No, why? Are you gonna make it for me?
[Product] : You think too much, I am ready to teach you to do a fried cabbage ~, with you write code ideas, I also try to write pseudo code
public void cookie(a){
// Step 1: Pour the oil
this.pourOil();
// Step 2: Heat the oil
this.HeatOil();
// Step 3: Pour the cabbage this.pourVegetable(); // Step 4: Add the seasonings this.pourSauce(); // Step 5: Stir fry this.fry(); } Copy the code
[Development] : I understand, little sister, you want to come to my home? I’ll make you a stir-fried garlic paste
[Product] :?? Didn’t you say you couldn’t cook?
[Dev] : You wrote out the steps, I already know, hehe hehe ~
❝
If you have not yet, then let’s look at the core code together ~ if you will, then directly jump to SSO combat ~
❞
HeadFirst core code
“An abstract class“
public abstract class TemplateClass {
/ * * ** Template method, used to control the process of cooking (the process of cooking is the same - reuse)* Can be declared final according to the requirement, preventing subclasses from overwriting this method, resulting in the process execution order* / final void cookProcess(a) { // Step 1: Pour the oil this.pourOil(); // Step 2: Heat the oil this.heatOil(); // Step 3: Pour the vegetables this.pourVegetable(); // Use the hook function to determine if you need to add seasoning if (needSauce()) { this.pourSauce(); } // Step 5: Stir fry this.fry(); } void pourOil(a) { System.out.println("Oil"); } void heatOil(a) { System.out.println("Hot oil"); } / * * ** The parts that need to be changed are defined as abstractions* / abstract void pourVegetable(a); abstract void pourSauce(a); / * * ** Hook functions that affect method call logic* / boolean needSauce(a) { return true; } void fry(a) { System.out.println("Saute and saute and saute until it's cooked."); } } Copy the code
“The subclass implementation“
public class SuanRong extends TemplateClass {
@Override
boolean needSauce(a) {
return false;
} @Override void pourVegetable(a) { System.out.println("The vegetable in the pot is choi Xin."); } @Override void pourSauce(a) { System.out.println("The sauce is minced garlic."); } } Copy the code
Design idea of template method pattern:
- AbstractClass abstracts base classes, defines abstract methods, method invocation order, and so on
- ConcreteClass inherits from an abstract base class to implement predefined methods
In short,
- We need an abstract class or interface (interfaces can also provide concrete methods after Java8) that defines the methods that need to be implemented and the method execution logic
- Inheriting abstract classes or interfaces based on business situations, implementing specific methods, makes multiple situations isolated from each other
- Implement classes that are reasonably built, such as by policy or other means
❝
If this seems a bit ambiguous, I recommend that after reading this article, you visit the Thematic Design Patterns Open source project, which has specific code examples linked at the bottom
❞
The power of templates: 5 minutes per SSO
When it comes to using the template method pattern for SSO, we need to know what SSO is.
SSO
SSO is single sign-on (SSO). In multiple systems, a user only needs to log in once, and each system will know that the user has logged in.
Common user authentication methods
This article mainly focuses on the actual combat of design mode, so simply say a few words, common ways such as:
- The 2.0
- cookie
- .
The first SSO
When we wrote the first SSO, it was a bit of a struggle, thinking about processes, details, and so on
(This refers to our integration with other companies’ authentication systems)
The company I work for has various technical levels and technical stacks, so it is not the standard OAUTH2.0 structure. The following core links are abstractly abstrused, such as:
public interface SSOContextAnalysis {
/** Jump login */
void toLogin(SSOConfig ssoConfig, HttpServletResponse httpServletResponse);
/** Obtain token */ Object getToken(SSOConfig ssoConfig, HttpServletRequest httpServletRequest); / * * ** Get user information * @paramSsoConfig configuration * @returnEncrypted string of user information* / String getUserInfo(SSOConfig ssoConfig, Object arg); / * * ** Parse the SSO context* / String getAccount(SSOConfig ssoConfig, Object userInfo); /** 进行退出 */ boolean tologout(SSOConfig ssoConfig, UserOnline userOnline, HttpServletResponse httpServletResponse); } Copy the code
“By SSO Demo“
public class LongTuSSOHandle implements SSOContextAnalysis{
@Override
public void toLogin(SSOConfig ssoConfig) {
// Skip to the SSO authentication address and set the callback address
} @Override public Object getToken(SSOConfig ssoConfig) { // Obtain Token information based on the encryption algorithm of the customer return null; } @Override public String getUserInfo(SSOConfig ssoConfig, Object arg) { // Assemble packets, initiate user requests, and obtain user data return null; } @Override public String getAccount(SSOConfig ssoConfig, Object userInfo) { // Obtain the user data of the platform based on the user data to complete the SSO process return null; } @Override public boolean tologout(SSOConfig ssoConfig) { // Exit based on the exit address and so on return false; } } Copy the code
When we write business code, we rely entirely on the top-level abstract class, and then we can dynamically change the concrete implementation class
How do I dynamically specify implementation classes
The best ways to dynamically specify an implementation class are as follows:
- Configuration file + Reflection build implementation class
- Configuration file + Preloads all implementation classes, dynamically selected based on configuration
- Database configuration + reflection (you can use the CGLIB agent)
- Database configuration + Pre-loaded all implementation classes, dynamically selected based on configuration
How long will the second SSO take?
When we use the template method mode, the entire SSO process has been combed, the second SSO only need to implement the corresponding interface, and then according to the requirements of the customer to build different encryption protocols, at the same time to change the configuration, anyway, I only spent 5 minutes ~
Follow the design principles
- “Packaging changes“
- In an abstract base class, we can have methods that are already implemented for subclasses to call
- In an abstract base class, method logic that is necessarily different is defined as abstract for subclasses to implement themselves
- “Hollywood principle“
- Don’t look for me, I will look for you to refer to the underlying code (the concrete implementation class) does not depend on the high-level code, we also reflected in this SSO practice, directly depend on the interface, the implementation class is only as the real implementer
What scenarios are suitable for use
- Implement the invariant parts of an algorithm once and leave the mutable behavior to subclasses
- Common behaviors in each subclass should be extracted and grouped into a common parent class to avoid code duplication
- Control subclass extension (hook method mentioned in article, control method execution or not)
Code/ Practical application in life
We use all of the APP, for example, when to pay mostly can choose to pay, pay treasure or WeChat actually pay the whole step, only a specific payment steps is divided into a variety of situations (WeChat, alipay, bank CARDS, etc.), push the rest of the order data reverse is likely to be the same, we can use the template method pattern to constraint behavior, It also reduces duplication of code
PS: This situation may also be handled using policy mode, depending on the situation
The last
“Attach the UML diagram for the template method pattern from the GOF book:“
Related code links
Making the address
- Examples from two classic books, HeadFirst and GOF
- Provides friendly reading instructions