Article directory
1. Store Bean objects
When we store beans before, we need to add bean registration in spring-config.xml, which is not easy. The core for us to store and read objects more easily is to use annotations
1. Use class annotations (five major types of annotations):
@Controller: Controller, verify the correctness of data requested by users (security system)
@Service: Service layer, arrange and schedule specific execution methods (customer service center)
@Repository: Persistence layer , to interact with the database, equivalent to DAO (Data Access Object) data access layer
@Component: component (tool class)
@Configuration: configuration item (some configuration in the configuration project)
2. Method annotation:
@Bean path
configuration scan
In order to successfully store objects in Spring, items need to configure the scanning package path for storing objects. Only all classes under the configured package can be correctly identified and saved in Spring with annotations added. It needs to be in the spring- config.xnl adds the following configuration:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:content="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<content:component-scan base-package="com.zd.demo"></content:component-scan>
</beans>
This step is very important. If the class object under the configuration scanning package is not configured, it cannot be stored in Spring even if it is annotated.
Add annotations to store Bean objects
The code to store beans using @Controller looks like this:
@Controller //将对象存储到Spring中
public class StudentController {
public void hello() {
System.out.println("hello Im student");
}
}
Read the StudentController object
public static void main(String[] args) {
//得到Spring上下文
ApplicationContext context = new ClassPathXmlApplicationContext("spring-config.xml");
//得到bean
StudentController studentController =
context.getBean("studentController",StudentController.class);
//调用bean方法
studentController.hello();
}
The code to store a bean using @Service looks like this:
@Service
public class StudentService {
public void hello() {
System.out.println("hello Im studentService");
}
}
Get the Bean object:
public static void main(String[] args) {
//得到Spring上下文
ApplicationContext context = new ClassPathXmlApplicationContext("spring-config.xml");
//得到bean
StudentService studentService =
context.getBean("studentService",StudentService.class);
//调用bean方法
studentService.hello();
}
The usage methods of several other class annotations are consistent, so I won’t demonstrate them one by one here.
Annotation use range
1. Can it be used together with component-scan?
We can find that it can be used together
2. Can the five categories of annotations be removed from the component-scan package?
No
3. Can the classes under component-scan be stored in Spring without annotations of the five major categories?
Can't
4. As long as the classes under all subpackages under componentmt-scan are annotated with the five major categories, can they be stored in Spring?
The classes under the subpackage can also be stored in Spring as long as they are annotated with five categories
Bean naming
When we get the Bean object, when passing in the name, there are generally two situations:
By default: the Bean object can be read by using the lowercase first letter of the original class name
Special case: if the original class name has the first letter and the second letter If the letters are all uppercase, then use the original class name to obtain
The relationship between the five categories of annotations
It can be considered that @Controller / @Service / @Repository /@Configuration are all "subclasses" of @Component, and they are all extensions for @Component
Why are five categories of annotations needed?
We can find that as long as we add annotations to the class, we can get the Bean object. Why do we need so many class annotations?
In order to let the programmer know the function of the current class at a glance after seeing the annotation
JavaEE standard layering:
1. Control layer (Controller)
2. Service layer (Service)
3. Data persistence layer (Dao)
2. Method annotation @Bean
Five categories of annotations are added to a class, while method annotations are placed on methods
We first prepare an entity class, and then use the method annotation @Bean to store the object in the Spring container
public class UserBeans {
@Bean
public static User getUser() {
User user = new User();
user.setUid(1);
user.setUsername("张三");
user.setPassword("123456");
return user;
}
}
Then get the object from the Spring container
public static void main(String[] args) {
ApplicationContext context =
new ClassPathXmlApplicationContext("spring-config.xml");
User user = context.getBean("user",User.class);
System.out.println(user);
}
We found that an error was reported when using it. There is no Bean object named user. There are two reasons for this phenomenon:
1. @Bean naming rules are different from the naming rules of the five major types of annotations. @Bean naming rules, the default @Bean stored object name == method name
2. The @Bean annotation must be used together with the five major types of annotations (the provisions made by Spring to improve performance).
Now the Bean object can be obtained normally.
Bean renaming
It is too abstract for us to obtain the Bean object through the method name above. We can rename the Bean object by setting the name attribute, as follows:
We give the Bean a user name
We can find that it can be obtained through this duplicate name.
Our renaming here can have multiple names, because our Spring container allows objects of the same type to be stored in multiple copies of the container
When @Bean uses renaming, can the object be obtained by using the method name?
No, when the @Bean object is renamed, the default method of obtaining the method name cannot be used
3. Object injection
Obtaining a Bean object is also called object assembly, which is to take the object out and put it in a certain class, sometimes called object injection.
There are three ways to implement object injection:
1. Attribute injection
2. Setter injection
3. Construction method injection
attribute injection
Property injection is achieved using the @AutoWired annotation
@Component
public class Group {
@Autowired
private User user;
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
}
In this way, attribute injection can be realized, althoughAttribute injection is simple to implement and easy to use, but it has the following disadvantages:
if we put the mouse on the annotation, it will prompt us that attribute injection is not recommended
1. It is impossible to inject an immutable object (final modified object)
The final modified object is either copied directly or assigned in the constructor. When we put our attribute injection, the above two are not satisfied, so the injection fails.
2. Universality, attribute injection can only be used in the IoC container, and it is not supported in other containers.
3. Violation of the single design principle. A simple understanding is that the simpler the injection method, the greater the probability of abuse, and the greater the probability of violating a single responsibility
Setter injection
Setter injection is also implemented using the @Autowired annotation
@Component
public class Group {
private User user;
@Autowired
public void setUser(User user) {
this.user = user;
}
public User getUser() {
return user;
}
}
We can also successfully store and retrieve using Setter injection. Setter injection conforms to the design principle of single responsibility, but it also has the following disadvantages:
1. Immutable objects cannot be injected
2. The injected object may be modified, because we can call the setXXX method in any event to change the injected object
constructor injection
Constructor injection is also the injection method officially recommended by Spring:
public class Group {
private User user;
@Autowired
public Group(User user) {
this.user = user;
}
}
If the current class has only one constructor, the @Autowired annotation can be omitted
Constructor injection. It has the following advantages:
1. Immutable objects can be injected
2. The injected object will not be modified.
The construction method will only be executed once when the object is created, because there is no case where the injected object is modified at any time.
3. The fully initialized
construction method is created when the object is created Previously, when we use the injected object, it will be fully initialized
4. Strong versatility
and support various frameworks
The difference between @Autowired and @Resource
When performing class injection, in addition to using the @Autowired keyword, we can also use @Resource to inject
the difference between @Autowired and @Resource:
1. Different origins: @Autowired is a Spring annotation, @Resource is a JDK annotation
2. The search order is different: @Autowired first queries by type and then by name, while @Resource first queries by name and then by type
3. Different support parameters, @Autowired supports one, @Resource supports 7
4. Dependency injection support is different: @Autowired supports Three injections, while @Resource only supports property injection and Setter injection
When there are multiple beans of the same type, an error will be reported
, and then an error will occur when obtaining the object. The non-unique Bean object, because we have user1 and user2 in Spring, I don’t know which one to inject. There are two solutions: 1. Use
@Resource( name = "XXX")
2. Use the @Qualifier annotation to define the name, and use it with the @Autowired annotation