https://docs.spring.io/spring/docs/3.2.x/spring-framework-reference/html/resources.html
java.net.URL
classpath:類路徑:
就是應用的源碼路徑:tomcat/webapps/應用/源碼文件夾
- ServletContext
遺憾的是,Java的標準java.net.URL類和各種URL前綴的標準處理程序不足以完全訪問低級資源。 例如管引,沒有標準化的URL實現(xiàn)可用于訪問需要從類路徑或相對于ServletContext獲取的資源赚爵。 雖然可以為專用URL前綴注冊新的處理程序(類似于http :)這樣的前綴的現(xiàn)有處理程序瓢湃,但這通常非常復雜矢炼,并且URL接口仍然缺少一些理想的功能斤葱,例如檢查存在的方法 被指向的資源慷垮。
資源路徑:
應用的類路徑:classpath:
操作系統(tǒng)的文件路徑: FileSystemXmlApplicationContext:
Url路徑: file: for accessing filesystem paths, http: for accessing resources via the HTTP protocol, ftp: for accessing resources via FTP, etc.
ApplicationContext
- ClassPathXmlApplicationContext
- FileSystemXmlApplicationContext
Spring的Resource接口旨在成為一個更強大的接口,用于抽象對低級資源的訪問揍堕。
6.3 Built-in Resource implementations
6.3.1 UrlResource
UrlResource包裝java.net.URL料身,可用于訪問通常可通過URL訪問的任何對象衩茸,例如文件芹血,HTTP目標,F(xiàn)TP目標等递瑰。所有URL都具有標準化的字符串表示形式祟牲,例如適當?shù)臉藴驶熬Y用于表示來自另一個的一種URL類型隙畜。這包括文件:用于訪問文件系統(tǒng)路徑抖部,http:用于通過HTTP協(xié)議訪問資源,ftp:用于通過FTP訪問資源等议惰。
UrlResource是由Java代碼使用UrlResource構(gòu)造函數(shù)顯式創(chuàng)建的慎颗,但是當您調(diào)用API方法時,通常會隱式創(chuàng)建它,該方法接受一個表示路徑的String參數(shù)俯萎。對于后一種情況傲宜,JavaBeans PropertyEditor最終將決定要創(chuàng)建哪種類型的Resource。如果路徑字符串包含一些眾所周知的(對于它)前綴夫啊,例如classpath:函卒,它將為該前綴創(chuàng)建適當?shù)膶S觅Y源。但是撇眯,如果它無法識別前綴报嵌,則會假定這只是一個標準的URL字符串,并將創(chuàng)建一個UrlResource熊榛。
6.3.2 ClassPathResource
此類表示應從類路徑獲取的資源锚国。 這使用線程上下文類加載器,給定的類加載器或給定的類來加載資源玄坦。
如果類路徑資源駐留在文件系統(tǒng)中血筑,則此Resource實現(xiàn)支持解析為java.io.File,但不支持駐留在jar中且尚未擴展(通過servlet引擎或任何環(huán)境)的類路徑資源的解析 文件系統(tǒng)煎楣。 為了解決這個問題豺总,各種Resource實現(xiàn)始終支持作為java.net.URL的解析。
ClassPathResource是由Java代碼使用ClassPathResource構(gòu)造函數(shù)顯式創(chuàng)建的择懂,但是當您調(diào)用一個API方法時园欣,它通常會隱式創(chuàng)建,該方法接受一個表示路徑的String參數(shù)休蟹。 對于后一種情況沸枯,JavaBeans PropertyEditor將識別字符串路徑上的特殊前綴classpath:并在此情況下創(chuàng)建ClassPathResource。
class loader 加載資源
6.3.3 FileSystemResource
6.3.4 ServletContextResource
6.3.4 ServletContextResource
這是ServletContext資源的Resource實現(xiàn)赂弓,用于解釋相關(guān)Web應用程序根目錄中的相對路徑绑榴。
這始終支持流訪問和URL訪問,但僅在擴展Web應用程序存檔且資源實際位于文件系統(tǒng)上時才允許java.io.File訪問盈魁。 它是否在這樣的文件系統(tǒng)上展開翔怎,或直接從JAR或其他地方(如DB)(可以想象)訪問,實際上是依賴于Servlet容器杨耙。
6.3.5 InputStreamResource
給定InputStream的Resource實現(xiàn)赤套。 只有在沒有適用的特定資源實現(xiàn)時才應使用此方法。 特別是珊膜,在可能的情況下容握,更喜歡ByteArrayResource或任何基于文件的資源實現(xiàn)。
與其他Resource實現(xiàn)相比车柠,這是已打開資源的描述符 - 因此從isOpen()返回true剔氏。 如果需要將資源描述符保留在某處塑猖,或者需要多次讀取流,請不要使用它谈跛。
6.3.6 ByteArrayResource
這是給定字節(jié)數(shù)組的Resource實現(xiàn)羊苟。 它為給定的字節(jié)數(shù)組創(chuàng)建一個ByteArrayInputStream。
它對于從任何給定的字節(jié)數(shù)組加載內(nèi)容非常有用感憾,而無需使用一次性使用的InputStreamResource蜡励。
6.4 The ResourceLoader
ResourceLoader接口旨在由可以返回(即加載)Resource實例的對象實現(xiàn)。
所有應用程序上下文都實現(xiàn)ResourceLoader接口阻桅,因此可以使用所有應用程序上下文來獲取Resource實例巍虫。
當您在特定應用程序上下文上調(diào)用getResource()并且指定的位置路徑?jīng)]有特定前綴時,您將返回適合該特定應用程序上下文的Resource類型鳍刷。 例如占遥,假設針對ClassPathXmlApplicationContext實例執(zhí)行了以下代碼片段:
Resource template = ctx.getResource("some/resource/path/myTemplate.txt");
將返回的是ClassPathResource; 如果對FileSystemXmlApplicationContext實例執(zhí)行相同的方法,則會返回FileSystemResource输瓜。 對于WebApplicationContext瓦胎,您將獲得ServletContextResource,依此類推尤揣。
因此搔啊,您可以以適合特定應用程序上下文的方式加載資源。
另一方面北戏,您也可以通過指定特殊的類路徑來強制使用ClassPathResource负芋,而不管應用程序上下文類型如何:prefix:
Resource template = ctx.getResource("classpath:some/resource/path/myTemplate.txt");
類似地,可以通過指定任何標準java.net.URL前綴來強制使用UrlResource:
Resource template = ctx.getResource("file:/some/resource/path/myTemplate.txt");
Resource template = ctx.getResource("http://myhost.com/resource/path/myTemplate.txt");
下表總結(jié)了將字符串轉(zhuǎn)換為資源的策略:
6.5 The ResourceLoaderAware interface
當類實現(xiàn)ResourceLoaderAware并部署到應用程序上下文(作為Spring管理的bean)時嗜愈,它被應用程序上下文識別為ResourceLoaderAware旧蛾。 然后,應用程序上下文將調(diào)用setResourceLoader(ResourceLoader)蠕嫁,將其自身作為參數(shù)提供(請記住锨天,Spring中的所有應用程序上下文都實現(xiàn)了ResourceLoader接口)。
當然剃毒,由于ApplicationContext是一個ResourceLoader病袄,bean也可以實現(xiàn)ApplicationContextAware接口并直接使用提供的應用程序上下文來加載資源,但一般情況下赘阀,最好使用專用的ResourceLoader接口益缠,如果只需要它。 代碼只會耦合到資源加載接口基公,可以將其視為實用程序接口幅慌,而不是整個Spring ApplicationContext接口。
從Spring 2.5開始酌媒,您可以依賴ResourceLoader的自動裝配作為實現(xiàn)ResourceLoaderAware接口的替代方法欠痴。 “傳統(tǒng)”構(gòu)造函數(shù)和byType自動裝配模式(如第5.4.5節(jié)“自動裝配協(xié)作者”中所述)現(xiàn)在能夠分別為構(gòu)造函數(shù)參數(shù)或setter方法參數(shù)提供ResourceLoader類型的依賴項。 為了獲得更大的靈活性(包括自動裝配字段和多參數(shù)方法的能力)秒咨,請考慮使用新的基于注釋的自動裝配功能喇辽。 在這種情況下,只要有問題的字段雨席,構(gòu)造函數(shù)或方法帶有@Autowired注釋菩咨,ResourceLoader就會自動裝入一個期望ResourceLoader類型的字段,構(gòu)造函數(shù)參數(shù)或方法參數(shù)陡厘。 有關(guān)更多信息抽米,請參見第5.9.2節(jié)“@Autowired”。
6.6 Resources as dependencies
如果bean本身將通過某種動態(tài)過程確定并提供資源路徑糙置,那么bean使用ResourceLoader接口加載資源可能是有意義的云茸。 以某種模板的加載為例,其中所需的特定資源取決于用戶的角色谤饭。 如果資源是靜態(tài)的标捺,那么完全消除ResourceLoader接口的使用是有意義的,只需讓bean公開它需要的Resource屬性揉抵,并期望它們被注入到它中亡容。
然后注入這些屬性變得微不足道的是,所有應用程序上下文都注冊并使用特殊的JavaBeans PropertyEditor冤今,它可以將String路徑轉(zhuǎn)換為Resource對象闺兢。 因此,如果myBean具有Resource類型的模板屬性戏罢,則可以使用該資源的簡單字符串進行配置屋谭,如下所示:
<bean id="myBean" class="...">
<property name="template" value="some/resource/path/myTemplate.txt"/>
</bean>
請注意,資源路徑?jīng)]有前綴龟糕,因為應用程序上下文本身將用作ResourceLoader戴而,資源本身將通過ClassPathResource,F(xiàn)ileSystemResource或ServletContextResource(根據(jù)需要)加載翩蘸,具體取決于上下文的確切類型所意。
如果需要強制使用特定的資源類型,則可以使用前綴催首。 以下兩個示例顯示如何強制ClassPathResource和UrlResource(后者用于訪問文件系統(tǒng)文件)扶踊。
<property name="template" value="classpath:some/resource/path/myTemplate.txt">
<property name="template" value="file:/some/resource/path/myTemplate.txt"/>
6.7 Application contexts and Resource paths
6.7.1 Constructing application contexts
應用程序上下文構(gòu)造函數(shù)(對于特定的應用程序上下文類型)通常將字符串或字符串數(shù)組作為資源的位置路徑(例如構(gòu)成上下文定義的XML文件)。
當這樣的位置路徑?jīng)]有前綴時郎任,從該路徑構(gòu)建并用于加載bean定義的特定資源類型依賴于并且適合于特定的應用程序上下文秧耗。 例如,如果您創(chuàng)建ClassPathXmlApplicationContext舶治,如下所示:
ApplicationContext ctx = new ClassPathXmlApplicationContext("conf/appContext.xml");
bean定義將從類路徑加載分井,因為將使用ClassPathResource车猬。 但是,如果您按如下方式創(chuàng)建FileSystemXmlApplicationContext:
ApplicationContext ctx =
new FileSystemXmlApplicationContext("conf/appContext.xml");
bean定義將從文件系統(tǒng)位置加載尺锚,在這種情況下相對于當前工作目錄珠闰。
請注意,在位置路徑上使用特殊類路徑前綴或標準URL前綴將覆蓋為加載定義而創(chuàng)建的默認Resource類型瘫辩。 所以這個FileSystemXmlApplicationContext ......
ApplicationContext ctx =
new FileSystemXmlApplicationContext("classpath:conf/appContext.xml");
...實際上將從類路徑加載其bean定義伏嗜。 但是,它仍然是FileSystemXmlApplicationContext伐厌。 如果它隨后用作ResourceLoader承绸,則任何未加前綴的路徑仍將被視為文件系統(tǒng)路徑。