💂 personal home page :Java program fish 🤟 the entire Java system of interview questions I will share, we can continue to pay attention to 💬 if the article is helpful to you, welcome to follow, like, favorites (one button three links) and subscribe to the column oh. 💅 have any question welcome private letter, see will reply in time!

The serial number content The link address
1 Java basic knowledge questions Blog.csdn.net/qq_35620342…
2 Java collection containers To share
3 Concurrent programming in Java To share
4 Java exception interview question To share
5 The JVM interview questions To share
6 Java Web interview questions Blog.csdn.net/qq_35620342…
7 Spring interview questions Blog.csdn.net/qq_35620342…
8 Spring MVC interview questions To share
9 Spring Boot interview question To share
10 MyBatis interview questions To share
11 Spring Cloud interview question To share
12 Redis interview questions Blog.csdn.net/qq_35620342…
13 MySQL database interview question Blog.csdn.net/qq_35620342…
14 The RabbitMQ interview questions To share
15 Dubbo interview questions To share
16 Linux interview questions To share
17 Tomcat interview questions To share
18 They are the interview questions To share
19 Netty interview questions To share
20 Data structures and algorithms interview questions To share

Overview of Spring

1. What is Spring?

Spring is a lightweight Java development framework originally created by Rod Johnson to solve the problem of coupling the business logic layer and other layers of enterprise application development. It is a layered JavaSE/JavaEE full-stack lightweight open source framework that provides comprehensive infrastructure support for developing Java applications. Spring takes care of the infrastructure, so Java developers can focus on application development.

Spring’s fundamental mission is to address the complexities of enterprise application development by simplifying Java development.

Spring can do a lot of things, and it provides rich functionality for enterprise development, but the underlying functionality is dependent on its two core features, dependency injection, DI) and aspect-oriented Programming (AOP).

To reduce the complexity of Java development, Spring has adopted four key strategies

  • Pojo-based lightweight and least intrusive programming;
  • Loose coupling through dependency injection and interface oriented;
  • Declarative programming based on aspects and conventions;
  • Reduce boilerplate code with cuts and templates.

2. What are the design goals, concepts, and core of the Spring framework?

Spring design goals: Spring provides a one-stop lightweight application development platform for developers;

Spring design concept: In JavaEE development, support POJO and JavaBean development methods, make the application interface oriented development, fully support OO (object-oriented) design method; Spring implements object coupling relationship management through IoC container, and realizes dependency inversion. The dependencies between objects are handed over to IoC container to achieve decoupling.

The core of the Spring framework: the IoC container and AOP modules. Managing POJO objects and coupling between them through the IoC container; Enhance services in a dynamic, non-intrusive manner through AOP.

IoC allows components that work together to remain loosely coupled, while AOP programming allows you to separate functionality across application layers into reusable functional components.

3. What are the benefits of using Spring?

  • Lightweight: Spring is lightweight, with a base version of about 2MB

  • Inversion of control: Spring implements loose coupling through inversion of control, where objects give out their dependencies rather than creating or finding dependent objects

  • Faceted Programming (AOP) : Spring supports faceted programming and separates application business logic from system services

  • Container: Spring contains and manages the life cycle and configuration of objects in your application

  • MVC Framework: Spring’s WEB framework is a well-designed framework and a good alternative to WEB frameworks

  • Transaction Management: Spring provides a continuous transaction management interface that can be extended up to local and down to global transactions (JTA)

  • Exception handling: Spring provides convenient apis for turning technology-specific exceptions (such as those thrown by JDBC, Hibernate, or JDO) into consistent, unchecked exceptions

4. What modules does Spring consist of?

  • Core Container

    The core container provides the basic functionality of the Spring framework. The main component in the core container is the BeanFactory class, which is the implementation of the factory pattern and is responsible for managing Javabeans. The BeanFactory class uses IOC to separate the application configuration and dependency specification from the actual application code.

  • The Data Access/Integration ORM module provides the Integration layer for the mainstream Object-relation Mapping API. These mainstream object-relational mapping apis include JPA, JDO, Hibernate, and IBatis. This module can be used by combining the O/R mapping framework with features provided by Spring

  • Web module The Web module includes Web, Servlet, and Protlet modules. The Web module provides basic Web-oriented integration features such as multiple file upload, initializing the IOC container with servlet listeners, and web-oriented application context, as well as web-related parts of Spring’s remote support. The Servlet module provides a model-View-controller (MVC) implementation of Spring’s Web applications. The Protlet module provides an MVC implementation for use in the Protlet environment.

  • The AOP module provides an implementation of faceted programming in the AOP Consortium standard

  • The Messaging module contains features for publishing and subscribing to messages.

  • The Test module supports testing of Spring components using JUnit and TestNG. It provides consistent ApplicationContexts and cackable contexts. It also provides mock objects that allow developers to Test their code independently.

5. What design patterns are used in the Spring framework?

Spring uses the factory pattern to create bean objects from either the BeanFactory or ApplicationContext.

Comparison between the two:

  • BeanFactory: Lazy injection (injected when a bean is used) takes up less memory and starts faster than a BeanFactory.
  • ApplicationContext: When the container starts, create all the beans at once, whether you use them or not. BeanFactory provides only the most basic dependency injection support. ApplicationContext extends BeanFactory to include additional functions. So the average developer will use ApplicationContext more.

ApplicationContext’s three implementation classes:

  • ClassPathXmlApplication: Treat the context file as a classpath resource.
  • FileSystemXmlApplication: Loads context definition information from XML files in the file system.
  • XmlWebApplicationContext: Loads context definition information from an XML file in the Web system.

The default scope of Spring beans is singleton

(3) Proxy mode AOP(aspect-oriented Programming: section-oriented Programming) can have nothing to do with the business, but for the business module jointly called logic or responsibility (such as transaction processing, log management, authority control, etc.) encapsulated, easy to reduce the system’s repeated code, The coupling degree between modules is reduced and the scalability and maintainability are improved in the future.

Spring AOP is based on dynamic proxies. If the object to be proxied implements an interface, Spring AOP uses JDK Proxies to create Proxy objects. For objects that do not implement an interface, Spring AOP uses Cglib. Spring AOP then uses Cglib to generate a subclass of the proxied object as the proxy, as shown in the following figure:You can also use AspectJ, Spring AOP, and integrate with AspectJ, which is probably the most complete AOP framework in the Java ecosystem.

With AOP, we can abstract out some common functions and use them where needed, which greatly simplifies the amount of code. It is also convenient when we need to add new features, which also improves system scalability. Logging capabilities, transaction management, and other scenarios use AOP.

Spring jdbcTemplate, hibernateTemplate and other classes that end in Template for database operations use the Template mode. Instead of using inheritance to implement the template pattern, Spring uses the Callback pattern in conjunction with the template method pattern to achieve code reuse and increase flexibility.

(5) The observer pattern defines a one-to-many dependency between object keys. When the state of an object changes, all objects that depend on it are notified to be updated, such as the implementation of ApplicationListener in Spring.

The Adapter Pattern translates one interface into another that the customer wants. The Adapter Pattern enables classes with incompatible interfaces to work together, and its alias is wrappers.

Adapter pattern in Spring AOP: We know that The implementation of Spring AOP is based on the proxy pattern, but Spring AOP enhancements or Advice use the adapter pattern, associated with AdvisorAdapter interface. Common types of Advice include: BeforeAdvice (before target method invocation), AfterAdvice (after target method invocation), AfterReturningAdvice(after target method execution ends, before return), and so on. Each type of Advice (inform) have corresponding interceptor: MethodBeforeAdviceInterceptor, AfterReturningAdviceAdapter, AfterReturningAdviceInterceptor. Spring predefined notification to go through the corresponding adapter, adapter into the MethodInterceptor interface interceptor (method) types of objects (such as: MethodBeforeAdviceInterceptor adapter MethodBeforeAdvice).

Adapter pattern in Spring MVC: In Spring MVC, the DispatcherServlet invokes HandlerMapping based on the request information and resolves the Handler corresponding to the request. After parsing to the corresponding Handler (commonly known as the Controller Controller), it is processed by the HandlerAdapter adapter. The HandlerAdapter acts as the desired interface, the specific adapter implementation class is used to adapt the target class, and the Controller acts as the class to be adapted.

6. Explain the core container (Spring Context) module in detail

This is the basic Spring module that provides the basic functionality of the Spring framework, and the BeanFactory is the core of any Spring-based application. The Spring framework builds on this module, which makes Spring a container.

The Bean factory is an implementation of the factory pattern that provides inversion of control to separate application configuration and dependencies from the actual application code. The most commonly used is org. Springframework. Beans. Factory. XML. XmlBeanFactory, it according to the loading beans defined in the XML file. The container reads configuration metadata from an XML file and uses it to create a fully configured system or application.

7. What are the different types of events in the Spring framework

Spring provides the following five standard events:

  • Context update events (ContextRefreshedEvent) : in the call ConfigurableApplicationContext interface the refresh () method is triggered.

  • Context Start event (ContextStartedEvent) : when the container calls ConfigurableApplicationContext Start () method of Start/restart container is triggered when the event.

  • Context Stop events (ContextStoppedEvent) : when the container calls ConfigurableApplicationContext Stop () method to Stop container is triggered when the event.

  • ContextClosedEvent: Triggered when ApplicationContext is closed. When the container is closed, all singleton beans it manages are destroyed.

  • Request processing event (RequestHandledEvent) : In a Web application, this event is triggered when an HTTP request ends. If a bean implements the ApplicationListener interface, the bean is automatically notified when an ApplicationEvent is published.

8. What are the different components of a Spring application?

Spring applications typically have the following components:

  • Interface – Defines functions.
  • Bean class – it contains properties, setter and getter methods, functions, and so on.
  • Bean configuration file – contains information about the classes and how to configure them.
  • Spring Tangential Programming (AOP) – Provides tangential programming capabilities.
  • User program – it uses interfaces.

9. What are the ways to use Spring?

Spring can be used in the following ways:

  • As a full-fledged Spring Web application.
  • As a third-party Web framework, use the Spring Frameworks middle layer.
  • As an enterprise-class Java Bean, it can wrap existing POJOs (Plain Old Java Objects).
  • For remote use.

2. Spring inversion of control

1. What is the Spring IOC container?

IOC is an Inversion of Control.

How to understand “inversion of control”? The key to understanding it well is to answer four questions:

  • Who controls who: In the traditional development model, we create objects directly by new object, which means that the objects you depend on are directly controlled by you, but with the IOC container, they are directly controlled by the IOC container. So “who controls who” is, of course, what the IoC container controls.
  • Control what: Control objects.
  • Why this is inversion: Without IoC we were all actively creating dependent objects in our own objects, which is a positive inversion. However, with IoC, the dependent object is directly created by IoC container and injected into the injected object. The dependent object is changed from the original active acquisition to passive acceptance, so it is a reversal.
  • Which aspects are reversed: The retrieval of dependent objects is reversed.

2. What does inversion of control (IoC) do?

  • Create managed objects and maintain their dependencies. Object creation is not a simple task, and when object relationships are more complex, it can be quite a headache if the dependencies need to be maintained by the programmer

  • Decoupled, leaving the container to maintain the concrete objects

  • Hosting the class generation process, for example, we need to do some processing in the class generation process, the most direct example is the proxy, if there is a container can hand this part of the processing to the container, the application does not care about how the class does the proxy

3. How does SpringIOC reduce coupling between objects?

In our daily development, creating objects is so common that it can feel tedious at the same time that we are familiar with them. Every time we need an object, we have to create it by hand, and in some cases it can’t be recycled due to bad programming habits. But more seriously, the principle of loose coupling, less intrusion that we’ve always advocated, becomes useless in this situation. The older generation began to think about how to use code to be more decoupled, and the solution was interface oriented programming, which is what it looks like:

public class BookServiceImpl {

	 private  BookDaoImpl bookDaoImpl;
	 
	 public void oldCode(a){
	     // The original way
	     bookDaoImpl = newbookDaoImpl(); bookDaoImpl.getAllCategories(); }}public class BookServiceImpl {

	 private BookDao bookDao;
	
	 public void newCode(a){
	     // Change to interface oriented programming
	     bookDao = newbookDaoImpl(); bookDao.getAllCategories(); }}Copy the code

Instead of interacting directly with BookDaoImp, the BookDao in the BookServiceImpl class will be BookDao. Even though the BookDao will still end up being BookDaoImp, the benefit is obvious. All calls are made through the BookDao interface. The actual implementor and ultimate implementor of the interface is bookDaoImpl, and when replacing the bookDaoImpl class, you simply change the bookDao to point to the new implementation class.

Although the above code greatly reduces the coupling of the code, the code is still intrusive and somewhat coupled. For example, when modifying the Implementation class of bookDao, you still need to modify the internal code of BookServiceImpl, and the process of finding and modifying the code can be quite bad when there are more dependent classes. So we still need to find a way for developers to modify the bookDao implementation class without touching the BookServiceImpl content code to achieve minimal coupling and intrusion. In fact there is a known as the reflection of the programming techniques can help to solve the above problem, reflection is a complete according to the given class name (string) to dynamically generated objects, this way of programming can make objects in the generated when decide whether is a kind of object, which can therefore assume that, in a configuration file, This file has the fully qualified name of the bookDaoImpl class written in it. By reading this file, we obtain the fully qualified name of the real implementation class of bookDao, and then use reflection technology to dynamically generate the class at runtime and finally assign the value to the bookDao interface. Use the properties file as the configuration file, classname.properties as follows:

bookDao.name=com.spring.dao.BookDaoImpl
Copy the code

Get this configuration file information to dynamically generate the implementation class for bookDao:

public class BookServiceImpl implements BookService
{
    // Utility class to read configuration files
    PropertiesUtil propertiesUtil=new PropertiesUtil("conf/className.properties");

    private BookDao bookDao;

    public void DaymicObject(a) throws ClassNotFoundException, IllegalAccessException, InstantiationException {
        // Get the fully qualified name
        String className=propertiesUtil.get("bookDao.name");
        // By reflection
        Class c=Class.forName(className);
        // Dynamically generate instance objectsbookDao= (BookDao) c.newInstance(); }}Copy the code

We did generate an instance of bookDao as we expected. The advantage of this is that in the case of replacing the bookDao implementation class, we only need to modify the contents of the configuration file without touching the internal code of BookServiceImpl, thus passing the code modification process to the configuration file. BookServiceImpl and its internal bookDao are associated with bookDao’s implementation class through a configuration file, so that there is a decoupling between BookServiceImpl and bookDao’s implementation class. Of course, the presence of a BookDao object in the BookServiceImpl class is inevitable, since this is fundamental to collaboration, and we can only decouple it to the maximum extent possible.

Understanding IOC is much easier with these issues in mind. Spring IOC is also a Java object that, after being created at a specific time, has control over other objects, including initialization, creation, destruction, and so on. Briefly, we configure the fully qualified name of the BookDaoImpl implementation class through the configuration file, and then use reflection to create the actual implementation class for BookDao at runtime, including the creation of BookServiceImpl, which Spring’s IOC container does for us. The only thing to do is to tell the IOC container, in a configuration file, which classes to create and which to inject, as well as the classes that need to be created and other classes that depend on them. Spring promotes loose coupling through this inversion of control (IoC) design pattern, in which an object is transmitted passively when it depends on another object (as when BookServiceImpl was created, The implementation classes of the BookDao that it depends on are also injected into BookServiceImpl), rather than creating them manually. We can think of the IoC pattern as a refinement of the factory pattern. We can think of IoC as a large factory, except that the objects to be generated in this factory are defined in the configuration file (XML), and then Java’s reflection technology is used to generate the corresponding objects based on the class names given in the XML. IoC, to some extent, is the equivalent of changing the hard-coded object creation code in the factory method to an XML file definition. In other words, the factory and object generation are separated independently, in order to improve flexibility and maintainability, and to achieve a minimum of coupling. Therefore, we should understand that the so-called IOC hands over the creation of objects to Spring, thus freeing the process of manually creating objects and at the same time making the relationship between classes reach the lowest degree of coupling.

4. What are the advantages of IOC?

  • IOC or dependency injection minimizes the amount of code in your application.
  • It makes applications easy to test, eliminating the need for singletons and JNDI lookups for unit tests.
  • Loose coupling is possible with minimal cost and intrusion.
  • The IOC container supports hunger-style initialization and lazy loading when loading services.

5. What features does Spring’s IOC support

Spring’s IoC design supports the following features:

  • Dependency injection
  • Depend on the check
  • Automatically.
  • Support the collection
  • Specify initialization and destruction methods
  • Support for callbacks to some methods (but need to implement the Spring interface, slightly intrusive)

The most important of these is dependency injection, which, in XML configuration terms, is the REF tag. Corresponds to the Spring RuntimeBeanReference object.

For the IoC, the most important thing is the container. The container manages the Bean life cycle and controls the dependency injection of beans.

6. What is the difference between BeanFactory and ApplicationContext?

BeanFactory and ApplicationContext are two core Spring interfaces that can be used as Spring containers. ApplicationContext is the subinterface of the BeanFactory.

(1) Dependency BeanFactory: it is the lowest interface in Spring, which contains the definition of various beans, reads Bean configuration documents, manages Bean loading and instantiation, controls the life cycle of beans, and maintains the dependency between beans. The ApplicationContext interface, a derivative of the BeanFactory interface, provides more complete framework functionality in addition to the functionality of the BeanFactory:

  • Inheriting MessageSource to provide a standard access strategy for internationalization.
  • Inheritance ApplicationEventPublisher, provide a powerful event mechanism
  • Extension ResourceLoader, can be used to load multiple resources, flexible access to different resources
  • Support for Web applications

The ApplicationContext interface inherits the BeanFactory interface. Spring’s core factory is BeanFactory. BranFactory uses lazy loading. The Bean is initialized the first time the getBean is loaded. The ApplicationContext initializes the Bean when the configuration file is loaded.

BeanFactory is usually created programmatically. ApplicationContext can also be created declaratively, such as using ContextLoader.

BeanFactory and ApplicationContext both support BeanPostProcessor and BeanPostProcessor, but the differences are as follows: BeanFactory needs to be registered manually, whereas ApplicationContext is automatically registered.

7. What is the common implementation of ApplicationContext?

  • FileSystemXmlApplicationContext: the container load from the XML file has been defined a bean. Here, you need to provide the full path to the constructor XML file

  • ClassPathXmlApplicationContext: the container load from the XML file has been defined a bean. Here, you don’t need to provide the full path to the XML file, just configure the CLASSPATH environment variable correctly, because the container will search the bean configuration file from the CLASSPATH.

  • WebXmlApplicationContext: This container loads beans defined in an XML file within the scope of a Web application.

8. What are the different types of dependency injection implementations?

Dependency Injection is the most popular implementation of IoC at present. Dependency Injection can be divided into Interface Injection, Setter Injection and Constructor Injection. Interface injection has been deprecated since Spring4 due to poor flexibility and ease of use.

Constructor dependency injection: Constructor dependency injection is implemented by the container firing the constructor of a class that has a series of parameters, each representing a dependency on another class.

Setter method injection: Setter method injection implements setter-based dependency injection by invoking Setter methods of a bean after the bean has been instantiated by calling either a no-argument constructor or a no-argument static factory method.

9. Constructor dependency injection versus Setter method injection

Constructor injection setter injection
No partial injection Partial injection
Setter properties are not overridden It overrides the setter property
Any changes will create a new instance Arbitrary changes do not create a new instance
This is useful for setting many properties Suitable for setting a small number of properties

Both types of dependency can be used, constructor injection and Setter method injection. The best solution is to implement mandatory dependencies with constructor arguments and optional dependencies with setter methods.

Third, the Spring Beans

1. What are Spring beans?

Spring Beans are the Java objects that form the backbone of a Spring application. They are initialized, assembled, and managed by the Spring IOC container. The Beans are created from metadata configured in the container. For example, as defined in an XML file.

Beans defined by the Spring framework are singleton Beans. There is an attribute “singleton” in the bean tag. If it is set to TRUE, the bean is a singleton, otherwise it is a Prototype bean. The default is TRUE, so all Beans in the Spring framework are singleton by default.

2. What does a Spring Bean definition contain?

The definition of a Spring Bean contains all configuration metadata that the container must know, including how to create a Bean, its lifecycle details, and its dependencies.

3. How do I provide configuration metadata to the Spring container? Spring can be configured in several ways

There are three important ways to provide configuration metadata to the Spring container.

  • XML configuration file.
  • Annotation-based configuration.
  • Java-based configuration.

4. Several ways Spring can inject beans based on XML

  • Set method injection;

  • Constructor injection: ① Set the position of the parameter through index; ② Set the parameter type by type.

  • Static factory injection;

  • Example factory;

5. How do you define the scope of a class?

When defining a bean in Spring, we can also declare a scope for the bean. It can be defined by the scope property in the bean definition. For example, when Spring produces a new bean instance each time it needs to, the scope property of the bean is specified as prototype. On the other hand, a bean must return the same instance every time it is used, and the scope property of the bean must be set to Singleton.

6. Explain the scope of several beans supported by Spring

The scope of a Bean refers to the entire process from creation to destruction after the Bean is created by the Spring container. All of the beans we created earlier are scoped to Singleton, which is the Spring default. Under such scoping, instances of each Bean are created only once, and the Spring container can use the instance for the entire life of the application. So after the Spring container created the Bean in the previous code, the Bean that the code fetched, no matter how many times, was an instance of the same Bean. We can use the scope attribute of the < bean > tag to specify the scope of a bean as follows:

<! -- Singleton is not declared by default -->
<bean name="accountDao" scope="singleton"    
class="com.spring.springIoc.dao.impl.AccountDaoImpl"/>
Copy the code

In addition to Singleton, there is another common scope, prototype, which represents the creation of a new instance object each time a Bean instance is fetched, similar to the new operator. Let’s have a quick test:

<! Prototype -->
<bean name="accountDao" scope="prototype"     class="com.spring.springIoc.dao.impl.AccountDaoImpl"/>
Copy the code

Test code:

@Test
public void test2(a)  {
    ApplicationContext applicationContext=new
            ClassPathXmlApplicationContext("spring/spring-ioc.xml");
    AccountDao accountDao1 = (AccountDao) applicationContext.getBean("accountDao");
    AccountDao accountDao2 = (AccountDao) applicationContext.getBean("accountDao");
    System.out.println("AccountDao1 address."+accountDao1.toString());
    System.out.println("AccountDao2 address."+accountDao2.toString());
}
Copy the code
Execution Result: AccountDao1 address: com. Spring. SpringIoc. Dao. Impl. A0931 AccountDaoImpl @ 579 AccountDao2 address: com. Spring. SpringIoc. Dao. Impl. 49 ads019 AccountDaoImpl @Copy the code

Obviously two different instance objects. We can also declare scopes with annotations:

@Scope("prototype")
public class AccountDaoImpl {
    / /...
}
Copy the code

A special case needs to be noted here, when a Singleton Bean is dependent on a prototype-scoped Bean:

<! Prototype -- scope -->
<bean name="accountDao" scope="prototype"
class="com.spring.springIoc.dao.impl.AccountDaoImpl"/>
<! -- scope Singleton -->
<bean name="accountService" class="com.spring.springIoc.service.impl.AccountServiceImpl">
    <! / / add prototype accountDao; / / add prototype accountDao;
    <property name="accountDao" ref="accountDao"/>
</bean>
Copy the code

In this case it is desirable that each getBean(” accountService “) handles a new accountDao instance object, but since the accountService dependency is injected when the Bean is created, The accountService is a Singleton and is created only once in its lifetime. Therefore, the accountDao instance on which it depends is injected only once and no new accountDao instance is injected thereafter. In order to solve this dilemma, the dependency injection function can only be abandoned and implemented in code, as follows: Override setApplicationContext by implementing the ApplicationContextAware interface so that the Spring container automatically injects the ApplicationContext object when creating an instance of AccountServiceImpl, This ensures that the accountDao instance is new each time it is obtained through the ApplicationContext. (The code here only demonstrates this process, and development generally does not require the accountDao to be a new instance each time. Because the accountDao does not need to record state information, that is, stateless bean, generally default singleton.)

<bean name="accountDao" scope="prototype"  class="com.zejian.spring.springIoc.dao.impl.AccountDaoImpl"/>
<! -- accountDao injected via code -->
<bean name="accountService" class="com.zejian.spring.springIoc.service.impl.AccountServiceImpl" />
Copy the code

Code injection demonstration:

public class AccountServiceImpl implements AccountService , ApplicationContextAware {
    private ApplicationContext applicationContext;

    @Override
    public void doSomething(a) {
        System.out.println("AccountServiceImpl#doSomething......");
        System.out.println("getAccountDao....."+ getAccountDao().toString());

    }

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        this.applicationContext=applicationContext;
    }

    private AccountDao getAccountDao(a){
        returnapplicationContext.getBean(AccountDao.class); }}Copy the code

Test code:

// Load the configuration file
ApplicationContext applicationContext=new ClassPathXmlApplicationContext("spring/spring-ioc.xml");
// Test getting accountDaOs of different instances
AccountService accountService= (AccountService) applicationContext.getBean("accountService");
accountService.doSomething();
AccountService accountService1= (AccountService) applicationContext.getBean("accountService");
accountService1.doSomething();
Copy the code
Result: AccountServiceImpl#doSomething...... getAccountDao..... com.spring.springIoc.dao.impl.AccountDaoImpl@ab321564 AccountServiceImpl#doSomething...... getAccountDao..... com.spring.springIoc.dao.impl.AccountDaoImpl@2aga1580Copy the code

Obviously, this approach resolves the above problem by obtaining a different daoAccount each time, or if a Bean scoped propoType depends on a singleton-scoped Bean, the solution is the same. Note that Spring is not responsible for the entire life cycle of a Bean once it is set to Prototype; the container initializes, configures, decorates, or assembs a Prototype instance, hands it to the client, and then doesn’t care about the Prototype instance. Therefore, it needs to be used with caution. In general, the Prototype scope should be used for stateful beans and the Singleton scope should be used for stateless beans. Stateful means that the bean has the ability to save information and cannot be shared, otherwise it will cause thread safety problems. Stateless means that the bean does not save information and is thread safe and can be shared. Most of the beans in Spring are Singleton and only one bean will exist in the whole life cycle.

(3) request and session scopes spring2.5 introduces two scopes, request and session, specifically for Web applications. Regarding request scope, the Spring container creates a new request-scoped bean instance for each HTTP request that arrives in the application. This bean instance is valid only within the current HTTP request, and only the same bean instance is used throughout the request. Therefore, we can safely change the internal state of the created instance as needed, while other requests HTTP requests create new instances of beans that do not interfere with each other. When the processing request ends, the bean instances in the request scope will be destroyed. For example, a bean instance may be needed to load some parameters when receiving parameters. Obviously the request parameters are almost never the same each time, so you want the bean instance to be sufficiently new each time and valid only within the scope of the request. As you might have guessed about sessions, a session-scoped Bean is created every time a new HTTP Session is created, and the instance Bean exists with the Session. Here is a test program:

@Component
@Scope(value = "singleton")
public class SingletonBean {
    / /...
}

@Component
@Scope(value = "prototype" , proxyMode = ScopedProxyMode.TARGET_CLASS)
public class PrototypeBean {
    / /...
}

@Component
@Scope(value = "request" , proxyMode = ScopedProxyMode.TARGET_CLASS)
public class RequestBean {
    / /...
}

@Component
@Scope(value = "session" , proxyMode = ScopedProxyMode.TARGET_CLASS)
public class SessionBean {
    / /...
}
Copy the code

@Component table name these are Component classes that need the help of the Spring container. @Scope indicates the Scope, value indicates the Scope, and SingletonBean indicates the Scope. Other beans also use proxyMode to specify which proxyMode is created. There is no interface, so CGLib proxy generation is used (we’ll see why this is done later). You then need to specify the scan package in the XML to tell the Spring container where they are (all four classes are declared under the com.zejian.spring.dto package).

<! -- Packet scanning -->
<context:component-scan  base-package="com.spring.dto" />
Copy the code

Create a Web access layer using SpringMVC (if you don’t know SpringMVC, you can understand that the Web access layer is going to be like a Servlet) :

@Controller
public class BookController {
    @Autowired
    private RequestBean requestBean;
    @Autowired
    private SessionBean sessionBean;
    @Autowired
    private PrototypeBean prototypeBean;
    @Autowired
    private SingletonBean singletonBean;


    @RequestMapping(value = "/test")
    public void test(a)
    {
        print();
    }

    public void print(a) {
        System.out.println("first time singleton is :" + singletonBean);
        System.out.println("second time singleton is :" + singletonBean);

        System.out.println("first time prototype is :" + prototypeBean);
        System.out.println("second time prototype is :" + prototypeBean);

        System.out.println("first time requestBean is :" + requestBean);
        System.out.println("second time requestBean is :" + requestBean);

        System.out.println("first time sessionBean is :" + sessionBean);
        System.out.println("second time sessionBean is :" + sessionBean);

        System.out.println("= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = ="); }}Copy the code

Now start the Tomcat server and use Chrome for two consecutive visits. The results are as follows:

first time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720 second time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720 first time prototypeBean is :com.zejian.spring.dto.PrototypeBean@1ed53cde second time prototypeBean is :com.zejian.spring.dto.PrototypeBean@35c052be first time requestBean is :com.zejian.spring.dto.RequestBean@15b9dfe1 second time requestBean is :com.zejian.spring.dto.RequestBean@15b9dfe1 first  time sessionBean is :com.zejian.spring.dto.SessionBean@5b355dae second time sessionBean is :com.zejian.spring.dto.SessionBean@5b355dae =========================================== first time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720 second time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720  first time prototypeBean is :com.zejian.spring.dto.PrototypeBean@7775fd09 second time prototypeBean is :com.zejian.spring.dto.PrototypeBean@79b20d97 first time requestBean is :com.zejian.spring.dto.RequestBean@7d8d9679 second time requestBean is :com.zejian.spring.dto.RequestBean@7d8d9679 first time sessionBean is :com.zejian.spring.dto.SessionBean@5b355dae second time sessionBean is :com.zejian.spring.dto.SessionBean@5b355dae = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =Copy the code

Obviously, a singletonBean will always have only one instance, whereas a PrototypeBean will create a new instance each time it is fetched, corresponding to the RequestBean, which is the same instance during the same Http request. When the request ends, the RequestBean is destroyed. New RequestBean instances are generated on new Http requests. In the case of session beans, the SessionBean instances are the same instance object because they are accessed in the same browser and belong to the same session. Now use another browser to start the access and see if the SessionBean changes.

first time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720 second time singletonBean is :com.zejian.spring.dto.SingletonBean@2ebdd720 first time prototypeBean is :com.zejian.spring.dto.PrototypeBean@5a85c6a7 second time prototypeBean is :com.zejian.spring.dto.PrototypeBean@54423387 first time requestBean is :com.zejian.spring.dto.RequestBean@507dadd7 second time requestBean is :com.zejian.spring.dto.RequestBean@507dadd7 first  time sessionBean is :com.zejian.spring.dto.SessionBean@157f39bc second time sessionBean is :com.zejian.spring.dto.SessionBean@157f39bc ===========================================Copy the code

Obviously, the SessionBean has changed, which means that the SessionBean instance is different in different sessions. But we were still wondering why we needed to set the proxy mode on the other three scopes. In fact, the essence of this problem is the same as that of the Prototype scoped bean that singleton-scoped beans depend on. Prototype analyzed this earlier (we must also declare proxy mode when using annotations). Here we focus on the Request and session scopes. Since the Spring container will only help us inject other bean instances that the instance bean depends on when it is created, and only once, which is not what the Request, session scope wants, After all, they all need to inject new instance objects in different scenarios instead of the only constant instance objects. To solve this dilemma, you must abandon injecting bean instances directly into XML and use Either Java code (implementing the ApplicationContextAware interface) or annotations (@AutoWired). The example chose the latter and declared the dynamic proxy pattern in the bean declaration (check out the resources for dynamic proxies). Fortunately, the Spring container is smart enough to generate new proxy instance beans by proxy to meet the need to create new instances. During program execution, when a method call reaches the proxy object, the Spring container tries to get the target object Bean(the actual instance Bean) on the current Request or Session. Use the Bean if it already exists; otherwise, the proxy method creates a new instance Bean to process the request or session, which is an Http request or session. If you want the Request and session scopes declared in an XML configuration file, you must place < AOP :scoped-proxy > as a child tag in the < bean > tag. This works in the same way as the annotation declaration proxy mode. Declare the proxy. Please note that this method of declaring proxies does not work in the Prototype scope as the only methods currently tested are the annotation-based method and the previous method based on implementing the ApplicationContextAware interface.


      
<beans xmlns="http://www.springframework.org/schema/beans"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:mvc="http://www.springframework.org/schema/mvc"
 xmlns:context="http://www.springframework.org/schema/context"
 xmlns:aop="http://www.springframework.org/schema/aop"
 xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.2.xsd http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"
>

<bean id="requestBean" scope="request" class="com.spring.dto.RequestBean" >
    <! Declare an AOP proxy -->
    <aop:scoped-proxy />
</bean>

<bean id="sessionBean" scope="request" class="com.spring.dto.SessionBean" >
    <! Declare an AOP proxy -->
    <aop:scoped-proxy />
</bean>
</beans>
Copy the code

One final point to make clear is that if the Web layer is suitable for SpringMVC to handle Web requests, nothing needs to be done to enable the Request and Session scopes. However, if other Web layer frameworks are applicable, it is important to declare the following listeners in web.xml for the Request and Session scopes to work properly:

<web-app>
    <listener>
        <listener-class> org.springframework.web.context.request.RequestContextListener <listener-class>
    </listener>
</web-app>
Copy the code

GlobalSession scope This scope is similar to the Session scope, which is equivalent to the global variable, and is similar to the Application of servlets. It is suitable for portlet-based Web applications. Note that portlet here refers to distributed development. Rather than portlet language development.

7. Are singleton beans in the Spring framework thread-safe?

No, singleton beans in the Spring framework are not thread-safe.

Beans in Spring are singleton by default. The Spring framework does not encapsulate singleton beans in multiple threads.

In fact, most of the time spring beans are stateless (such as dao classes), all beans are safe to some extent, but if beans are stateful (such as View Model objects), it is up to the developer to keep them thread-safe. The simplest is to change the scope of the bean and change “singleton” to “Prototype” so that the request bean is equivalent to new bean (), so thread-safe.

  • Stateful is data storage.
  • Stateless means no data is saved.

8. How does Spring handle thread concurrency?

In general, only stateless beans can be shared in a multithreaded environment. In Spring, most beans can be declared singleton scoped because Spring uses ThreadLocal to handle non-thread-safe state of some beans to address thread-safe issues.

Both ThreadLocal and thread synchronization are designed to solve the problem of conflicting access to the same variable in multiple threads. The synchronization mechanism adopts the “time for space” approach, providing only one variable, different threads need to acquire the lock before accessing, and threads that do not acquire the lock need to queue. ThreadLocal takes a “space for time” approach.

ThreadLocal provides a separate copy of variables for each thread, isolating conflicting data access from multiple threads. Since each thread has its own copy of the variable, there is no need to synchronize it. ThreadLocal provides thread-safe shared objects that can encapsulate unsafe variables in ThreadLocal when writing multithreaded code.

9. Explain the lifecycle of beans in the Spring framework

interface methods instructions
BeanFactoryPostProcessor postProcessBeanFactory Executed before the Bean object is instantiated, the beanFactory lets you get the Bean definition information and modify the Bean definition information. This is the biggest difference from BeanPostProcessor
BeanPostProcessor postProcessBeforeInitialization After instantiation, dependency injection, some custom initialization tasks are completed before the initialization of the call display
postProcessAfterInitialization Instantiation, dependency injection, and initialization are completed
InstantiationAwareBeanPostProcessor postProcessBeforeInstantiation The method is executed before the method is instantiated, and the result is null. If the result is not null, the method is skipped and the initialization process is completed
postProcessAfterInstantiation After methods instantiate execution and returns the result of true will perform postProcessPropertyValues method
postProcessPropertyValues You can use it to modify the contents of a property in a Bean
InitializingBean afterPropertiesSet Method of initialization
DisposableBean destroy Callback method before container destruction
Aware setXXX Aware of the contents of the corresponding Spring container
@PostConstruct Note in the method header to indicate the initialization method
@PreDestroy Labeled in the method header to indicate the method of callback before destruction
The init method attribute Specifies the method of initialization
Destory – method attribute Specifies the callback method before destruction

(1) BeanFactoryPostProcessor Interface The methods in this interface are executed first. Execute before Bean instantiation

/** * Custom BeanFactoryPostProcessor ** /
public class MyBeanFactoryPostProcessor implements BeanFactoryPostProcessor {

	/** * This method is executed before the Bean object is instantiated. The beanFactory is used to obtain the Bean definition information, and the Bean definition information can be modified. This is the biggest difference from BeanPostProcessor */
	@Override
	public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
		
		System.out.println("****** BeanFactoryPostProcessor is running");
		/*String[] names = beanFactory.getBeanDefinitionNames(); for (String name : names) { if("user".equals(name)){ BeanDefinition beanDefinition = beanFactory.getBeanDefinition(name); MutablePropertyValues propertyValues = beanDefinition.getPropertyValues(); // MutablePropertyValues can be changed if the related properties are set. If there is no set related attribute information if you can add (propertyValues. The contains (" name ")) {propertyValues. AddPropertyValue (" name ", "bobo"); System.out.println(" modify attribute information "); }}} * /
		System.out.println("******* BeanFactoryPostProcessor execution finished"); }}Copy the code

This interface defines two methods, which are respectively executed after Bean object instantiation and assembly before and after initialization

The BeanPostProcessor interface is used to add our own logic before and after bean instantiation, configuration, and other initialization methods ** /
public class MyBeanPostProcessor implements BeanPostProcessor{

	/** * Complete some custom initialization tasks before calling display initialization * Note: Method return value cannot be null * If null is returned then subsequent initializers will either report a null pointer exception or the bena instance object cannot be retrieved through the getBean() method */ because the backend handler took the bean instance object from the Spring IoC container and did not put it back into the IoC container */
	@Override
	public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println(">> postprocessor before method :"+bean+"\t"+beanName);
		}
		
		// Different processing operations can be performed depending on the beanName
		return bean;
	}

	/** * execute when instantiation, dependency injection, and initialization are complete Method return value cannot be null * If null is returned then subsequent initializers will either report a null pointer exception or the bena instance object cannot be retrieved through the getBean() method */ because the backend handler took the bean instance object from the Spring IoC container and did not put it back into the IoC container */
	@Override
	public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println(<< post-processor after method:+bean+"\t"+beanName);
		}
		// Different processing operations can be performed depending on the beanName
		returnbean; }}Copy the code

(3) InstantiationAwareBeanPostProcessor interface The interface a BeanPostProcessor interface as part of the interface, so must have the function of the BeanPostProcessor interface, the interface defines three own interface again at the same time, These three interfaces are methods that execute before and after Bean instantiation.

/** * Custom processor ** /
public class MyInstantiationAwareBeanPostProcessor implements InstantiationAwareBeanPostProcessor{

	/** * Methods in the BeanPostProcessor interface * execute before the Bean's custom initialization method * The Bean object already exists */
	@Override
	public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
		// TODO Auto-generated method stub
		if("user".equals(beanName)){
			System.out.println("- InstantiationAwareBeanPostProcessor - postProcessBeforeInitialization 】");
		}
		
		return bean;
	}

	/** * Methods in the BeanPostProcessor interface * execute after the Bean's custom initialization method has completed * the Bean object already exists */
	@Override
	public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println("- InstantiationAwareBeanPostProcessor postProcessAfterInitialization 】");
		}
		return bean;
	}

	/ custom methods of * * * * InstantiationAwareBeanPostProcessor before methods instantiate execution Bean object has not been * /
	@Override
	public Object postProcessBeforeInstantiation(Class
        beanClass, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println("- InstantiationAwareBeanPostProcessor postProcessBeforeInstantiation 】");
		}
		return null;
	}

	/ custom methods of * * * * InstantiationAwareBeanPostProcessor after methods instantiate execution Bean object has been created * /
	@Override
	public boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println("- InstantiationAwareBeanPostProcessor postProcessAfterInstantiation 】");
		}
		return true;
	}

	/ custom methods of * * * * InstantiationAwareBeanPostProcessor can be used to modify the content of the Bean attribute * /
	@Override
	public PropertyValues postProcessPropertyValues(PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
		if("user".equals(beanName)){
			System.out.println("【--InstantiationAwareBeanPostProcessor----】postProcessPropertyValues--->");
		}
		returnpvs; }}Copy the code

(4) BeanNameAware, BeanFactoryAware Aware interface Aware interface is used to make objects such as perceive the current environment of the IOC

(5) the InitializingBean and DisposableBean interfaces The two interfaces are Bean initialization and destruction of the callback methods.

(6) @postconstruct and @predestroy

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.BeanFactoryAware;
import org.springframework.beans.factory.BeanNameAware;
import org.springframework.beans.factory.DisposableBean;
import org.springframework.beans.factory.InitializingBean;
/** * Implement the InitializingBean and DisposableBean interfaces ** /
public class User implements InitializingBean.DisposableBean.BeanNameAware.BeanFactoryAware{

	private int id;
	
	private String name;
	// Be aware of the object's ID attribute in the Spring container
	private String beanName;
	// Sense the BeanFactory object to which this object belongs
	private BeanFactory factory;
	
	public User(a){
		System.out.println("Constructor is executed... User is instantiated");
	}

	public int getId(a) {
		return id;
	}

	public void setId(int id) {
		this.id = id;
	}

	public String getName(a) {
		return name;
	}

	public void setName(String name) {
		System.out.println("Inject Properties" Inject the name property+name);
		this.name = name;
	}

	public String getBeanName(a) {
		return beanName;
	}

	
	@Override
	public String toString(a) {
		return "User [id=" + id + ", name=" + name + ", beanName=" + beanName + "]";
	}

	/** * callback method */ before the bean object is destroyed
	@Override
	public void destroy(a) throws Exception {
		// TODO Auto-generated method stub
		System.out.println("DisposableBean interface destory....");
	}

	/** * the initialization method */
	@Override
	public void afterPropertiesSet(a) throws Exception {
		System.out.println("InitializingBean interface afterPropertiesSet....");
	}

	@Override
	public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
		// TODO Auto-generated method stub
		System.out.println("[BeanFactoryAware] setBeanFactory");
		this.factory = beanFactory;
	}

	@Override
	public void setBeanName(String name) {
		System.out.println("[BeanNameWare] setBeanName");
		this.beanName = name;
	}

	public BeanFactory getFactory(a) {
		return factory;
	}

	/** * is also an initialization method */
	@PostConstruct
	public void postConstruct(a){
		System.out.println("Initialize: [@postconstruct] executes...");
	}
	/** * Callback method before destruction */
	@PreDestroy
	public void preDestory(a){
		System.out.println("[@predeStory] executed...");
	} 
	/** * The method to initialize * is specified by the init-method attribute in the bean tag */
	public void start(a){
		System.out.println("Initialize: the [init-method] method executes....");
	}
	
	/** * The pre-destruction callback method is specified by the destory-method attribute in the bean tag */
	public void stop(a){
		System.out.println("The [destory-method] method executes...."); }}Copy the code

(7) init-method, destroy-method


      
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns:context="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 http://www.springframework.org/schema/context/spring-context-4.3.xsd">
	
	<context:annotation-config/>

	<bean class="com.pojo.User" id="user" init-method="start" destroy-method="stop" >
		<property name="name" value="Duck"></property>
	</bean>
	
	<! -- Register post-processor -->
	<bean class="com.processor.MyBeanPostProcessor"/>
	
	
	<! - registered InstantiationAwareBeanPostProcessor -- -- >
	<bean class="com.processor.MyInstantiationAwareBeanPostProcessor"></bean>
	<! Register BeanFactoryPostProcessor object -->
	<bean class="com.factoryprocessor.MyBeanFactoryPostProcessor"/>
</beans>
Copy the code

(8) Test

@Test
public void test1(a) {
	System.out.println("Spring container starts loading....");
	ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
	User user = ac.getBean(User.class);
	System.out.println("-- -- -- -- -- -- -- -- -- -- -- -- -- -- --"+user);
	ac.registerShutdownHook();
	System.out.println("Spring container uninstallation completed....");
}
Copy the code

Results:

The Spring container starts loading.... March 4, 2019 afternoon 11:14:38 org. Springframework. Context. Support. The ClassPathXmlApplicationContext prepareRefresh information: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@707f7052: startup date [Mon Mar 04 23:14:38 CST 2019]; Root of Context Hierarchy March 04, 2019 11:14:39 afternoon org. Springframework. Beans. Factory. XML. XmlBeanDefinitionReader loadBeanDefinitions information: Loading XML bean definitions from Class Path Resource [ApplicationContext.xml] ****** BeanFactoryPostProcessor * * * * * * * the end of the spring BeanFactoryPostProcessor implementation - InstantiationAwareBeanPostProcessor postProcessBeforeInstantiation 】 Constructor is executed... The User is instantiated - InstantiationAwareBeanPostProcessor postProcessAfterInstantiation 】 - InstantiationAwareBeanPostProcessor postProcessPropertyValues 】 -- - > the injection property into property name bobo setBeanName BeanNameWare interface 】 【 roast duck Before method :User [id=0, name= bobo, BeanName = user] user - InstantiationAwareBeanPostProcessor - postProcessBeforeInitialization 】 Initialization: [@postconstruct] executes... Initialization: InitializingBean interface afterPropertiesSet.... Init: the [init-method] method executes.... User [id=0, name= duck, BeanName = user] user - InstantiationAwareBeanPostProcessor postProcessAfterInitialization 】 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the user [id=0, name= bobo duck, beanName=user] Spring container uninstallation is complete.... March 4, 2019 afternoon 11:14:39 org. Springframework. Context. Support. The ClassPathXmlApplicationContext doClose information: Closing org.springframework.context.support.ClassPathXmlApplicationContext@707f7052: startup date [Mon Mar 04 23:14:38 CST 2019]; Root of context Hierarchy [@predeStory] executes... DisposableBean interface destroy.... The destory-method method executes....Copy the code

1. If the BeanFactoryPostProcessor interface is implemented, the postProcessBeanFactory method in this interface can modify the information in the Bean metadata when the container is started. The method is performed before instantiation objects (2) if implemented InstantiationAwareBeanPostProcessor interface, so before instantiation Bean object will call postProcessBeforeInstantiation method, If the return is not null then this method can directly call postProcessAfterInitialization method, and skipped the Bean is instantiated and after initialization before the relevant methods, if the returns null the normal process, PostProcessAfterInstantiation execution after instantiation success, when the object is instantiated, but the instance attribute has not been set up, is null. Because it is the return value is decided to don’t call postProcessPropertyValues method is one of the factors (because there is another factor is MBD getDependencyCheck ()); If this method returns false, and do not need to check, then postProcessPropertyValues will be ignored no execution; If returns true, postProcessPropertyValues will be executed, postProcessPropertyValues used to modify properties, perform before initialization method. 3. If Aware related results are implemented, the related set methods are executed before initialization. 4. If the BeanPostProcessor interface is implemented, its methods are executed before and after the instantiated initialization methods. 5. AfterPropertiesSet 6 is executed during initialization if the InitializingBean interface is implemented. If init-method is specified, the specified method is executed during initialization. 7. If @postconstruct is specified the annotation method will be executed at initialization. 9. When the object needs to be destroyed. 10. If you implement the DisposableBean interface, you will execute method 11 destroy. If the destroy-method attribute is specified, the specified method 12 is executed. If the @predestroy annotation is specified, the annotation method is executed

10. How do I inject a Java collection in Spring?

Spring provides configuration elements for several collections:

Type is used to inject a list of values that are allowed to have the same value.

Type is used to inject a set of values that are not allowed to be the same.

Type is used to inject a set of key-value pairs, both of which can be of any type.

Type is used to inject a set of key-value pairs. The key and value can only be strings.

12. What is bean assembly?

Assembly, or bean assembly, refers to the assembly of beans together in the Spring container, provided that the container needs to know the dependencies of the beans and how to assemble them together through dependency injection.

13. What is bean autowiring?

In the Spring framework, setting bean dependencies in configuration files is a good mechanism. The Spring container can automatically assemble beans that cooperate with each other. This means that the container does not need configuration and can handle collaboration between beans automatically through the bean factory. This means that Spring can automatically handle Bean dependencies by injecting them into the Bean Factory. Autowiring can be set up on a per-bean basis or on a specific bean.

14. What are the methods for Sring to automatically assemble beans?

The Spring container can automatically assemble beans. That is, Spring can automatically resolve the bean’s collaborators by examining the contents of the BeanFactory.

Different modes of automatic assembly:

  • No, which is the default setting and means there is no autowiring. Assembly should be done using explicit bean references.
  • ByName, which injects object dependencies based on the bean name. It matches and assembles its attributes with beans defined by the same name in the XML file.
  • ByType, which injects object dependencies based on type. If the type of the attribute matches a bean name in the XML file, the attribute is matched and assembled.
  • Constructor, which injects dependencies by calling the class’s constructor. It has a lot of parameters.
  • Autodetect, first the container tries to assemble using Autowire via constructors, or if not, byType autowire.

15. What is the process of auto-assembly using @Autowired annotations?

Use the @AutoWired annotation to automatically assemble the specified bean. The @autowired annotation needs to be configured in the Spring configuration file before being used, <context:annotation-config />.

When to start the Spring IOC container automatically loaded with a rear AutowiredAnnotationBeanPostProcessor processor, when a container scanning to @ Autowied, @ when the Resource or @ Inject, The desired bean is automatically found in the IoC container and the properties are assembled for that object. When using @autowired, we first query the container for the bean of the corresponding type:

  • If the query results in exactly one, it assembles the bean to the data specified by @AutoWired;

  • If the query has more than one result, @AutoWired looks it up by name;

  • If the result of the above lookup is empty, an exception is thrown. For the resolution, use required=false.

16. What are the limitations of autowiring?

The limitations of autowiring are:

Overwrite: You still need to define dependencies with and configuration, which means you always have to override autoassembly.

Primitive data types: You cannot auto-assemble simple properties such as primitive data types, strings, and classes.

Fuzzy features: Automatic assembly is less accurate than explicit assembly, and explicit assembly is recommended if possible.

4. Spring annotations

1. What is the Java-based Spring annotation configuration? Give some examples of annotations

Java-based configuration allows you to do most of your Spring configuration with the help of a few Java annotations instead of XML files.

The @Configuration annotation, for example, is used to mark the definition of a class that can be used as a bean by the Spring IOC container.

Another example is the @bean annotation, which indicates that this method will return an object registered as a Bean in the Spring application context.

@Configuration public class StudentConfig { @Bean public StudentBean myStudent() { return new StudentBean(); }}Copy the code

2. How to start annotation assembly?

Annotation assembly is not turned on by default. To use annotation assembly, we must configure the
element in the Spring configuration file.

What is the difference between 3.@Component, @controller, @repository, and @service?

@Component: This marks the Java class as a bean. It is a common stereotype for any Spring management component. Spring’s component scanning mechanism can now pick them up and pull them into the application environment.

Controller: This marks a class as a Spring Web MVC Controller. Beans labeled with it are automatically imported into the IoC container.

@service: This annotation is a specialization of the component annotation. It does not provide any additional behavior for the @Component annotation. You can use @Service instead of @Component in the Service layer class because it specifies intents in a better way.

@Repository: This annotation is a specialization of the @Component annotation with similar utility and functionality. It provides additional benefits for daOs. It imports the DAO into the IoC container and makes unchecked exceptions eligible for translation into Spring DataAccessException.

4.@Required What are annotations for

This annotation indicates that the bean’s property must be set in the configuration, through a bean definition of explicit attribute values or by automatic assembly, if @ Required annotations bean attribute is not set, the container will throw BeanInitializationException. Example:

public class Employee { private String name; @Required public void setName(String name){ this.name=name; } public string getName(){ return name; }}Copy the code

5.@Autowired What are annotations for

By default, @AutoWired assembles injection by type, which by default requires that the dependent object must exist (you can set its required property to false). The @AutoWired annotation provides more fine-grained control over where and how autoassembly is done. It is used the same way as @required to modify setter methods, constructors, properties, or PN methods with arbitrary names and/or multiple parameters.

public class Employee { private String name; @Autowired public void setName(String name) { this.name=name; } public string getName(){ return name; }}Copy the code

The difference between 6.@Autowired and @resource

@autowired can be used for: constructors, member variables, Setter methods

The difference between @Autowired and @Resource

  • By default, @AutoWired assembles injection by type, which by default requires that the dependent object must exist (you can set its required property to false).

  • By default, @Resource assemples injection by name, and only by type if no bean matching the name can be found.

7.@Qualifier What are annotations for

When you create multiple beans of the same type and want to assemble only one of them using properties, you can use the @Qualifier annotation and @AutoWired to disambiguously specify which exact bean should be assembled.

8.@RequestMapping what’s the use of annotations?

The @RequestMapping annotation is used to map a specific HTTP request method to a specific class/method in the controller that will handle the corresponding request. This annotation applies at two levels:

  • Class level: URL of the mapping request
  • Method level: mapping URLS and HTTP request methods

5. Spring data access

1. Explain the object/relational mapping integration module

Spring provides ORM modules that allow us to use an object/relational mapping (ORM) tool on top of direct JDBC. Spring supports integration with major ORM frameworks such as Hiberate, JDO and iBATIS, JPA, TopLink, JDO, and OJB. Spring’s transaction management also supports all of the above ORM frameworks and JDBC.

2. How can I use JDBC more effectively in the Spring framework?

Using the Spring JDBC framework, the cost of resource management and error handling is reduced. So developers only need to write statements and queries to retrieve data from the data. JDBC can also be used more efficiently with the help of a template class provided by the Spring framework called JdbcTemplate

3. Explain the JDBC abstraction and DAO modules

By using THE JDBC abstraction and DAO module, the database code is kept simple and the problems caused by the incorrect shutdown of database resources can be avoided. It provides a unified exception access layer on the error information of various databases. It also leverages Spring’s AOP modules to provide transaction management services to objects in Spring applications.

4. What is the use of Spring DAO?

The Spring DAO (Data Access Object) makes it easier for data access technologies like JDBC, Hibernate, or JDO to work in a unified way. This makes it easy for users to switch between persistence technologies. It also allows you to write code without having to worry about catching exceptions that are different for each technology.

5. What classes exist in the Spring JDBC API?

JdbcTemplate

SimpleJdbcTemplate

NamedParameterJdbcTemplate

SimpleJdbcInsert

SimpleJdbcCall

6. The JdbcTemplate is what

The JdbcTemplate class provides convenient methods for converting database data to primitive data types or objects, executing written or callable database operation statements, and providing custom data error handling.

7. How to access Hibernate using Spring? What are the ways to access Hibernate using Spring?

There are two ways to access Hibernate in Spring:

  • Use Hibernate templates and callbacks for inversion of control
  • Extend Hibernateda Support and apply the AOP interceptor node

8. How to combine Spring and Hibernate with Hibernateda Support?

Call LocalSessionFactory with Spring’s SessionFactory. The integration process is divided into three steps:

  • Configure the Hibernate SessionFactory
  • Implement a DAO by inheriting HibernateDaoSupport
  • Assemble in an AOP supported transaction

9. What transaction management types are supported by Spring and how are Spring transactions implemented?

Spring supports two types of transaction management:

Programmatic transaction management: This means you manage transactions programmatically, giving you great flexibility but being difficult to maintain.

Declarative transaction management: This means you can separate business code from transaction management, and you only need to manage transactions with annotations and XML configuration.

10. Implementation methods and principles of Spring transactions

The essence of Spring transactions is the transaction support of the database. Without the transaction support of the database, Spring cannot provide transaction functionality. The real database layer commits and rolls back transactions through binlog or redo log.

11.Spring transaction propagation behavior

There are seven transactional propagation behaviors:

(1) PROPAGATION_REQUIRED: This is the most common, that is, if servicea. method calls Serviceb. method, if servicea. method opens a transaction, and then serviceB. method declares a transaction, The serviceB. method does not start a separate transaction, but executes its operations in a servicea. method transaction. An error reported by either ServiceA or ServiceB will cause the transaction to roll back. That’s the default behavior, and that’s what we need in general.

(2) PROPAGATION_SUPPORTS: If ServiceA.method opens a transaction, ServiceB adds itself to the ServiceA to run, and if ServiceA. Method does not open a transaction, ServiceB does not open a transaction

(3) PROPAGATION_MANDATORY: You must be called by a transaction-enabled method, otherwise an error is reported

Method forces itself to start a new transaction, PROPAGATION_REQUIRES_NEW: ServiceB. Method’s transaction is stuck, and it will continue after the ServiceB transaction completes. If ServiceB reports an error, ServiceB will not be affected. If ServiceB reports an error, ServiceA can optionally roll back or commit.

(5) PROPAGATION_NOT_SUPPORTED: ServiceB.method does not support transactions, a ServiceB.method transaction is suspended, PROPAGATION_NOT_SUPPORTED, and serviceB.Method executes a non-transactional transaction. The benefit is that ServiceB code errors do not cause ServiceA to roll back.

(6) PROPAGATION_NEVER: Cannot be called by a transaction, PROPAGATION_NEVER, Servicea. method opens a transaction, but ServiceB calls an error

(7) PROPAGATION_NESTED: Enables nested transactions, and ServiceB starts a subtransaction, and if rolled back, ServiceB rolls back to the save point where the subtransaction was started.

If you think back to the interview question, it is actually ServiceA. The 51 call to ServiceB failed. The first option is to set both transactions to PROPAGATION_REQUIRED, and all ServiceB operations are PROPAGATION_REQUIRED in a large transaction started by ServiceA. Any failure will cause the entire transaction to be rolled back. The second option is to set ServiceB to PROPAGATION_REQUIRES_NEW, so that each call to ServiceB is executed in a separate transaction. In this case, even if an error is reported on the 51st, only the operation on the 51st is rolled back. The previous 50 attempts were successful in a separate transaction. It doesn’t roll back.

“PROPAGATION_REQUIRES_NEW” is commonly used, and the effect is that the nested transaction is an independent transaction, PROPAGATION_REQUIRES_NEW, which commits or rolls back without any impact on the larger transaction, which can retrieve the exception thrown and decide whether to continue to commit or roll back the larger transaction.

12. Transaction isolation in Spring?

What is transaction isolation? Isolation means that when the concurrent transactions of multiple users access the same database, the transactions of one user should not be disturbed by the transactions of other users, and multiple concurrent transactions should be isolated from each other.

Let’s take an example.

Construction sentences:

CREATE TABLE `T`  (
  `id` int(11) NOT NULL.`name` varchar(255) NOT NULL,
  PRIMARY KEY (`id`))ENGINE = INNODB;
Copy the code

Data list:

id name
1 xiaohong
2 zhangsan
3 lisi

Case 1:

Transaction A, executed first, in uncommitted state:

insert into T values(4, wangwu);

Transaction B, later executed, also not committed:

select * from T;

If transaction B can read the record (4, wangwu), transaction A has an effect on transaction B. This effect is called “read dirty”, reading the records of uncommitted transactions.

Case 2:

Transaction A, first executed:

select * from T where id=1;

The result set is: 1, xiaohong

Transaction B, then executes, and commits:

update T set name=hzy where id=1;

commit;

Transaction A, execute the same query again:

select * from T where id=1;

The result set is: 1, hzy

This time it is the effect of committed transaction B on transaction A. This effect is called “unrepeatable reads”, where the same query within A transaction yields different results.

Case 3:

Transaction A, first executed:

select * from T where id>3;

The result set is NULL

Transaction B, then executes, and commits:

insert into T values(4, wangwu); commit;

Select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from (select * from)))));

insert into T values(4, hzy);

The result set is: Error: Duplicate key!

This time it is the effect of committed transaction B on transaction A. This effect is called A “phantom read”.

As you can see, concurrent transactions can lead to other transactions:

  • Read the dirty

  • Unrepeatable read

  • Phantom read

InnoDB implements four different transaction isolation levels:

  • Read Uncommitted
  • Read Committed (RC)
  • Repeated Read (RR)
  • Serialization (Serializable)

Different transaction isolation levels are a tradeoff between consistency and concurrency.

How are InnoDB’s four transaction isolation levels implemented?

InnoDB uses different Locking strategies to achieve different isolation levels.

(1) Read Uncommitted

At this transaction isolation level, select statements are not locked.

In this case, inconsistent data may be read, that is, read dirty. This is the isolation level with the highest concurrency and lowest consistency.

(2) Serializable

At this transaction isolation level, all SELECT statements are implicitly converted to SELECT… in share mode.

This can result in any SELECT reading rows being blocked if uncommitted transactions are modifying them.

This is the isolation level with the best consistency but the worst concurrency. In the scenario of large data volume and high concurrency on the Internet, the above two isolation levels will hardly be used.

(3) Repeated Read (RR) This is InnoDB’s default isolation level, in RR:

① Common select uses Snapshot read, which is a Consistent Nonlocking read, and MVCC is used to implement it.

Select (select… in share mode / select … For update, update, delete, etc., their locks depend on whether they use unique search conditions on unique indexes. Or range-type search condition:

  • A unique query condition on a unique index uses a record lock instead of locking the interval between records, i.e., a gap lock and a next-key lock are not used.
  • Range query conditions use gap and near-key locks to lock ranges between index records, avoid inserting records between ranges, avoid phantom row records, and avoid non-repeatable reads

Read Committed (RC) This is the most commonly used isolation level on the Internet, under RC:

(1) Common read is snapshot read.

(2) Select, UPDATE, delete, and other locked statements, except for foreign-key constraint checking and duplicate-key checking. All other times only log locks are used;

At this point, the insertion of other transactions can still be performed, which may result in the phantom record being read.

13. What are the advantages of the Spring framework’s transaction management?

  • Provides an unchanging programming pattern for different transaction apis such as JTA, JDBC, Hibernate, JPA and JDO.
  • Provides a simple SET of apis for programmatic transaction management rather than complex transaction apis
  • Support for declarative transaction management.
  • Integrates well with Spring’s various data access abstraction layers.

14. What type of transaction management do you prefer?

Most users of the Spring framework opt for declarative transaction management because it has the least impact on application code and is therefore more in line with the idea of a lightweight container with no intrusion. Declarative transaction management is superior to programmatic transaction management, although it is less flexible than programmatic transaction management, which allows you to control transactions through code. The only downside is that the maximum granularity applies only at the method level, not at the code block level like programmatic transactions.

Spring AOP

1. What is AOP?

OOP is object-oriented program design, talked about OOP, we have to know about the POP process oriented programming, it was based on the function of the center for thinking and organization of a programming mode, emphasizes the system of data processing and processing process, namely pay attention to the implementation of functional, achieved good, while the OOP pay attention to packaging, Emphasizing the concept of wholeness, centering on the object, distinguishing the internal organization of the object from the external environment. I saw a good explanation earlier, and the blogger drew it as a picture like this:Here we are compared the program design for the layout of the house, a house layout, need to all sorts of function of furniture and sanitary ware (similar to method), such as toilet, bathtub, gas stove, bed, table, etc., to pay more attention to process oriented programming is a function of the implementation of the (i.e., the realization of the function method), it is good effect in line with expectations, Therefore, process-oriented programming would prefer to set up the structure in Figure 1, and the various functions would be implemented and the house would be habitable. But for the object-oriented program design is unbearable, in such a setting give house puts scattered between all kinds of furniture and sanitary ware and greatly increase the risk of exposure, each all kinds of smells mixed each other, obviously is very bad, so in order to set the layout of the building to the more elegant, object-oriented program design and use the position of the figure 2, For object-oriented programming such set advantage is obvious, every room in the house have their own names and the corresponding function (in the Java programming generally called the room like this class, each class represents a room of abstract body), such as toilet is size bath solution and dressing, is rest in the bedroom, the kitchen is cooking, Every small room do their job without time exposed to the world of internal structure, the whole room structure is clear, the only need to know the room and use the functions can be provided in the room (method invocation), at the same time also more conducive to later expanded, which room, after all, you need to add the function, its scope has a limit, This makes responsibilities clearer (the principle of single responsibility). The emergence of OOP to POP does exist a lot of disruptive, but does not say POP has no value, after all, is the product of different times, from methodology, prefer to process oriented and object oriented as the two aspects of things – local and whole (you have to notice the local and overall is relative), so in practice, Both methods are equally important. After understanding the characteristics of OOP and POP, we look at OOP applications in the Java programming process. In the Java programming process, we almost enjoy the benefits brought by OOP design ideas, so that in this world where everything is an object and everyone is equal, we are in a carnival. OOP, however, does adhere to its purpose of putting data and actions on it together as an interdependent, indivisible whole, which is nicely named: Object, using the definitions for the same type of object classification, abstract, it is concluded that common features, thus formed the class, the class is a class in Java program design, because the class (object), the basic concept of the existence of the real world affairs (such as in front of different small room) so much closer to people’s understanding of objective things, At the same time, the data and method (algorithm) encapsulated in a class (object), which is more conducive to data security, under normal circumstances, attributes and algorithms only belong to a separate class, so that the program design is simpler, but also easier to maintain. Based on this theory, in the actual software development, the whole software system is actually composed of a series of interdependent objects, and these objects are also abstracted classes. I believe you have some experience in the actual development (this document assumes that readers have object-oriented development ideas including encapsulation, inheritance, polymorphic knowledge). But as the software gets bigger and the application gets upgraded, OOP slowly starts to show some problems. There’s no need to know about them now.

Class A:

public class A {
    public void executeA(a){
        // Other service operations are omitted......
        recordLog();
    }

    public void recordLog(a){
        / /... Record logs and report them to the log system}}Copy the code

Class B:

public class B {
    public void executeB(a){
        // Other service operations are omitted......
        recordLog();
    }

    public void recordLog(a){
        / /... Record logs and report them to the log system}}Copy the code

Class C:

public class C {
    public void executeC(a){
        // Other service operations are omitted......
        recordLog();
    }

    public void recordLog(a){
        / /... Record logs and report them to the log system}}Copy the code

Suppose there are three classes A, B, and C, and they need to log their method access, and there are various recordLog methods in the code to log and report. It is probably impossible for engineers today to write such bad code, but OOP writing is allowed. And there was a lot of this code at the beginning of OOP, and it wasn’t until engineers were digging around for the recordLog that they decided to fix it. In order to solve the problem of too much redundant code between programs, engineers started using the following code.

// Generic parent class
public class Dparent {
    public void commond(a){
        // Common code}}/ / A Dparent inheritance
public class A extends Dparent {
    public void executeA(a){
        // Other service operations are omitted......commond(); }}/ / B Dparent inheritance
public class B extends Dparent{
    public void executeB(a){
        // Other service operations are omitted......commond(); }}/ / C Dparent inheritance
public class C extends Dparent{
    public void executeC(a){
        // Other service operations are omitted......commond(); }}Copy the code

Obviously, code redundancy has also been resolved, and this method of extracting common code through inheritance is also known as vertical scaling, as opposed to horizontal scaling (don’t be too quick to understand now, it will be everywhere in the analysis that follows). In fact, with these two solutions, the problem of code redundancy in most business scenarios is actually solved, as shown in the following figureHowever, as the software development system becomes more and more complex, engineers realize that traditional OOP programs often exhibit some unnatural phenomena. The core business is always mixed with some unrelated special business, such as logging, permission verification, transaction control, performance detection, error message detection, etc. These special businesses can be said to have no fundamental relationship with the core business and the core business does not care about them. For example, in the user management module, the module itself only cares about the business information processing related to the user, and the other businesses can be completely ignored. Let’s look at a simple example to help understand this problem

public interface IUserService {

    void saveUser(a);

    void deleteUser(a);

    void findAllUser(a);
}
/ / implementation class
public class UserServiceImpl implements IUserService {

    // Core data member

    // Log operation object

    // Permission managed objects

    // Transaction control object

    @Override
    public void saveUser(a) {

        // Permission validation (assuming permission validation is dropped here)

        // Transaction control

        // Log operations

        // Perform Dao layer operations
        userDao.saveUser();

    }

    @Override
    public void deleteUser(a) {}@Override
    public void findAllUser(a) {}}Copy the code

We noticed that some problems in the code above, permissions, logging, transactions are not user management core business, which means the user management module in addition to deal with its core business, also need to deal with authority, logging, transaction wait for these assorted the outside of the relevant business operations, and the peripheral operation will also appear in other business modules, This leads to the following problems

  • Code clutter: The core business module may have to take care of other unrelated business peripheral operations that may clutter the code for the core operation and affect the core module when significant changes are made to the peripheral module, which is obviously unreasonable.
  • Code dispersion and redundancy: The same functional code can be seen almost everywhere in other modules, resulting in high code dispersion and redundancy.
  • Low code quality Difficult to expand: The core business code cannot be focused on because the irrelevant business code is mixed together. When similar unrelated business extension is carried out, the code of the core business will be directly involved, resulting in low extensibility.

Obviously, the two solutions analyzed above are no longer available, so what is the solution? In fact we know such as log, permissions, transactions, such as performance monitoring business covers almost all of the core module, if these special business code directly into the core business of the module code will cause the above problem, the engineers more hope these modules can realize the hotplug features without code invasion of peripheral to the core module, Such maintenance and extension in the future also will have a better performance, assuming that now we have logs, permissions, transaction, performance monitoring, and other peripheral business as a separate concern (can also be interpreted as a separate module), each focus can in time to need them is applied in time and need not integrated into the core module in advance, this form is below:Can be seen from the figure, each separation of concerns and core business module as a separate function, crosscutting several core business modules, such doing is obvious, the benefits of each function code is no longer alone into the core business class code, namely the core modules focus on relevant business, when you need to peripheral business (log, permissions, Performance monitoring and transaction control), the peripheral business would automatically through a special technology is applied to the core module, these concerns have a special name, called “crosscutting concerns,” above is also very good showing this concept, the level of abstraction technology also called AOP (aspect oriented programming), as is shown above, crosscutting core modules of the whole face, So the concept of AOP emerged, and the so-called special technology is also oriented to the implementation of faceted programming technology, AOP implementation technology has a variety of, with Java seamless docking is a technology called AspectJ. So how does this aspect technology (AspectJ) apply to Java? There is no need to worry or understand AspectJ completely, and this post will not do so. We will cover AspectJ in a very brief way that will provide a good foundation for understanding AOP in Spring. (Spring AOP and AspectJ are not exactly implemented in principle, but are functionally similar. This will be discussed later), after all, AOP’s main functionality is already implemented in Spring, so we can simply use the AOP functionality provided in Spring for development, unless we want to use AspectJ’s other capabilities alone. It is also important to note that the advent of AOP does solve the problem of separating peripheral business code from core business code, but it does not replace OOP. Whereas OOP is about modularizing coding problems, AOP is about unifying the management of a class of problems involving many modules. So it’s no surprise that AOP and OOP exist together in real development, as we’ll see later. Ok, can’t wait, let’s start learning about AspectJ like the Gods.

What is the difference between Spring AOP and AspectJ? What are the implementations of AOP?

The key of AOP implementation lies in the proxy mode. AOP proxy is mainly divided into static proxy and dynamic proxy. Static proxies are represented by AspectJ; Dynamic proxies are represented by Spring AOP.

(1) AspectJ is an enhancement to static proxies. Static proxies are the AOP framework that generates AOP proxy classes at compile time, so it is also called compile-time enhancement. It will weave AspectJ(aspects) into Java bytecode at compile time and run as enhanced AOP objects.

(2) Spring AOP use dynamic proxy, the so-called dynamic proxy is an AOP framework won’t go to modify the bytecode, but each time to run in memory temporarily for the method to generate a AOP object, the object of AOP method contains all of the target object, and in particular the tangent point of enhancement processing, and the correction method of the original object.

3. The difference between JDK dynamic proxy and CGLIB dynamic proxy

There are two main types of dynamic proxies in Spring AOP, JDK dynamic proxies and CGLIB dynamic proxies:

  • JDK dynamic proxies only provide proxies for interfaces, not classes. The core InvocationHandler interface and Proxy class, InvocationHandler invokes code in the target class through the invoke() method reflection, dynamically weaving crosscutting logic and business together; Next, the Proxy uses InvocationHandler to dynamically create an instance that conforms to an interface, generating a Proxy object for the target class.

  • If the proxy class does not implement the InvocationHandler interface, Spring AOP will choose to use CGLIB to dynamically proxy the target class. CGLIB (Code Generation Library) is a Code Generation Library that can dynamically generate a subclass object of a specified class at runtime, and override specific methods and add enhanced Code to implement AOP. CGLIB is dynamically proxied by inheritance, so if a class is marked final, it cannot be dynamically proxied using CGLIB.

Static proxies differ from dynamic proxies in the timing of the generation of AOP proxy objects. AspectJ’s approach to static proxies has better performance, but AspectJ requires a specific compiler for processing, whereas Spring AOP does not.

Invoke (Object Proxy,Method Method,Object[] args) of InvocationHandler: Proxy is the final generated proxy instance; Method is a specific method of the proxied target instance; Args is a concrete entry to a method of the propped target instance that is used when the method reflection is invoked.

4. How to understand proxies in Spring?

The objects created after Advice is applied to the target object are called proxies. In the case of the client object, the target object and the proxy object are identical.

Advice + Target Object = Proxy

5. Explain some terms from Spring AOP

(1) Aspect: Aspect is the combination of notification and pointcut. Together, notifications and pointcuts define the entire content of the aspect. In Spring AOP, aspects can be implemented using generic classes (pattern-based styles) or in ordinary classes with @AspectJ annotations.

(2) Join point: refers to method. In Spring AOP, a Join point always represents the execution of a method. Applications may have thousands of times to apply notifications. These moments are called connection points. A join point is a point at which an aspect can be inserted during application execution. This point can be when a method is called, when an exception is thrown, or even when a field is modified. These points can be used by aspect code to plug into the normal flow of your application and add new behavior.

(3) Advice: In AOP terminology, aspect work is called Advice.

(4) Pointcut: The definition of the Pointcut matches one or more join points into which the advice is woven. We usually specify these pointcuts using either explicit class and method names, or regular expressions that define matching class and method names.

Introduction: Introduction allows us to add new methods or properties to existing classes.

(6) Target Object: an Object that is advised by one or more aspects. It is usually a proxy object. Others call it an adviced object. Since Spring AOP is implemented through a runtime proxy, this object is always a proxied object.

Weaving: Weaving is the process of applying a slice to a target object and creating a new proxy object. How many points can be woven into the life cycle of the target object:

  • Compile time: The aspect is woven in when the target class is compiled. AspectJ’s weaving compiler weaves facets in this way.
  • Class loading time: The aspect is woven when the target class is loaded into the JVM. Special class loaders are required that enhance the bytecode of the target class before it is introduced into the application. AspectJ5’s load-time weaving supports weaving into facets in this way.
  • Run-time: Facets are woven in at some point during the application run. Typically, the AOP container dynamically creates a proxy object for the target object when weaving into the cut. SpringAOP is woven into the facets in this way.

6.Spring notifies objects at run time

Spring weaves the aspects into spring-managed beans at run time by wrapping them in a proxy class. The proxy encapsulates the target class, intercepts the invocation of the notified method, and forwards the invocation to the actual target bean. When the proxy intercepts a method call, the aspect logic is performed before calling the target bean method.

Spring does not create a proxy object until the bean that needs to be proxied is applied. If you use the ApplicationContext, Spring creates the proxied object only when the ApplicationContext loads all the beans from the BeanFactory. Since the Spring runtime only creates proxy objects, we don’t need a special compiler to weave into SpringAOP’s facets.

7.Spring only supports method level join points

Because Spring is based on dynamic proxies, Spring only supports method join points. Spring lacks support for field join points, and it does not support constructor join points. Join point interception capabilities outside of methods that we can complement with aspects.

8. What is the difference between concerns and crosscutting concerns in Spring AOP? The difference between Concern and cross-cutting Concern in Spring AOP

Concern is the behavior of a module in an application. A concern may be defined as a function we want to implement.

A cross-cutting concern is a concern that is used by and affects the entire application, such as logging, security and data transfer, and is required by almost every module of the application. So these are crosscutting concerns.

9. What are the types of Spring notifications?

In AOP terminology, aspect work is called advice and is actually a piece of code that is triggered by the SpringAOP framework when a program executes.

The Spring aspect can apply five types of notification: 1. Before: the notification function is called Before the target method is called; 2. Post-notification (After) : Call notification After the target method has completed without caring what the output of the method is; 3. After-returning: Notifications are called After successful execution of the target method; 4. After-throwing: Calls the notification After the target method throws an exception; 5. Surround advice (Around) : Advice wraps the notified method, performing custom behavior before and after the notified method invocation.

The order of execution of different advice in the same aspect:

① Execution order without exception:

Around before advice before advice target method Executes around after advice after advice afterReturning

(2) The order of execution in abnormal cases:

Around before advice before advice Target method Executes around after advice after advice afterThrowing: an exception occurs Java. Lang. RuntimeException: exception occurs

10. What is a Aspect?

An aspect consists of pointcount and advice, and a section is a combination of advice and pointcuts. It includes both the definition of crosscutting logic and the definition of join points. Spring AOP is the framework responsible for implementing the aspect, weaving the crosscutting logic defined by the aspect into the join points specified by the aspect. AOP’s focus is on how to enhance the join points of the woven target objects, which consists of two tasks:

  • How do I locate a specific JoinPoint using pointcut and advice
  • How to write aspect code in advice.

It is easy to think of a class annotated with @aspect as an Aspect.

11. Explain the implementation of aspects based on XML Schema

In this case, the facets are implemented by regular classes as well as XML-based configurations.

12. Explain annotation-based aspect implementation

In this case (based on the @AspectJ implementation), the style of aspect declarations involved is consistent with normal Java classes with Java5 annotations.

13. How many different types of automatic agents are there?

BeanNameAutoProxyCreator

DefaultAdvisorAutoProxyCreator

Metadata autoproxying