In addition to Weibo, there is also WeChat
Please pay attention
WeChat public account
Shulou
2025-01-18 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >
Share
Shulou(Shulou.com)06/03 Report--
This article mainly explains the "holographic perspective to see the Dao layer of the two traditional ways and agent ways", the article explains the content is simple and clear, easy to learn and understand, the following please follow the editor's ideas slowly in-depth, together to study and learn "holographic perspective to see the Dao layer of the two ways of the traditional way and the agent way" bar!
1. How did Mybatis find the SQL statement?
Through the previous study, we have a good understanding of the architecture design of Mybatis and the implementation process of the core data layer. In fact, for our application layer R & D users, the purpose of using the Mybatis framework is very simple. We hope that through it to eliminate the original JDBC redundant code logic, reduce our development workload, improve R & D efficiency, so that we can focus on the preparation of SQL. So in the final analysis, we write SQL,Mybatis to help us execute SQL and interact with the database. To put it more simply, our cooperation with Mybatis is only 5 steps:
1. We write SQL
2. Give orders (call API)
3. Mybatis looking for SQL
4. Mybatis executes SQL
5. Return the execution result
See, Mybatis is really a good helper for database interaction, clever and efficient, as long as we write a good SQL, we can issue orders everywhere (call API) in the program application, and let Mybatis help us to implement SQL. But in fact, we know that Mybatis has done a lot of things in silence, which we have analyzed in detail before:
For example, step 1 is to write SQL. In fact, Mybatis requires us to complete the information configuration Config.xml and the mapping file Mapper.xml ahead of time before we start writing SQL.
For example, step 2 is to call the API for adding, deleting, modifying and searching in our actual application (such as sqlsession.selectList).
For example, step 4 executes SQL, which is actually the session invocation executor, the executor invokes the statement processor, the statement processor combines the parameter processor and the type processor, and finally interacts with the database through JDBC.
For example, step 5 returns the execution result, which is the result set returned by JDBC, maps the encapsulation, and finally returns the expected encapsulation object.
If you are careful, you may find that we didn't talk about step 3, so what is step 3: Mybatis looking for SQL.
At this point, we begin the research topic of our summary:
How did Mybatis find the SQL statement?
To solve this problem, let's first think carefully about where our SQL statements are written on weekdays. Well, if nothing happens, I'm sure two places will come to mind: one is the XML configuration file, and the other is the Java annotation.
That's right! If you use the XML configuration method, write the SQL statement in the UserMapper.xml configuration file:
Select * from User
When writing SQL using XML configuration, the "namespace identity + statement block ID" in XML is identified as the unique statement identity, where the unique statement is identified as:
Com.panshenlian.dao.UserDao.findAll
If you use Java annotations, write SQL statements in the UserDao interface:
Public class UserDao {/ * query user list * @ return * / @ Select (value = "select * from User") List findAll ();}
If you write SQL with Java annotations, you will use the "interface fully qualified name + method name" in the interface as the unique statement identity, and the unique statement identity here is the same:
Com.panshenlian.dao.UserDao.findAll
In fact, our Mybatis supports the use of XML configuration and Java annotations to write SQL statements, the two are not absolutely superior or inferior, each project team can make a choice according to its own R & D staff coding habits / capabilities, project coupling requirements, R & D performance-to-price ratio and other aspects. After all, no matter which method we use, the purpose is just to prepare the SQL that actually needs to be executed for Mybatis to use when interacting with the database.
The thing is, when Mybatis starts the build, it scans the SQL file we wrote. If you use XML configuration to write SQL, then you need to specify the mapper file mapper.xml in the Config.xml core configuration file (the following code demonstrates the first); if you use Java annotations to write SQL, then you need to specify in the Config.xml core configuration file to load the Mapper interface that uses annotations (the following code demonstrates the second kind).
Similarly, no matter which way you tell Mybatis to scan / build, it will eventually be uniformly loaded into a large pool of SQL statements, which is a Map collection, with the unique statement identification as the collection key, each SQL statement object as the value, and eventually the large pool of SQL statements Map collection will be set as an attribute on the global configuration Configuration. For us to use Mybatis at any time throughout the application cycle.
Look, each SQL statement is instantiated as an MappedStatement statement object, and the large pool of the SQL statement Map collection is used as the property mappedStatements of the global configuration Configuration.
/ / Mybatis global configuration object public class Configuration {/ / the collection pool for storing SQL statements Map mappedStatements = new StrictMap}
Basic simple SQL statement parsing process:
At this point, I believe some curious friends still want to know, how does Mybatis load every SQL statement we write into the statement collection big pool? How do you ensure that the Key value (unique statement identification) of each statement in the collection pool is unique and will not be repeated?
Well, with curious little heads, we explore these two questions:
1. How does Mybatis load every SQL statement we write into the statement collection pool?
First, let's see that when Mybatis initially builds the session, it gets the session factory object by loading the core configuration file:
/ / load the core configuration file InputStream is = Resources.getResourceAsStream ("SqlMapConfig.xml"); / / get the sqlSession factory object SqlSessionFactory f = new SqlSessionFactoryBuilder () .build (is)
We traced the source code and found that in the build () logic of the session factory builder SqlSessionFactoryBuilder, while implementing the session factory instance construction, the configuration file was parsed and encapsulated into a global configuration object Configuration and a statement object collection MappedStatement.
There is no better way to describe the process of writing SQL and building a set of statements in XML configuration and Java annotations.
2. How does Mybatis ensure that the Key value (unique statement identification) of each statement in the collection pool is unique and will not be repeated?
According to the analysis of the first question, we know that the SQL statement will eventually be stored in the statement set, so is this statement set ordinary Map? No, this collection instance is actually a static anonymous inner class StrictMap of the Mybatis framework in the Configuration global configuration object, which inherits HashMap, overrides the put () method, and implements a duplicate check of the Key value (unique statement identity) in put ().
/ / Global configuration public class Configuration {/ / static anonymous inner class protected static class StrictMap extends HashMap {/ / overrides the put method @ Override public V put (String key V value) {/ / if a duplicate key occurs, throw an exception if (containsKey (key)) {throw duplicate exception }}
Therefore, whether you use XML configuration or Java annotations, you must ensure that each SQL statement has a unique statement identity, otherwise you will receive a parsing exception from Mybatis during the construction phase of Mybatis startup. For example, I set two findAll statements in UserMapper.xml.
Select 1 from User select * from User
Not surprisingly, there is an exception warning that Mybatis parses SQL:
/ / the exception location is very accurate-- > when parsing mapper sql # org.apache.ibatis.builder.BuilderException: which mapper file is Error parsing SQL Mapper Configuration.//-- > UserMapper.xml### Cause: org.apache.ibatis.builder.BuilderException: Error parsing Mapper XML. Which id of The XML location is' UserMapper.xml'// repeats-- > findAll### Cause: java.lang.IllegalArgumentException: Mapped Statements collection already contains value for com.panshenlian.dao.IUserDao.findAll. Please check UserMapper.xml and UserMapper.xml
Well, at this point we are basically clear, how do you save SQL, and why don't you store it repeatedly, and where does it exist? Then the rest is very simple. For the value of a Map collection, I believe you all know that it is nothing more than getting the stored value value through key. And the value of this set of statements in Mybatis is also obtained through the key value. This key, we here are the unique statement identification of each statement. When we call the addition, deletion, modification and query API of the session SqlSession, we will pass this unique statement identification, telling Mybatis: "help us execute the SQL of the statement object corresponding to this key." that's all.
However, when users in our application layer call to add, delete, modify and check API, how do we * * inform Mybatis of the Key value? * * should I tell Mybatis directly? Or tell Mybatis euphemistically (through proxy).
This is more interesting, and it is also what we are going to explain in part 3. We will talk about it in detail below. Let's take a look at the theme of part 2 first.
2. Why is there a Dao layer?
In software development, in order to facilitate the development and maintenance of applications, we generally use clear and reasonable framework patterns to standardize development behavior, improve the cohesion of the same module, and reduce the coupling of different modules, such as MVC, MVP, MVVM and so on. MVC (Model-View-Controller) is the most widely used hierarchical framework pattern in Java language.
For the MVC hierarchical mode, in fact, the earliest design comes from desktop applications, generally M represents the business model Model,V represents the view interface view,C represents the controller Controller, generally:
View (View layer): the view layer directly faces the user / terminal and provides the instruction input or interface operation request to the user / terminal.
Controller (control layer): the control layer is responsible for receiving instructions or operation requests from the "view layer" and transferring them to the "model layer". After receiving the return results from the "model layer", it will be synchronously transmitted back to the "view layer" to achieve the role of control / link.
Model (model layer): the model layer is the core data information processing layer, which is divided into business logic processing and data persistence processing. The model layer receives requests from the "control layer" and returns the processing results to the "control layer" through logical operations and data conversion.
From the point of view of program coding, the main purpose of using MVC is to separate the implementation code of layer M and layer V, so as to facilitate hierarchical code design and maintenance. From the point of view of the result morphology, in fact, M layer and V layer can be understood as different forms of the same information (or matter), analogy between water and ice, or water and gas (may not be appropriate, But I do understand as information / material form transfer), and the purpose of C layer is to connect the transfer M layer and V layer and ensure the synchronization / updating of M layer and V layer.
Curious friends want to know, what does the MVC framework pattern introduced above have to do with our Dao layer?
It has to be relevant!
We know that in the MVC framework pattern, the model layer Model is the core data information processing layer, including business logic processing and data persistence processing, in which business logic processing is divided into Service module, which is responsible for the operation logic corresponding to specific business requirements; data persistence processing is divided into Dao module (full name Data Access Object, that is, data access object), which is responsible for interacting with database and connecting Service module and database. So as long as it is dealing with the database, our Dao layer is essential!
At this point, I believe many friends will think that the Dao module is responsible for data persistence processing, and our Mybatis is not a persistence layer framework? That's right, so the Mybatis framework is absolutely in charge of dealing with the database, so when our project integrates the Mybatis framework, API such as adding, deleting, modifying and querying Mybatis is basically used in the Dao module, and the interface call and code implementation is also extremely simple and convenient.
In part 3, we talk about the key topic of this article, "two implementations of the Dao layer: tradition and proxy."
3. Two ways to implement Dao layer: traditional and proxy.
With the first two points as the basis, the explanation of our third topic, "two implementations of the Dao layer: tradition and proxy", will be easy for everyone to accept, because we spent a lot of time in the first part of the topic to clarify how Mybatis finds the SQL statement, so that you have a comprehensive understanding of the search for the SQL statement, so I would like to spoil it to you in advance: two implementation ways of the Dao layer: tradition and proxy. It can be roughly understood that there is only a difference between them in the way they look for SQL statements and the objects they execute.
Let's first take a brief look at our general example of the structure of a project directory (pinch the head and tail and leave only the basic MVC directory skeleton).
The traditional code implementation of the general Dao layer:
1. Write UserDao interface
Public interface UserDao {List findAll ();}
2. Write UserDaoImpl implementation
Public class UserDaoImpl implements UserDao {@ Override public List findAll () {/ / load the core configuration file InputStream is = Resources.getResourceAsStream ("config.xml"); / / get the sqlSession factory object SqlSessionFactory fy = new SqlSessionFactoryBuilder () .build (is); / / get the sqlSession object SqlSession sqlSession = fy.openSession () / / execute the sql statement List userList = sqlSession.selectList ("dao.UserDao.findAll"); return userList;}}
3. Write UserMapper.xml
Select * from User
4. Dao layer calls (through the application's Service layer calls or directly using the Junit framework for testing)
/ / Service service layer calls / / or / / Junit test framework test @ Test public void tesDaoMethod () {UserDao userDao = new UserDaoImpl (); List userList = userDao.findAll (); System.out.println (userList);}
All User records can be obtained from the above call results. This way of defining interfaces in the Dao layer and creating Dao layer interface implementation classes is generally called the traditional implementation method of the Dao layer. This way builds an interface implementation class to act as the execution object of the Dao layer, and the way to find the SQL statement is very simple and direct, directly specifying the unique statement identity. There is hard coding in the Java file, for example, the SQL statement in this example is uniquely identified as: dao.UserDao.findAll.
After introducing the traditional development and implementation methods, let's talk about the proxy development and implementation of the Dao layer. First of all, what is the special way of proxy development of the Dao layer?
First of all, proxy development implementation only requires us to write the Dao interface instead of the implementation class.
So since you don't have to write implementation classes, will there be some other constraints?
Of course, this proxy development implementation requires our interface and configuration file Mapper.xml to follow some specifications:
1) the namespace in the Mapper.xml file is the same as the fully qualified name of the mapper interface
2) the method name of the Mapper interface is the same as the id of each statement defined in Mapper.xml
3) the input parameter type of the Mapper interface method is the same as the parameterType type of each sql defined in mapper.xml
4) the output parameter type of the Mapper interface method is the same as the resultType type of each sql defined in mapper.xml
Because the implementation of proxy development is closely related to the Mapper configuration, we also call it the Mapper interface development method. The reason why we do not need to write the implementation class is that the dynamic proxy object of the Dao interface is created at the bottom, and the proxy object itself will build the method body of the Dao interface and the code implementation of the Dao layer proxy implementation:
1. Write UserDao interface
Public interface UserDao {User findOne (int userId);}
2. Write UserMapper.xml
Select * from User where id = # {id}
3. Dao layer calls (through the application's Service layer calls or directly using the Junit framework for testing)
/ / Service service layer calls / / or / Junit test framework test @ Test public void tesDaoMethod () {/ / load core configuration file InputStream is = Resources.getResourceAsStream ("config.xml"); / / get sqlSession factory object SqlSessionFactory fy = new SqlSessionFactoryBuilder () .build (is); / / get sqlSession object SqlSession sqlSession = fy.openSession () / / get the proxy class UserMapper userMapper = sqlSession.getMapper (UserMapper.class) of the UserMapper interface generated by the MyBatis framework; / / execute SQL User user = userMapper.findById (1); System.out.println (user); sqlSession.close ();}
The User record of the specified ID can be obtained from the above call result. In this way, the actual SQL statement is executed through the proxy. Since the Dao API and Mapper.xml configuration have been agreed upon, there is no need to specify a unique statement identity when calling the API, and there will be no hard coding problem in the Java file.
When you get here, some of your friends will wonder? The sqlSession session gets the interface proxy class through getMapper and then invokes the interface method. When the interface method is actually executed, how does the Mybatis proxy match the SQL statement in the mapper.xml configuration file logically?
The black ① ~ ⑥ above is the actual process of building a Dao proxy object, which is basically the process of generating a proxy object. The MapperProxy proxy class itself implements the InvocationHandler interface, so it meets the requirements of a proxy class. The MapperProxy proxy instance ultimately assigns the MapperMethod object to distribute and execute statements, including additions, deletions, modifications, queries, and other operations.
The red ① ~ ③ above is the process by which the proxy object goes to the SQL statement collection pool to find SQL specific statements according to the fully qualified name of the interface when executing the actual interface.
/ / actual statement execution method object public class MapperMethod {/ / assign execution SQL public Object execute (SqlSession sqlSession, Object [] args) {switch (command.getType ()) {case INSERT: sqlSession.insert (interface statement ID); break; case UPDATE: sqlSession.update (interface statement ID); break Case DELETE: sqlSession.insert (ID); break; case SELECT: sqlSession.select (ID); break } Thank you for your reading. The above is the content of "what are the traditional and proxy ways of viewing the two implementation ways of the Dao layer from a holographic perspective". After the study of this article, I believe you have a deeper understanding of the traditional and proxy ways of viewing the two implementation methods of the Dao layer from a holographic perspective, and the specific use needs to be verified in practice. Here is, the editor will push for you more related knowledge points of the article, welcome to follow!
Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.
Views: 0
*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.
Continue with the installation of the previous hadoop.First, install zookooper1. Decompress zookoope
"Every 5-10 years, there's a rare product, a really special, very unusual product that's the most un
© 2024 shulou.com SLNews company. All rights reserved.