This is the 10th day of my participation in the Gwen Challenge in November. See details of the event: The Last Gwen Challenge in 2021 “.

👨🎓 author: Java Academic Conference

🏦 Storage: Github, Gitee

✏️ blogs: CSDN, Nuggets, InfoQ, Cloud + Community

💌 public account: Java Academic Party

🚫 special statement: the original is not easy, shall not be reproduced or copied without authorization, if you need to reproduce can contact xiaobian authorization.

🙏 Copyright notice: part of the text or pictures in the article come from the Internet and Baidu Encyclopedia, if there is infringement, please contact xiaobian as soon as possible. Wechat search public Java academic party contact xiaobian.

☠️ Daily toxic chicken soup: smile embrace every day, be like sunflower warm woman.

👋 Hello! I’m your old friend Java Academic Party. Recently xiaobian in the whole Spring family bucket notes, notes will be issued regularly every day, like the big guys welcome to collect points like attention yo. Xiaobian will share it every day. The Spring framework is not limited to server-side development. Any Java application can benefit from Spring in terms of simplicity, testability, and loose coupling. The Spring framework is also a super glue platform, providing the ability to glue other technologies and frameworks in addition to its own capabilities.

Chapter 1 Spring transactions

Before we get to business, let’s talk about one of the things you do most often in your daily life: withdraw money. For example, if you go to the ATM to withdraw 1000 yuan, there are generally two steps: first input the password amount, the bank card deduct 1000 yuan; And then the ATM pays out 1,000 yuan. These two steps must be either performed or not performed. If 1,000 yuan is deducted from your bank card but the ATM payment fails, you will lose 1,000 yuan. If the bank card fails to withdraw the money but the ATM pays out 1000 yuan, the bank will lose 1000 yuan. So, if one step succeeds and the other fails, it’s bad for both of us, and it’s great for both of us if after either step fails, the entire withdrawal process can be rolled back, that is, completely cancelled. Transactions are designed to solve similar problems. A transaction is a sequence of actions that, taken together, constitute a complete unit of work. These actions must all be completed, and if one fails, the transaction rolls back to its original state as if nothing had happened.

Transaction management is an essential technique in enterprise application development to ensure data integrity and consistency.

Transactions have four properties: ACID

  • Atomicity: A transaction is an atomic operation consisting of a series of actions. The atomicity of the transaction ensures that the action either completes completely or does not work at all.

  • Consistency: Once a transaction has completed (whether successfully or failed), the system must ensure that the business it models is in a consistent state and not partially complete and partially failed. Data in the real world should not be corrupted.

  • Isolation: There may be many transactions processing the same data at the same time, so each transaction should be isolated from the others to prevent data corruption.

  • Durability: Once a transaction completes, its results should not be affected no matter what system errors occur so they can recover from any system crashes. Typically, the results of a transaction are written to persistent storage.

The core interface

1.1 Analysis of transactions

Spring transactions are performed on the same database and operate on different tables in the same database.

What is a transaction:

  • The term transaction is introduced in mysql. A transaction is a collection of MULTIPLE SQL statements. It could be delete, UPDATE, INSERT, etc. We want these SQL statements to succeed or fail at the same time. Like the money transfer system. The execution of these SQL statements is consistent and executed as a unit.

When are transactions used

  • When multiple tables are required to implement a function in a project, or for insert, UPDATE, or DELETE statements from multiple SQL statements. To complete a function, ensure that all statements succeed or fail simultaneously. A single SQL statement cannot be executed successfully.

When you write a program in Java code that controls a transaction, where do you put the transaction?

  • In the business methods of the Service class, because a function (method) in the Service class may require methods in multiple DAOs to complete the business, and daOs execute SQL statements, the methods called by these DAOs can be regarded as a business

Usually use JDBC access database, mybatis access database is how to handle business.

  • JDBC access database: handling transactions (Connection Conn; conn.commit(); conn.rollback();)
  • Sqlsession.mit (); SqlSession. The rollback ();
  • Session.mit (); The Session. The rollback ())

What are the shortcomings of the above operations

  1. Different databases need different transaction objects, different methods, need to understand the principle of different database transaction technology
  2. Master the business logic of transaction processing in various databases. When to commit a transaction and when to roll back a transaction.
  3. The Chinese approach to business is different.

Address deficiencies in transaction processing

  • Use the Spring framework to unify transaction processing

1.2 Spring’s unified way of handling transactions

  • Transactions were originally a database concept, at the Dao layer. In general, however, transactions need to be promoted to the business layer, the Service layer. This is done in order to be able to use the transactional nature to manage specific businesses.

Transaction management is typically implemented in Spring in one of two ways:

  1. Programmatic Transaction Management: Use Spring’s transaction annotations to manage transactions
  2. Declarative transaction Management: Use AspectJ’s AOP configuration to manage transactions

Spring provides a unified transaction model that can be used in a unified way to complete transactions for many different database access technologies.

  • Using the transaction processing mechanism of Spring, you can complete the transaction processing of mybatis accessing the database.
  • Using The transaction processing mechanism of Spring, you can complete the transaction processing of Hibernate accessing the database.

1.3 Spring Transaction Management API

  • Spring uses two transaction-related interfaces for transaction management.

(1) Transaction manager interface (emphasis)

  • The transaction manager is PlatformTransactionManager interface object. It is mainly used to complete the transaction commit, rollback, and obtain the transaction status information.

The transaction manager is PlatformTransactionManager interface object. Two commonly used implementation classes:

  • DataSourceTransactionManager: using JDBC or when MyBatis for database operations.
  • HibernateTransactionManager: use when using Hibernate for persistent data.

Spring rollback (understand)

  • Spring transactions are rolled back when runtime exceptions and errors occur and committed when checked (compiled) exceptions occur by default. However, for checked exceptions, the programmer can manually set the rollback method.

Review errors and exceptions

  • The Throwable class is the superclass for all errors or exceptions in the Java language. Only if the object is an instance of this class (or one of its subclasses) can it be thrown by a Java virtual machine or Java throw statement.
  • An Error is an unhandled Error that occurs during the execution of a program, such as OutOfMemoryError, ThreadDeath, NoSuchMethodError, etc. When these errors occur, the program cannot handle them (catch or throw them), and the JVM generally terminates the thread.
  • Another type of error that occurs when a program is compiled and run is called an exception, which is the JVM’s way of notifying the programmer. In this way, you let the programmer know that an error has occurred or is likely to occur and ask the programmer to deal with it.

Exceptions are divided into runtime exceptions and checked exceptions.

  • Runtime exceptions, which are RuntimeException classes or subclasses, are exceptions that occur only at runtime. Such as, NullPointerException, ArrayIndexOutOfBoundsException, IllegalArgumentException all belong to a runtime exception. These exceptions are thrown by the JVM and are not required to be handled (caught or thrown) at compile time. However, run-time exceptions can be avoided if the code is written carefully and the program is robust.
  • Checked exceptions, also known as compile-time exceptions, are exceptions that must be caught or thrown when the code is written. If they are not handled, they cannot be compiled. Such as SQLException, ClassNotFoundException, IOException and so on are checked exceptions.
  • Exceptions other than RuntimeException and its subclasses are checked exceptions. Of course, user-defined exceptions, which are subclasses of user-defined Exception, are also checked exceptions. When a programmer defines an exception, he defines a checked exception as long as he does not explicitly declare a subclass of RuntimeException.

(2) Transaction definition interface

  • Three constants related to transaction description are defined in the TransactionDefinition interface: transaction isolation level, transaction propagation behavior, transaction default timeout, and operations on them

Defines five transaction isolation level constants (master)

These constants all start with ISOLATION_. Such as ISOLATION_XXX.

Trained: Transaction isolation level. MySql defaults to REPEATABLE_READ; Oracle defaults to READ_COMMITTED.

READ_UNCOMMITTED: Read uncommitted. No concurrency issues were resolved.

Prepared READ_COMMITTED: Read committed. Solve dirty read, there is no repeat read and unreal read.

REPEATABLE_READ: repeatable read. Solve dirty read, unrepeatable read, phantom read.

Preparation for SERIALIZABLE: serialization. There is no concurrency problem.

Defines seven transaction propagation behavior constants (master)

  • Transaction propagation behavior refers to the maintenance of a transaction during execution when methods in different transactions call each other. For example, if method doSome() in transaction A calls method doOther() in transaction B, the maintenance of the transaction during the execution of the call is called transaction propagation behavior. The transaction propagation behavior is added to the method.

Transaction propagation behavior constants begin with PROPAGATION_, PROPAGATION_XXX.

  • PROPAGATION_REQUIRED
  • PROPAGATION_REQUIRES_NEW
  • PROPAGATION_SUPPORTS

Focus on the first three

  • PROPAGATION_MANDATORY
  • PROPAGATION_NESTED
  • PROPAGATION_NEVER
  • PROPAGATION_NOT_SUPPORTED

PROPAGATION_REQUIRED:

  • The specified method must be executed within a transaction. If a transaction exists, join the current transaction. If there is no current transaction, create a new transaction. This propagation behavior is the most common choice and is Spring’s default transaction propagation behavior.
  • If the propagation behavior is added to the doOther() method. If the doSome() method is run inside the transaction when the doOther() method is called, the execution of the doOther() method is added to the transaction. If the doSome() method is not executed within a transaction when the doOther() method is called, the doOther() method creates a transaction and executes within it.

PROPAGATION_SUPPORTS

  • The specified method supports the current transaction, but can be executed nontransactionally if there is no current transaction.

PROPAGATION_REQUIRES_NEW

  • Always create a new transaction and, if one exists, suspend the current transaction until the new transaction completes

Defines the default transaction timeout period

  • The constant TIMEOUT_DEFAULT defines the default timeout at the bottom of the transaction, the execution time of the SQL statement.
  • Note that there are many conditions under which a transaction timeout takes effect, and the calculation point of the timeout time is complex. Therefore, the default value is generally used.

Summarize Spring transactions

  1. Transactions are managed by transaction management and its implementation classes

  2. A unified model of Spring transactions

    1) Specify the transaction manager implementation class to use, using

    2) Specify which classes and methods need to be added to the transaction functionality.

    3) Specify the isolation level, propagation behavior, timeout, and so on required by the method

  3. We need to tell Spring about the class information in the project, the name of the method, and the transaction propagation behavior of the method.

1.4 There are two ways to manage transactions using Spring’s approach

  • Declarative: The AspectJ framework implementation is used.

Using the aspectJ framework requires adding aspectJ dependencies to pom.xml

<dependency> <groupId>org.springframework</groupId> <artifactId>spring-aspects</artifactId> < version > 5.2.5. RELEASE < / version > < / dependency >Copy the code

Use the following code in spring’s main configuration file (applicationContext.xml)

<! Use Spring's AOP approach to transaction processing --> <! - 1. Declare the transaction manager - > < bean id = "transactionManager" class = ". Org. Springframework. JDBC datasource. DataSourceTransactionManager "> <! < dataSource ="dataSource" /> </ dataSource > <! Turn on the transaction annotation driver and tell Spring to use annotations to manage transactions and create proxy objects --> <! Note: the annotation-driven used here must be under the TX class. Transaction-manager: id value representing the transaction manager --> <tx:annotation-driven Transaction manager="transactionManager"/>Copy the code
  • Annotated: Implemented using the AOP approach that comes with annotation Spring.
<! - 1. The statement transaction management object - > < bean id = "transactionManager" class = ". Org. Springframework. JDBC datasource. DataSourceTransactionManager ">  <property name="dataSource" ref="myDataSource"/> </bean> <! Tx :advice ID ="myAdvice" transaction-manager="transactionManager"> <! - tx: attributes: Is a child tag of advice, <tx: Method Name ="buy" Propagation ="REQUIRED" Isolation ="DEFAULT" < TX: Method name=" Buy "Propagation ="REQUIRED" Isolation ="DEFAULT" rollback-for="java.lang.NullPointerException,com.yunbocheng.error.RangeExceeds"/> <! <tx:method name="add*" Propagation ="REQUIRES_NEW"/> <! <tx:method name="modify*" /> <! <tx:method name="*" Read-only ="true" Propagation ="SUPPORTS" /> </tx:attributes> </tx:advice> <! < AOP :pointcut id="servicePt" expression="execution(* *.. service.. *. * (..) )"/> <aop:advisor advice-ref="myAdvice" pointcut-ref="servicePt"/> </aop:config>Copy the code

1.5 Manage transactions using Spring’s transaction annotations (Master)

The @Transactional annotation enables transaction management by weaving transactions into corresponding public methods.

Note that @Transactional, when used on methods, can only be used on public methods. For other non-public methods, if annotated @Transactional, Spring does not report an error but does not weave the specified transaction into the method. Because Spring ignores @Transaction annotations on all non-public methods.

If the @Transaction annotation is on a class, it means that all methods on that class will be woven into a Transaction at execution time.

If the @Transaction annotation is on a method, it means that the method must be public to weave into a Transaction at execution time.

All the optional attributes of @Transactional look like this:

Trained propagation: Used to set transaction propagation attributes. This attribute is of type Propagation enumeration and the default value is Propagation.REQUIRED.

Isolation: Used to set the isolation level of a transaction. This property is of type Isolation enumeration and the DEFAULT value is Isolation.default.

Preparing readOnly: Used to set whether the operation of this method on the database is read-only. This property is Boolean and the default value is false.

Locality: Used to set the timeout period between this operation and the database connection. The unit is second and the type is int. The default value is -1, that is, there is no time limit.

RollbackFor: Specifies the exception class that needs to be rolled back. The type is Class[] and the default value is an empty array. Of course, if you only have one exception class, you don’t have to use arrays.

RollbackForClassName: Specifies the name of the exception class to be rolled back. The type is String[] and the default value is an empty array. Of course, if you only have one exception class, you don’t have to use arrays.

NoRollbackFor: Specifies an exception class that does not need to be rolled back. The type is Class[] and the default value is an empty array. Of course, if you only have one exception class, you don’t have to use arrays.

NoRollbackForClassName: Specifies the name of an exception class that does not need to be rolled back. The type is String[] and the default value is an empty array. Of course, if you only have one exception class, you don’t have to use arrays.

Chapter 2 Spring and the Web

  • To use the Spring framework in a Web project, you first have to solve the problem of getting the Spring container in the Web layer (in this case, servlets). Once you get the Spring container at the Web layer, you can get the Service object from the container.

2.1 Problems with Using Spring for Web Projects (Understanding)

  • Step 1: Create a New Maven Project

Type maven archetype – webapp

  • *Step 2: Copy the code, configuration file, jar

Copy the following from the Spring-Mybatis project into the current project:

(1) All codes of Service layer and Dao layer

(2) Configuration files applicationContext. XML and jdbc.properties, mybatis

(3) the pom. XML

(4) Add servlet, JSP dependency

<! Javax. servlet</groupId> <artifactId>javax.servlet- API </artifactId> The < version > 3.1.0 < / version > < scope > provided < / scope > < / dependency > <! Javax.servlet. JSP </groupId> <artifactId>jsp-api</artifactId> < version > 2.2.1 - b03 < / version > < scope > provided < / scope > < / dependency >Copy the code
  • Step 3: Define the Index page

Step 4: Define the RegisterServlet (key code)

Step 5: Define the Success page

Step 6: Web.xml registers the Servlet

Step 7: Run result analysis

  • After the form is submitted and you jump to success.jsp, refresh the page several times and look at the background output. Find that each time the page is refreshed, a new Spring container is created. That is, each time a request is submitted, a new Spring container is created. For an application, you only need a Spring container. Therefore, putting the creation statement of the Spring container in the doGet() or doPost() methods of the Servlet is problematic.

  • At this point, consider placing the creation of the Spring container at Servlet initialization time, when the init() method is executed. Moreover, servlets are singleton multithreaded, that is, a business has only one Servlet instance, and all users executing that business execute that single Servlet instance. In this way, the Spring container is unique.
  • However, a Servlet is a business and a Servlet instance, that is, there is only one LoginServlet, but there are also StudentServlet, TeacherServlet, etc. Each business will have a Servlet, will execute its init() method, and will create a Spring container. In this way, the Spring container is not unique again.

2.2 Using Spring’s ContextLoaderListener

  • Example: SpringWeb-2 project (modified from the Spring-Web project)
  • A ServletContext object is unique to a Web application, there is only one ServletContext object for a Web application, and that object is initialized when the Web application is loaded. Placing the creation time of the Spring container at the time of ServletContext initialization ensures that the creation of the Spring container is performed only once, thus ensuring the uniqueness of the Spring container throughout the application.
  • Once the Spring container is created, it should be readily accessible throughout the application lifecycle. That is, the Spring container should be global. Properties that you put into the ServletContext object are global to the application. So, by putting the created Spring container into the space of the ServletContext as a property, the global nature of the Spring container is guaranteed.
  • All of this work is wrapped up in the following Spring Jar API: Spring-Web-5.2.5.release

Step 1: Maven relies on POM.xml

< the dependency > < groupId > org. Springframework < / groupId > < artifactId > spring - web < / artifactId > < version > 5.2.5. RELEASE < / version >  </dependency>Copy the code

Step 2: Register a listener ContextLoaderListener

  • To create a Spring container when the ServletContext is first initiated, you need to have the ServletContextListener listen on the ServletContext. Register the listener in web.xml.

  • Spring defines an implementation class for this listener interface, ContextLoaderListener, that does two important things: create a container object and place it in the space of the ServletContext.
  • Open the ContextLoaderListener source. See there are four methods, two constructor methods, one initialization method, and one destruction method.

So, the more important of the four methods is probably contextInitialized(), the context initialization method.

  • Tracking initWebApplicationContext () method, you can see, in which to create a container object.

And, will create good container objects in space in the ServletContext, the key to a constant: WebApplicationContext. ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE.

Step 3: Specify the location of the Spring configuration file < context-parm >

  • ContextLoaderListener When creating the Spring container, the Spring configuration file needs to be loaded. The Spring configuration file location and name for its default: WEB – INF/applicationContext. XML. However, this configuration file is typically placed in the project’s classpath, SRC, so you need to specify the location and name of the Spring configuration file in web.xml.

  • From the source of the parent class of the listener, ContextLoaderListener, you can see the name of contextConfigLocation, the configuration file location parameter it is reading.

Step 4: Get the Spring container object

There are two common ways to get container objects in servlets:

(1) Get it directly from the ServletContext

From the source analysis of ContextLoaderListener, Container object in put the key in the ServletContext for WebApplicationContext. ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE. Therefore, the container object can be retrieved with the specified key directly through the getAttribute() method of the ServletContext.

(2) through WebApplicationContextUtils access

  • Utility class WebApplicationContextUtils has a special method is used to obtain the Spring container from ServletContext object: getRequiredWebApplicationContext(ServletContext sc)

Call the spring-provided method to get the container object:

Summary: After refreshing the Success page, you can see that the Spring container used in the code is the same object, regardless of which method is used to obtain the container object.

That’s all we have to say about Spring, and I’ll bring you something new tomorrow, SpringMVC.

For the source code of the above project, click planet for free accessplanet(Github address) If you don’t have a Github partner. You can follow my wechat official account:Java academic lie prone, send Spring, free to send you the project source code, the code is personally tested by xiaobian, absolutely reliable. It’s free to use.