Spring - Initial Definitions
This post will introduce the initial concepts used by Spring in every part of the framework. It is the base to have a good experience and a good understanding to make good decisions in your work.
If you don't know nothing about Spring you can see an overview about the Spring Ecosystem here.
Key Principles:
- Don't Repeat Your Self (DRY)
- Separation of Concerns
- Convention Over configuration Testability
The Inversion of Control (IoC) container
The usual flow of control is done by programmer. In other words, the programmer is the responsible for, for example, the flow of creating or binding an object and execute the functions. What the IoC does is delegate this responsibility to other one, then, the container or framework will be responsible for all lifecycle of that object.
The IoC is a principle that allows classes to have low coupling (minimum interdependence). It can be implemented using different patterns as factory, service locator and dependency injection (by constructor, setter or interface).
The Spring Framework implements the IoC by Dependence Injection (DI) which can achieved through the constructor (best practice ) and Setters. The BeanFactory and ApplicationContext are part of Spring Framework's IoC container.
(1) The BeanFactory interface provides an advanced configuration mechanism capable of managing any type of object. (2) ApplicationContext is a sub-interface of BeanFactory. It adds easier integration with Spring's AOP features; message resource handling (for use in internationalization), event publication; and application-layer specific contexts such as the WebApplicationContext for use in web applications. [1]
Benefits of IoC:
- Less code
- Low coupling
- Make the tests and maintenance easier
Configuring the application
ApplicationContext
It is the heart of the SpringApplication. It incapsulate the BeanFactory, responsible for the injection of the beans and which handles all singleton beans. The ApplicationContext provides metadata for bean creation, as well, manage the order of creation. An application can have more then one context, as web containers.
The interface org.springframework.context.ApplicationContext represents the Spring IoC container and is responsible for instantiating, configuring, and assembling the aforementioned beans. The ApplicationContext is the interface for an advanced factory capable of maintaining a registry of different beans and their dependencies. [2] [3]
Spring separates the application's configuration from the application's objects (beans). The context manages the beans.
POM
The dependencies required to use these features are here:
Multiple Configurations
The definition or configuration of the beans is done by Spring in separate classes with @Configuration annotation. The framework allows create more than one configuration class to support the best practices to separates application and infrastructure configs. The SpringApplication will use the config class which import all the configs.
Environment
Other import resource given by framework is the possibility to use properties files to the configuration. Additional properties can be declared using @PropertySource annotation.
Profiles
The profiles are a resource used by containers to have different beans by environment.
PS: Those examples are in Spring documentation
Spring Expression Language (SpEL)
The SpEL is another resource to give support to the configuration. It uses expressions to evolve logic and to return a value.
Component Scanning
The use of the root annotation @Component indicate the class should be loaded into the BeanFactory. The @Component is a generic stereotype. Its specialization are @Repository, @Service, @Controller, @RestController, @Configuration.
The process scan the package and loads configuration for each bean found. So, it goes through @Autowired, @Qualifier, @Value annotation. The scanning happing in the startup.
You can make your class to be autodetected using @ComponentScan(basePackages = "org.example") annotation.
Spring adding those new annotation and you can see the benefits to use them instead the standard annotation here
If you needs adding some behavior at startup or shutdown you can use @PostConstruct and @PreDestroy annotation, which are not specific of the Spring. The sequence of the call is:
Bean
BeanDefinition represents the bean's metadadata and contain a package-qualified class name, bean behavioral configuration elements (scope, lifecycle callbacks, etc.), references to other beans and other configuration settings.
The instantiating of a bean is done by container through configuration metadata. It can be done using the constructor. By default, the instantiation of beans are eagerly.
When you create a bean by the constructor approach, all normal classes are usable by and compatible with Spring.[4]
Constructor inject make the tests esier comparing to do by fields. It is the priority also comparing to the setter option because ensures required dependencies are not null. One example where setter injection should be used insted constructor injection is to avoid circular dependency.
Bean ScopesThe beans can be defined using one of the different bean scopes.
- Singleton: "Scopes a single bean definition to a single object instance for each Spring IoC container."
- Prototype: "Scopes a single bean definition to any number of object instances."
- Request: "Scopes a single bean definition to the lifecycle of a single HTTP request. "
- Session: "Scopes a single bean definition to the lifecycle of an HTTP Session"
- Application: "Scopes a single bean definition to the lifecycle of a ServletContext"
- WebSocket: "Scopes a single bean definition to the lifecycle of a WebSocket"
Understanding the lifecycle helps to define your strategy to develop your application.
Spring Bean container runs through three phases:
- Initialization: creating beans and DI process. It beginnings with creation of ApplicationContext. After that happen the BeanFactory initialization phase (load and process bean definition). Then, it's time of the beans initialization and instantiation, where the beans are really created and managed by the framework.
- Usage: beans are available
- Destruction: beans ready for Garbage Collection.
Spring Pattern
Here is a list of some patterns you can find in the Spring framework.
- Inversion Of Control(IoC) Pattern: It is an architectural pattern and it is the core pattern of the Spring wich one the runtime of the framework is based on. It makes Spring manages the dependencies. The objects are injected in runtime. ApplicationContext is the IoC Container.
- Factory Pattern: IoC container is a factory. BeanFactory is a data factory.
- Builder Patter: A creational pattern used, for example, in MockMvc.
- Singleton and Prototype: Most of the configurations use them. Every bean is a singleton by default. The bean configuration is used as prototype.
- Adapter: Used in Spring Integration to support communication between two different systems.
- Decorator: the framework itself uses decorator. The @Qualifier is a way to use the decorator. It allows add behavior without code modification
- Proxy Patter: involved in every object managed by Spring. Allows add new behaviors to improve the use of the framework. Every bean created gets a proxy. Creating proxies in Spring usually resolves around aspect-oriented programming. It is important when operations should be protected and called only when necessary, or to remove object access
- Repository: It is a pattern introduced by DDD and used by Spring Data.
- Template Pattern: Most used in remote calls. JDBC and REST are the most common scenario.
- MVC: All the Web framework is based on this.
- Observer: One example of use is by ApplicationListener interface to observe if ApplicationContext is changed.
- Command: One example is in AbstractCommandController in MVC.
- Mediator: One example is use this when you need set state of many components at once.
- Interpreter: Used by Spring Expression Language.
Aspect-Oriented Programming in Spring (AOP)
Aspect-oriented Programming (AOP) complements Object-oriented Programming (OOP) by providing another way of thinking about program structure. The key unit of modularity in OOP is the class, whereas in AOP the unit of modularity is the aspect. Aspects enable the modularization of concerns that cut across multiple types and objects.
"(1) Provide declarative enterprise services. (2) Let users implement custom aspects, complementing their use of OOP with AOP"
AOP allows reusable blocks of code inject in runtime.
Common Applications of Aspects | Parts of Spring Aspects |
---|---|
|
|
Summary
Here is a good summary about beans. It is in portugues, but I could not left it behind. They are very good.
O que é um bean Spring Framework | Quando Utilizar @Bean em Spring |
---|---|
Profiles | Cache |
References
- Linkedin - Spring: Framework in Depth
- Linkedin - Spring: Desing Pattern
- Spring Doc: The IoC container
- martinfowler - Inversion of Control Containers and the Dependency Injection pattern
- Edutative: What is Inversion of Control?
- TutorialsTeacher - Inversion of Control
- Spring – Inversion of Control vs Dependency Injection
- Baeldung - Intro to Inversion of Control and Dependency Injection with Spring
- Perfomatix - Inversion of Control(IoC) and Dependency injection(DI) in Java Development Services
- Constructor Dependency Injection in Spring