国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

如何扒開 SqlSession 的外衣

運維 數據庫運維
如果我們配置的是MANAGED,會把事務交給容器來管理,比如JBOSS,Weblogic。因為我們是本地跑的程序,如果配置成MANAGED就會不有任何事務。

[[360740]]

老規矩,先上案例代碼,我們按照這個案例一步一步的搞定Mybatis源碼。

  1. public class MybatisApplication { 
  2.     public static final String URL = "jdbc:mysql://localhost:3306/mblog"
  3.     public static final String USER = "root"
  4.     public static final String PASSWORD = "123456"
  5.  
  6.     public static void main(String[] args) { 
  7.         String resource = "mybatis-config.xml"
  8.         InputStream inputStream = null
  9.         SqlSession sqlSession = null
  10.         try { 
  11.             inputStream = Resources.getResourceAsStream(resource); 
  12.             SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream); 
  13.             sqlSession = sqlSessionFactory.openSession(); 
  14.             UserMapper userMapper = sqlSession.getMapper(UserMapper.class); 
  15.             System.out.println(userMapper.selectById(1)); 
  16.  
  17.         } catch (Exception e) { 
  18.             e.printStackTrace(); 
  19.         } finally { 
  20.             try { 
  21.                 inputStream.close(); 
  22.             } catch (IOException e) { 
  23.                 e.printStackTrace(); 
  24.             } 
  25.             sqlSession.close(); 
  26.         } 
  27.     } 

由于很多小伙伴在催,說Mybatis源碼系列好像何時才有下文了,為此老田熬夜寫了這篇。

 

繼續開擼~~

  1. SqlSession sqlSession = sqlSessionFactory.openSession(); 

前面那篇文章已經分析了,這里的sqlSessionFactory其實就是DefaultSqlSessionFactory。

所以這里,我們就從DefaultSqlSessionFactory里的openSession方法開始。

  1. public class DefaultSqlSessionFactory implements SqlSessionFactory { 
  2.  
  3.   private final Configuration configuration; 
  4.  
  5.   public DefaultSqlSessionFactory(Configuration configuration) { 
  6.     this.configuration = configuration; 
  7.   } 
  8.   //創建session,這個方法直接調用本類中的另外一個方法 
  9.   @Override 
  10.   public SqlSession openSession() { 
  11.     return openSessionFromDataSource(configuration.getDefaultExecutorType(), nullfalse); 
  12.   } 
  13.   //其實是調用這個方法 
  14.   private SqlSession openSessionFromDataSource(ExecutorType execType, TransactionIsolationLevel level, boolean autoCommit) { 
  15.     Transaction tx = null
  16.     try { 
  17.       //對應xml標簽<environments> ,這個在配置文件解析的時候就已經存放到configuration中了。 
  18.       final Environment environment = configuration.getEnvironment(); 
  19.       final TransactionFactory transactionFactory = getTransactionFactoryFromEnvironment(environment); 
  20.       tx = transactionFactory.newTransaction(environment.getDataSource(), level, autoCommit); 
  21.       //創建一個executor來執行SQL   
  22.       final Executor executor = configuration.newExecutor(tx, execType); 
  23.       //這里也說明了,為什么我們代碼里的SqlSession是DefaultSqlSession 
  24.       return new DefaultSqlSession(configuration, executor, autoCommit); 
  25.     } catch (Exception e) { 
  26.       closeTransaction(tx); // may have fetched a connection so lets call close() 
  27.       throw ExceptionFactory.wrapException("Error opening session.  Cause: " + e, e); 
  28.     } finally { 
  29.       ErrorContext.instance().reset(); 
  30.     } 
  31.   } 
  32.    
  33.     private TransactionFactory getTransactionFactoryFromEnvironment(Environment environment) { 
  34.     if (environment == null || environment.getTransactionFactory() == null) { 
  35.       return new ManagedTransactionFactory(); 
  36.     } 
  37.     return environment.getTransactionFactory(); 
  38.   } 

這個方法中的主要內容有:

 

下面我們就來逐個攻破。

創建事務Transaction

事務工廠類型可以配置為JDBC類型或者MANAGED類型。

JdbcTransactionFactory生產JdbcTransaction。

ManagedTransactionFactory生產ManagedTransaction。

如果配置的JDBC,則會使用Connection對象的commit()、rollback()、close()方法來管理事務。

如果我們配置的是MANAGED,會把事務交給容器來管理,比如JBOSS,Weblogic。因為我們是本地跑的程序,如果配置成MANAGED就會不有任何事務。

但是,如果我們項目中是Spring集成Mybatis,則沒有必要配置事務,因為我們會直接在applicationContext.xml里配置數據源和事務管理器,從而覆蓋Mybatis的配置。

創建執行器Executor

調用configuration的newExecutor方法創建Executor。

  1. final Executor executor = configuration.newExecutor(tx, execType); 
  2. //Configuration中 
  3. public Executor newExecutor(Transaction transaction, ExecutorType executorType) { 
  4.     executorType = executorType == null ? defaultExecutorType : executorType; 
  5.     executorType = executorType == null ? ExecutorType.SIMPLE : executorType; 
  6.     Executor executor; 
  7.     //第一步 
  8.     if (ExecutorType.BATCH == executorType) { 
  9.       executor = new BatchExecutor(this, transaction); 
  10.     } else if (ExecutorType.REUSE == executorType) { 
  11.       executor = new ReuseExecutor(this, transaction); 
  12.     } else { 
  13.       executor = new SimpleExecutor(this, transaction); 
  14.     } 
  15.     //第二步 
  16.     if (cacheEnabled) { 
  17.       executor = new CachingExecutor(executor); 
  18.     } 
  19.     //第三步 
  20.     executor = (Executor) interceptorChain.pluginAll(executor); 
  21.     return executor; 
  22.   } 

此方法分三個步驟。

第一步:創建執行器

Executor的基本類型有三種:

  1. public enum ExecutorType { 
  2.   SIMPLE, REUSE, BATCH 

SIMPLE為默認類型。

 

為什么要讓抽象類BaseExecutor實現Executor接口,然后讓具體實現類繼承抽象類呢?

這就是模板方法模式的實現。

模板方法模式就是定義一個算法骨架,并允許子類為一個或者多個步驟提供實現。模板方法是得子類可以再不改變算法結構的情況下,重新定義算法的某些步驟。

抽象方法是在子類匯總實現的,每種執行器自己實現自己的邏輯,BaseExecutor最終會調用到具體的子類中。

抽象方法

  1. protected abstract int doUpdate(MappedStatement ms, Object parameter) throws SQLException; 
  2.  
  3. protected abstract List<BatchResult> doFlushStatements(boolean isRollback) throws SQLException; 
  4.  
  5. protected abstract <E> List<E> doQuery(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) throws SQLException; 
  6.  
  7. protected abstract <E> Cursor<E> doQueryCursor(MappedStatement ms, Object parameter, RowBounds rowBounds, BoundSql boundSql)  throws SQLException; 

第二步:緩存裝飾

在上面代碼中的第二步

  1. if (cacheEnabled) { 
  2.       executor = new CachingExecutor(executor); 

如果cacheEnabled=true,會用裝飾器設計模式對Executor進行裝飾。

第三步:插件代理緩存裝飾完后,就會執行

  1. executor = (Executor) interceptorChain.pluginAll(executor); 

這里會對Executor植入插件邏輯。

比如:分頁插件中就需要把插件植入的Executor

 

好了,到此,執行器創建的就搞定了。

創建DefaultSqlSession對象

把前面解析配置文件創建的Configuration對象和創建的執行器Executor賦給DefaultSqlSession中的屬性。

  1. public DefaultSqlSession(Configuration configuration, Executor executor, boolean autoCommit) { 
  2.   this.configuration = configuration; 
  3.   this.executor = executor; 
  4.   this.dirty = false
  5.   this.autoCommit = autoCommit; 

到這里,SqlSession(DefaultSqlSession)對象就創建完畢。

總結

本文我們講了如何創建SqlSession的幾個步驟,最后我們獲得一個DefaultSqlSession對象,里面包含了執行器Executor和配置對象Configuration。Executor是SQL的實際執行對象。Configuration里保存著配置文件內容。

本文源碼分析的整個流程如下圖:

本文轉載自微信公眾號「Java后端技術全棧」,可以通過以下二維碼關注。轉載本文請聯系Java后端技術全棧公眾號。

 

責任編輯:武曉燕 來源: Java后端技術全棧
相關推薦

2025-04-28 01:22:45

2018-12-29 16:40:29

c語言編程語言指針

2021-05-25 07:59:59

Linux運維Linux系統

2012-08-30 09:17:28

Win 7Win 8操作系統

2021-08-10 12:05:19

Linuxworkqueue內核

2021-03-28 20:44:34

Kafka中間件MQ

2020-12-01 10:27:39

區塊鏈比特幣

2015-11-02 16:42:26

2013-10-10 09:24:34

2010-06-29 16:36:27

間諜木馬惡意程序卡巴斯基

2025-09-16 00:31:23

2020-12-09 09:22:53

GETPOSTWeb

2023-08-14 07:19:23

2012-09-06 09:57:34

Saas云安全云計算

2014-11-13 17:48:21

2009-05-27 08:44:24

2017-09-07 07:20:10

2020-02-06 10:20:19

硬件黑客技術

2022-11-26 10:14:48

Zookeepermybatisspring

2022-11-15 07:35:50

Spring事件觀察者模式
點贊
收藏

51CTO技術棧公眾號

欧美日韩黄视频| 国产一级免费在线观看| 一区二区三区四区在线观看国产日韩| 精品国产凹凸成av人网站| h动漫在线视频| 久久精品人人做人人爽人人| 日韩少妇中文字幕| 亚洲一区中文| 久久久精品有限公司| 亚洲国产裸拍裸体视频在线观看乱了中文 | 999亚洲国产精| 国产日本欧美一区| 国产免费久久| 国产成人精品视频在线| 日韩黄色网络| 国产99久久久欧美黑人| 国产精品免费99久久久| 91国产视频在线播放| 美国成人xxx| 国产成人精品一区二区| 欧美色图在线播放| 99久久精品无码一区二区毛片 | 久久这里有精品| 国产一区二区三区亚洲综合| 日韩精品中文在线观看| 美女高潮在线观看| 亚洲色图综合久久| 日韩网站中文字幕| 精品国产一区二区在线| 97久久中文字幕| 欧美黑人一区二区三区| 理论片一区二区在线| 欧洲一区二区视频| 日韩成人精品一区| 亚洲xxxx做受欧美| 国产精品亚洲综合久久| 杨幂一区欧美专区| 国产高清成人在线| 欧美一区二区中文字幕| 中文字幕在线不卡一区二区三区| 成年人视频网站| 色综合一区二区| a免费在线观看| 亚洲精品一区中文| 99re8这里有精品热视频免费| 全球成人中文在线| 国产综合亚洲精品一区二| 欧美视频小说| 2021久久国产精品不只是精品| 九色porny自拍| 一本一道久久a久久精品| 日韩精品分区| 欧美成人合集magnet| 亚洲激情77| 久久99精品久久久久久久久久| 国产在线一区二区| 九七影院理伦片| 欧洲成人一区| 欧美专区福利免费| 7777精品伊人久久久大香线蕉完整版| 波多野结衣中文在线| 久久影视电视剧免费网站清宫辞电视 | 日本欧美在线看| 日韩精品久久一区二区| 国产日韩欧美不卡| 未来日记在线观看| 亚洲激情视频在线| 这里视频有精品| 91久色国产| 国产激情偷乱视频一区二区三区 | 丁香花高清视频完整版在线观看| 日韩欧美中文字幕在线观看| 91美女主播在线视频| 久久久久久久久国产精品| 亚洲xxx拳头交| 久久精品无码中文字幕| 一区二区三区.www| 日本在线播放一二三区| 欧美在线不卡区| 久久一区激情| 黄网视频在线观看| 欧美白人最猛性xxxxx69交| 成人av综合网| 精品视频第一区| 国产精品的网站| av大片在线| 欧美v日韩v国产v| 欧美大胆a级| 亚洲新中文字幕| 欧美日韩精品一区二区视频| 久久久久久久久久久av| 最近高清中文在线字幕在线观看| 日韩国产高清视频在线| 91九色单男在线观看| 蜜乳av一区二区| 丁香婷婷自拍| 亚洲无亚洲人成网站77777| 亚洲人成网亚洲欧洲无码| 伊人久久大香线蕉成人综合网| 综合自拍亚洲综合图不卡区| 婷婷av在线| 国产精品久久久久久av福利| 国产精品一区久久久久| 三级在线电影| 国产69精品久久久久9999| 秋霞午夜av一区二区三区| 性疯狂做受xxxx高清视频| 尤物yw午夜国产精品视频| 亚洲视频大全| 亚洲做受高潮| 欧美激情喷水视频| 国产成人综合在线播放| 岛国成人毛片| 俄罗斯精品一区二区三区| 一区二区三区在线播放| 日韩欧美激情电影| 精品一区二区三区无码视频| 91精品国产入口在线| 久久久久电影| 老司机午夜激情| 久久久免费av| 97精品电影院| 在线亚洲人成| 亚洲一卡二卡区| 欧美一二三四在线| 亚洲精品护士| 免费黄色网址在线观看| 高清视频一区| 在线一区二区视频| 亚洲mv大片欧洲mv大片| 91在线最新| 国产精品h在线观看| 国产女人18水真多18精品一级做| 男女啪啪999亚洲精品| 精品嫩模一区二区三区| 亚洲第一福利视频| 日本欧美韩国一区三区| 老司机午夜在线| 国产一区二区三区黄| 婷婷中文字幕综合| 欧美一级精品| 色视频免费在线观看| 国产精品一区二区三区免费视频 | 久久久福利视频| 在线观看91精品国产入口| 久久久久久久久国产一区| 欧美13~18sex性hd| 国产精品黄视频| 疯狂做受xxxx高潮欧美日本| 欧美日韩国产免费观看视频| 国产91久久久久蜜臀青青天草二| 国产精品99久久久久久www| 午夜电影网一区| 在线精品一区二区| bbw在线视频| 日韩一级性生活片| 69av在线播放| 狠狠色狠狠色综合日日小说| 亚洲久久视频| 性爽视频在线| 男人搞女人网站| 日韩一区欧美小说| 久久国产成人精品| 在线观看免费黄色| 天天干天天色天天爽| 色伦专区97中文字幕| 亚洲天堂久久久久久久| 婷婷中文字幕一区| 91老司机福利在线| 北条麻妃在线观看| 国产精品狠色婷| 欧美精品在线视频| 成人性生交大片免费看中文网站| 高清不卡一区| 中国大陆高清aⅴ毛片| 激情视频一区二区| 亚洲精品视频免费观看| 亚洲国产精品久久久天堂| 九色91在线| 日本一道本久久| 国产成人免费91av在线| 欧美怡红院视频| 国产丶欧美丶日本不卡视频| 女人抽搐喷水高潮国产精品| 男操女在线观看| 无码av天堂一区二区三区| 国产不卡视频在线| 精品奇米国产一区二区三区| 91麻豆视频网站| 欧美激情综合色综合啪啪| 乱人伦视频在线| 97影院理论午夜| 视频一区视频二区视频| 4438全国成人免费| 欧美一区二区精品久久911| 91视频国产资源| 好看的亚洲午夜视频在线| 韩国精品视频在线观看| 国产一二三区在线视频| 男的插女的下面视频|