Unlocking Spring’s Design Patterns: From Proxy to Adapter Explained

This article explores how Spring implements classic design patterns—Proxy, Strategy, Decorator, Singleton, Simple Factory, Factory Method, Observer, Template, and Adapter—detailing their purpose, core code snippets, and the way Spring leverages them to provide flexible, extensible, and maintainable backend functionality.

Su San Talks Tech
Su San Talks Tech
Su San Talks Tech
Unlocking Spring’s Design Patterns: From Proxy to Adapter Explained

Preface

A reader asked which design patterns are used in the Spring framework, prompting this comprehensive overview.

Proxy Pattern

Proxy objects share the same interface as the target, allowing clients to interact through the proxy, which can add pre‑ and post‑processing. Spring AOP uses dynamic proxies to generate proxy classes at runtime, inserting interceptors to enhance method behavior.

Strategy Pattern

Spring’s dynamic proxy choice (JDK proxy or CGLIB) is a classic use of the Strategy pattern. The AopProxy interface defines the strategy, with JdkDynamicAopProxy and CglibAopProxy as concrete implementations. The AopProxyFactory (default DefaultAopProxyFactory) creates the appropriate proxy based on runtime conditions.

The factory decides which strategy to apply, with line 10 of the source code containing the conditional logic.

Decorator Pattern

To keep cache writes consistent with database transactions, Spring uses the Decorator pattern. TransactionAwareCacheDecorator implements Cache and delegates operations to the target cache while adding transactional behavior.

Singleton Pattern

Spring beans are singleton by default. The framework implements this via a singleton registry backed by a ConcurrentHashMap:

public class DefaultSingletonBeanRegistry {
    // Thread‑safe container for singleton objects
    private final Map singletonObjects = new ConcurrentHashMap();

    protected Object getSingleton(String beanName) {
        // Retrieve from map
        Object singletonObject = singletonObjects.get(beanName);
        // If absent, create via reflection and store
        if (singletonObject == null) {
            singletonObjects.put(beanName, Class.forName(beanName).newInstance());
        }
        // Return the instance
        return singletonObjects.get(beanName);
    }
}

Simple Factory Pattern

Spring’s BeanFactory exemplifies the Simple Factory pattern, providing a central method getBean that creates beans via reflection:

BeanFactory bf = new ClassPathXmlApplicationContext("spring.xml");
FlyFish flyFishBean = (FlyFish) bf.getBean("flyfishBean");

Factory Method Pattern

Spring’s FactoryBean follows the Factory Method pattern, allowing custom creation logic inside getObject. Implementations such as FlyFishFactoryBean produce FlyFish instances while the container returns the product, not the factory itself.

BeanFactory bf = new ClassPathXmlApplicationContext("spring.xml");
FlyFish flyFishBean = (FlyFish) bf.getBean("flyfishBean");

Observer Pattern

Spring implements the Observer pattern with three components: an Event (message), a Listener (observer), and a Publisher (subject). The framework registers listeners in the ApplicationContext, and event dispatch is handled by ApplicationEventMulticaster, supporting both synchronous and asynchronous delivery.

// Event definition
public class DemoEvent extends ApplicationEvent {
    private String message;
    public DemoEvent(Object source, String message) { super(source); this.message = message; }
    public String getMessage() { return this.message; }
}

// Listener implementation
@Component
public class DemoListener implements ApplicationListener<DemoEvent> {
    @Override
    public void onApplicationEvent(DemoEvent event) {
        System.out.println(event.getMessage());
    }
}

// Publisher usage
@Component
public class DemoPublisher {
    @Autowired private ApplicationContext ctx;
    public void publishEvent(DemoEvent e) { ctx.publishEvent(e); }
}

Template Pattern

The Spring bean creation process follows the Template pattern, allowing users to plug in custom steps (e.g., initialization callbacks) without modifying core framework code.

Adapter Pattern

Spring MVC adapts various controller definitions (annotation‑based, Controller interface, or HttpServlet) to a common handler interface via the Adapter pattern. Different HandlerAdapter implementations (e.g., AnnotationMethodHandlerAdapter, SimpleControllerHandlerAdapter, SimpleServletHandlerAdapter) translate specific controller methods into a uniform handle() call used by DispatcherServlet.

// Annotation‑based controller
@Controller
public class DemoController {
    @RequestMapping("/FlyFish")
    public ModelAndView getEmployeeName() {
        ModelAndView model = new ModelAndView("FlyFish");
        model.addObject("message", "FlyFish");
        return model;
    }
}

// Interface‑based controller
public class DemoController implements Controller {
    @Override
    public ModelAndView handleRequest(HttpServletRequest req, HttpServletResponse resp) throws Exception {
        ModelAndView model = new ModelAndView("FlyFish");
        model.addObject("message", "FlyFish");
        return model;
    }
}

// Servlet‑based controller
public class DemoServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doPost(req, resp);
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.getWriter().write("Hello World.");
    }
}
Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

BackendDesign PatternsJavaaopspringdependency-injection
Su San Talks Tech
Written by

Su San Talks Tech

Su San, former staff at several leading tech companies, is a top creator on Juejin and a premium creator on CSDN, and runs the free coding practice site www.susan.net.cn.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.