為了修復生產資料,需要執行一段一次性的代碼, 鑒于是spring老專案,就想到了InitializingBean,
代碼如下,服務啟動后,log里發現出現2條“一次性任務開始”, 好在里面邏輯做了防重控制,沒有受到什么影響,
@Slf4j @Component public class TransToBankBean implements InitializingBean { @Autowired private FixedLdysZhOrdersService xxxService; @Override public synchronized void afterPropertiesSet() { log.info("一次性任務開始"); .... } }
今天理了一下程式配置,發現web.xml配置有問題,
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd" version="4.0"> <context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:spring-mvc.xml,classpath:spring-mybatis.xml,classpath:spring-dubbo.xml</param-value> </context-param> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <listener> <listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class> </listener> <servlet> <servlet-name>SpringMVC</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:spring-mvc.xml</param-value> </init-param> <load-on-startup>1</load-on-startup> <async-supported>true</async-supported> </servlet> <servlet-mapping> <servlet-name>SpringMVC</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>/index.jsp</welcome-file> </welcome-file-list> </web-app>
注意到上面web.xml中有兩個contextConfigLocation, 一個位于context-param引數中, 另一個位于servelt的init-param引數中,
問題就出現在這個contextConfigLocation上,
contextConfigLocation,名如其義,指的是context配置(檔案)的位置,
servelt/init-param的contextConfig是為了加載DispatcherServlet的, 而context-param的contextConfig是為了加載web程式需要加載的資料庫等等配置,
再來說說servlet節點配置:
servlet有這么幾個屬性:servlet-name、servlet-class、init-param,其中,servlet-class通常就是我們熟知的 DispatcherServlet,init-param中可以指定contextConfigLocation,
1) init-param里如果未配置contextConfigLocation,則要求程式在WEB-INF存在名為[servlet-name]-servlet.xml的組態檔,否則程式啟動會報例外:java.io.FileNotFoundException:Could not open ServletContext resource [/WEB-INF/SpringMVC-servlet.xml] ,(注意:我這里servlet-name的值是SpringMVC,所以檔案名字會是 SpringMVC-servlet.xml)
2) init-param里如果有contextConfigLocation配置,則DispatcherServlet會使用這個指定的組態檔作為配置,例如,我指定的引數值是classpath:spring-mvc.xml, 這個檔案定義在main/resources下,編譯后存在于程式包的classes目錄中,
顯然,上面web.xml中兩個contextConfigLocation都指定了spring-mvc.xml,這個context檔案里指定了component-scan包掃描路徑,
上面定義的InitializingBean實作類就在這些package下面,所以,不難理解,這個類所覆寫的afterPropertiesSet會被執行兩次,
好,了解了上面的解釋,那么,我們就知道該怎么改了,------>分離配置,解決掃描兩遍的問題,
改造后的web.xml如下, 兩處contextConfigLocation分別指定的是application-context.xml 和 spring-mvc.xml,兩者各司其職 -----> application-context.xml是spring應用程式的背景關系配置,不含springmvc配置; spring-mvc.xml中只有springmvc配置,
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd" version="4.0"> <context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:application-context.xml</param-value> </context-param> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <listener> <listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class> </listener> <servlet> <servlet-name>SpringMVC</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:spring-mvc.xml</param-value> </init-param> <load-on-startup>1</load-on-startup> <async-supported>true</async-supported> </servlet> <servlet-mapping> <servlet-name>SpringMVC</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>/index.jsp</welcome-file> </welcome-file-list> </web-app>
spring-mvc.xml
<?xml version="1.0" encoding="UTF-8"?> <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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.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"> <!-- 擴充了注解驅動,可以將請求引數系結到控制器引數 --> <mvc:annotation-driven/> <mvc:default-servlet-handler/> <!-- controller所在包--> <context:component-scan base-package="com.levy.rpcprovider.controller"/> </beans>
當看到一些不好的代碼時,會發現我還算優秀;當看到優秀的代碼時,也才意識到持續學習的重要!--buguge
本文來自博客園,轉載請注明原文鏈接:https://www.cnblogs.com/buguge/p/16286630.html
<style>hr.signhr{width:80%;margin:0 auto;border: 0;height: 4px;background-image: linear-gradient(to right, rgba(0, 0, 0, 0), rgba(0, 0, 0, 0.75), rgba(0, 0, 0, 0))}</style>
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/477508.html
標籤:Java
上一篇:Java 15 新特性:隱藏類
