摘要:同時(shí)注釋配置失敗的構(gòu)造方法觸發(fā)了兩次,添加到中的實(shí)例和注冊到容器中的實(shí)例并不是同一個(gè)實(shí)例解決方法增加一個(gè)獲取的實(shí)例的工具類,通過這個(gè)工具類調(diào)用需要注入的服務(wù)的方法工具類修改攔截器執(zhí)行結(jié)果
開發(fā)環(huán)境
JDK 1.8
Springboot 2.1.1.RELEASE
pom配置關(guān)鍵代碼 實(shí)體類org.springframework.boot spring-boot-starter-parent 2.1.1.RELEASE org.springframework.boot spring-boot-starter-data-jpa mysql mysql-connector-java 8.0.13 org.springframework.boot spring-boot-starter-test test
@Entity public class User implements Serializable { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Integer id; private String name; public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } }Repository
public interface UserRepository extends JpaRepository自定義服務(wù){ }
@Service public class MyService { public void print(){ System.out.println(this.getClass().getSimpleName()+" call"); } }攔截器
public class SimpleInterceptor extends EmptyInterceptor { @Resource private MyService myService; @Override public String onPrepareStatement(String sql) { myService.print(); System.out.println("sql:"+sql); return super.onPrepareStatement(sql); } }啟動類
@SpringBootApplication public class BootHibernateInterceptorProblemApplication { public static void main(String[] args) { SpringApplication.run(BootHibernateInterceptorProblemApplication.class, args); } }配置
## DataSource spring.datasource.url=jdbc:mysql://localhost:3306/demo?characterEncoding=utf8&useSSL=true spring.datasource.username=root spring.datasource.password=123456789 ## hibernate spring.jpa.hibernate.ddl-auto=update ## add interceptor spring.jpa.properties.hibernate.ejb.interceptor=com.rjh.interceptor.SimpleInterceptor單元測試類
@RunWith(SpringRunner.class) @SpringBootTest public class BootHibernateInterceptorProblemApplicationTests { @Resource private UserRepository userRepository; @Test public void contextLoads() { System.out.println(userRepository.findAll()); } }運(yùn)行結(jié)果
java.lang.NullPointerException at com.rjh.interceptor.SimpleInterceptor.onPrepareStatement(SimpleInterceptor.java:20) ... ... ...分析
根據(jù)異常信息,猜測是注入MyService失敗
修改單元測試@RunWith(SpringRunner.class) @SpringBootTest public class BootHibernateInterceptorProblemApplicationTests { @Resource private UserRepository userRepository; @Resource private MyService myService; @Resource private SimpleInterceptor simpleInterceptor; @Test public void contextLoads() { Assert.assertNotNull(myService); Assert.assertNotNull(simpleInterceptor); System.out.println(userRepository.findAll()); } }運(yùn)行結(jié)果
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type "com.rjh.interceptor.SimpleInterceptor" available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@javax.annotation.Resource(shareable=true, lookup=, name=, description=, authenticationType=CONTAINER, type=class java.lang.Object, mappedName=)} ...分析
根據(jù)異常信息可知,Spring的IoC容器中并沒有SimpleInterceptor這個(gè)Bean,從此處可知spring.jpa.properties.hibernate.ejb.interceptor=com.rjh.interceptor.SimpleInterceptor并沒有把這個(gè)攔截器注冊到Spring容器中
失敗方案在SimpleInterceptor上添加@Component注解,將SimpleInterceptor注冊到Spring容器中。同時(shí)注釋spring.jpa.properties.hibernate.ejb.interceptor配置
失敗:SimpleInterceptor的構(gòu)造方法觸發(fā)了兩次,添加到Hibernate中的SimpleInterceptor實(shí)例和注冊到Spring容器中的SimpleInterceptor實(shí)例并不是同一個(gè)實(shí)例
解決方法增加一個(gè)獲取Spring的ApplicationContext實(shí)例的工具類,通過這個(gè)工具類調(diào)用需要注入的服務(wù)的方法
工具類@Component public class SpringContextUtil implements ApplicationContextAware { private static ApplicationContext applicationContext; @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { SpringContextUtil.applicationContext=applicationContext; } public static ApplicationContext getApplicationContext() { return applicationContext; } }修改攔截器
public class SimpleInterceptor extends EmptyInterceptor { @Override public String onPrepareStatement(String sql) { MyService myService= SpringContextUtil.getApplicationContext().getBean(MyService.class); myService.print(); System.out.println("sql:"+sql); return super.onPrepareStatement(sql); } }執(zhí)行結(jié)果
MyService call sql:select user0_.id as id1_0_, user0_.name as name2_0_ from user user0_ []
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/75061.html
摘要:熱加載代表的是我們不需要重啟服務(wù)器,就能夠類檢測得到,重新生成類的字節(jié)碼文件無論是熱部署或者是熱加載都是基于類加載器來完成的。驗(yàn)證階段字節(jié)碼文件不會對造成危害準(zhǔn)備階段是會賦初始值,并不是程序中的值。 一、SpringBoot入門 今天在慕課網(wǎng)中看見了Spring Boot這么一個(gè)教程,這個(gè)Spring Boot作為JavaWeb的學(xué)習(xí)者肯定至少會聽過,但我是不知道他是什么玩意。 只是大...
摘要:本章目的基于平臺整合分別完成客戶端服務(wù)端的單元測試。在測試控制器內(nèi)添加了三個(gè)測試方法,我們接下來開始編寫單元測試代碼。總結(jié)本章主要介紹了基于平臺的兩種單元測試方式,一種是在服務(wù)端采用注入方式將需要測試的或者注入到測試類中,然后調(diào)用方法即可。 單元測試對于開發(fā)人員來說是非常熟悉的,我們每天的工作也都是圍繞著開發(fā)與測試進(jìn)行的,在最早的時(shí)候測試都是采用工具Debug模式進(jìn)行調(diào)試程序,后來Ju...
摘要:前言由于寫的文章已經(jīng)是有點(diǎn)多了,為了自己和大家的檢索方便,于是我就做了這么一個(gè)博客導(dǎo)航。 前言 由于寫的文章已經(jīng)是有點(diǎn)多了,為了自己和大家的檢索方便,于是我就做了這么一個(gè)博客導(dǎo)航。 由于更新比較頻繁,因此隔一段時(shí)間才會更新目錄導(dǎo)航哦~想要獲取最新原創(chuàng)的技術(shù)文章歡迎關(guān)注我的公眾號:Java3y Java3y文章目錄導(dǎo)航 Java基礎(chǔ) 泛型就這么簡單 注解就這么簡單 Druid數(shù)據(jù)庫連接池...
摘要:此文章僅僅說明在整合時(shí)的一些坑并不是教程增加依賴集成依賴配置三個(gè)必須的用于授權(quán)和登錄創(chuàng)建自己的實(shí)例用于實(shí)現(xiàn)權(quán)限三種方式實(shí)現(xiàn)定義權(quán)限路徑第一種使用角色名定義第二種使用權(quán)限定義第三種使用接口的自定義配置此處配置之后需要在對應(yīng)的 此文章僅僅說明在springboot整合shiro時(shí)的一些坑,并不是教程 增加依賴 org.apache.shiro shiro-spring-...
摘要:請求重試攔截器錯(cuò)誤解碼器在發(fā)生請求錯(cuò)誤包括發(fā)生異?;蛘唔憫?yīng)數(shù)據(jù)不符合預(yù)期的時(shí)候,錯(cuò)誤解碼器可將相關(guān)信息解碼到自定義異常中。 在SpringBoot項(xiàng)目直接使用okhttp、httpClient或者RestTemplate發(fā)起HTTP請求,既繁瑣又不方便統(tǒng)一管理。因此,在這里推薦一個(gè)適...
閱讀 1042·2021-09-30 09:58
閱讀 2878·2021-09-09 11:55
閱讀 2035·2021-09-01 11:41
閱讀 1021·2019-08-30 15:55
閱讀 3383·2019-08-30 12:50
閱讀 3528·2019-08-29 18:37
閱讀 3327·2019-08-29 16:37
閱讀 2042·2019-08-29 13:00