談一談我對Spring Resource的理解

擁抱心中的夢想發表於2018-03-20

一、什麼是Resource

當我們學習Spring時,我們總會在xml中對bean進行宣告,然後再通過下面的程式碼片段來獲取bean。程式碼如下:

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class Context {

  public static void main(String[] args) {
    
    ApplicationContext ctx = new ClassPathXmlApplicationContext("Spring.xml");//1、載入配置檔案
    System.err.println(ctx.getBean("stu").toString());//2、通過配置檔案獲取一個bean並列印

   }
}
複製程式碼

上面第一行程式碼載入了一個資原始檔Spring.xml,這個資原始檔在Spring中屬於Resource的一種。這樣講,Spring把各種型別的檔案,二進位制流都稱之為Resource,只不過對於Spring開發者來說,Resource大多都是xml檔案。

Resource是一個介面,介面裡邊定義了非常多關於檔案的操作策略,比如

  • exists():判斷資源是否存在
  • getURL():獲取資源的URL
  • getFilename():獲取資源的名稱
  • ......(方法非常多,我就不一一列舉了)

Resource 介面是具體資源訪問策略的抽象,也是所有資源訪問類所實現的介面。Resource 介面本身沒有提供訪問任何底層資源的實現邏輯,針對不同的底層資源,Spring 將會提供不同的 Resource 實現類,不同的實現類負責不同的資源訪問邏輯。

非常重要的一點,這也是Spring Resource設計最美妙的地方,那就是Spring 在Resource資源處理上採用啦策略模式,這也是我為什麼上面把Resource介面中的方法稱之為策略的原因了!

如果還不瞭解Java 策略模式的朋友請先自行學習!

二、Spring Resource介面類結構圖

為了更好地理解,在這裡我先放一張策略模式的UML圖,它的具體內容本文不講。

談一談我對Spring Resource的理解

談一談我對Spring Resource的理解

好了!圖片放上去了,那麼策略模式Resource體系上如何體現出來呢?

  • 1、Resource介面相當於我們的策略
  • 2、下面所有的實現類,包括AbstractResource在內都屬於我們的具體策略實現
  • 3、你可能要問,那麼我們的context角色到哪裡去了呢?哈哈,做生意不能忘了我們的老本啊!它就是我們的IOC容器ApplicationContext,它是我們策略模式中最最最具有決策能力的老大了

至於為什麼容器就可以處理我們的Resource,我接下去會說到!

很明顯,Resource是資源的最高抽象,通常我們的應用程式不是都從classpath下去載入我們的xml檔案,我們也可以通過一個URL,URI,InputStream等方式獲取一個資源,這就是Spring把資源的獲取方式和資源的定義之間解耦了!

三、ResourceLoader介面

  • ResourceLoader:該介面實現類的例項可以獲得一個 Resource 例項。。

ResourceLoader 介面裡有如下方法:

  • Resource getResource(String location):該介面僅包含這個方法,該方法用於返回一個 Resource 例項。

ApplicationContext 的實現類都實現 ResourceLoader 介面,而該介面又返回一個Resource例項,因此 ApplicationContext 可用於直接獲取 Resource 例項,這也是為什麼容器就可以處理Resource的原因!

四、策略模式在Spring中使用有什麼優勢

Spring 應用需要進行資源訪問時,實際上並不需要直接使用 Resource 實現類,而是呼叫 ApplicationContext 例項的 getResource() 方法來獲得資源,ApplicationContext 將會負責選擇 Resource 的實現類,也就是確定具體的資源訪問策略,從而將應用程式和具體的資源訪問策略分離開來。

既然有那麼多的優勢,下面就在來解釋我們上面的第一段程式碼,為什麼要使用ClassPathXmlApplicationContext這個類來對資源進行載入?

我們都知道,在容器ApplicationContext下有很多的實現,比如FileSystemXmlApplicationContext,ClassPathXmlApplicationContext,XmlWebApplicationContext,而且我們載入配置檔案的方式通常也是使用它們來進行載入,在Spring中,ApplicationContext的實現類顧名思義也是對應了我們Resource介面的一些實現策略,比如ClassPathResource,FileSystemResource等。

相關文章