簡介 intro

流量會透過CDN傳遞至Apache網頁伺服器層,該層支援包括Dispatcher在內的模組。 為了提高效能,Dispatcher主要用作快取,以限制發佈節點上的處理作業。
規則可以套用至Dispatcher設定,以修改任何預設快取逾期設定,從而在CDN上產生快取。 Dispatcher也會在符合以下條件時遵循產生的快取過期標頭: enableTTL 會在Dispatcher設定中啟用,這表示它會在重新發佈內容之外重新整理特定內容。

此頁面也說明Dispatcher快取如何失效以及在瀏覽器層級關於使用者端程式庫的快取運作方式。

快取 caching

HTML/文字 html-text

  • 根據預設,瀏覽器會快取五分鐘 cache-control Apache圖層發出的標頭。 CDN也會遵守此值。
  • 透過定義「 」,可停用預設的HTML/文字快取設定 DISABLE_DEFAULT_CACHING 中的變數 global.vars
Define DISABLE_DEFAULT_CACHING

例如,當您的商業邏輯需要微調年齡標題(具有以行事曆日期為基準的值)時,此方法很有用,因為依預設,年齡標題設為0。 話雖如此 關閉預設快取時請小心。

  • HTML可透過定義 EXPIRATION_TIME 中的變數 global.vars 使用AEMas a Cloud ServiceSDK Dispatcher工具。

  • 可在較精細的層級上覆寫,包括獨立控制CDN和瀏覽器快取,並使用下列Apache mod_headers 指令:

    code language-none
    <LocationMatch "^/content/.*\.(html)$">
         Header set Cache-Control "max-age=200"
         Header set Surrogate-Control "max-age=3600"
         Header set Age 0
    </LocationMatch>
    
    note note
    NOTE
    Surrogate-Control標頭會套用至Adobe管理的CDN。 若使用 客戶管理的CDN,視您的CDN提供者而定,可能需要不同的標頭。

    設定全域快取控制標頭或符合寬範圍Regex的類似快取標頭時,請務必謹慎,以免套用至必須私人儲存的內容。 請考慮使用多個指示,以確保以微調的方式套用規則。 話雖如此,如果AEMas a Cloud Service偵測到快取標題已套用至偵測到Dispatcher無法快取的專案,則會移除快取標題,如Dispatcher檔案所述。 若要強制AEM一律套用快取標題,您可以新增 always 選項如下所示:

    code language-none
    <LocationMatch "^/content/.*\.(html)$">
         Header unset Cache-Control
         Header unset Expires
         Header always set Cache-Control "max-age=200"
         Header set Age 0
    </LocationMatch>
    

    確定位於以下位置的檔案: src/conf.dispatcher.d/cache 有以下規則(在預設設定中):

    code language-none
    /0000
    { /glob "*" /type "allow" }
    
  • 防止快取特定內容 在CDN,將Cache-Control標頭設為 私人. 例如,在名為的目錄下,以下內容會防止html內容 secure 從CDN快取:

    code language-none
       <LocationMatch "/content/secure/.*\.(html)$">.  // replace with the right regex
       Header unset Cache-Control
       Header unset Expires
       Header always set Cache-Control "private"
      </LocationMatch>
    
  • 雖然設為私用的HTML內容不會在CDN上快取,但可以在以下情況下在Dispatcher上快取 許可權敏感型快取 已設定,確保僅授權使用者能獲得內容。

    note note
    NOTE
    其他方法,包括 Dispatcher-ttl AEM ACS Commons專案,無法成功覆寫值。
    note note
    NOTE
    Dispatcher可能仍會根據自己的快取內容 快取規則. 若要讓內容確實為私人,請確保Dispatcher不會快取該內容。

使用者端資料庫(js,css) client-side-libraries

  • 使用AEM使用者端程式庫架構時,JavaScript和CSS程式碼會以瀏覽器可無限期快取的方式產生,因為任何變更都會顯示為具有唯一路徑的新檔案。 換言之,會視需要產生參考使用者端資料庫的HTML,讓客戶可在發佈新內容時體驗內容。 若舊版瀏覽器不遵循「不可變」值,則快取控制設為「不可變」,或設為30天。
  • 請參閱區段 使用者端程式庫和版本一致性 以取得其他詳細資訊。

影像和任何足以儲存在Blob儲存空間中的內容 images

對於2022年5月中旬之後建立的計畫(特別是高於65000的計畫ID),預設行為是快取,同時遵循請求的驗證上下文。 舊版程式(程式id等於或小於65000)預設不會快取blob內容。

在這兩種情況下,都可以使用Apache在Apache/Dispatcher層的較精細層級覆寫快取標題 mod_headers 指令,例如:

   <LocationMatch "^/content/.*\.(jpeg|jpg)$">
     Header set Cache-Control "max-age=222"
     Header set Age 0
   </LocationMatch>

在Dispatcher層修改快取標題時,請注意不要快取太廣泛。 請參閱HTML/文字區段中的討論 以上. 此外,也請確定原本要私密儲存(而非快取)的資產並未包含在 LocationMatch 指令篩選器。

儲存在Blob存放區中的JCR資源(大於16KB)通常可由AEM做為302重新導向。 這些重新導向會遭到攔截並隨後導向CDN,而內容會直接從blob存放區傳送。 在這些回應中只能自訂有限的標題集。 例如,若要自訂 Content-Disposition 您應依照以下方式使用dispatcher指示:

<LocationMatch "\.(?i:pdf)$">
  ForceType application/pdf
  Header set Content-Disposition inline
  </LocationMatch>

可在blob回應上自訂的標頭清單為:

content-security-policy
x-frame-options
x-xss-protection
x-content-type-options
x-robots-tag
access-control-allow-origin
content-disposition
permissions-policy
referrer-policy
x-vhost
content-disposition
cache-control
vary

新的預設快取行為 new-caching-behavior

AEM層會根據是否已設定快取標頭及請求型別的值來設定快取標頭。 如果未設定快取控制標題,則會快取公開內容,且驗證的流量會設為私人。 如果設定了快取控制標題,則快取標題保持不變。

快取控制標頭是否存在?
請求類型
AEM將快取標頭設為
公共
Cache-Control: public, max-age=600,不可變
已驗證
Cache-Control: private, max-age=600,不可變
任何
未變更

雖然不建議使用,但您可以設定Cloud Manager環境變數,將新的預設行為變更為遵循舊行為(計畫id等於或小於65000) AEM_BLOB_ENABLE_CACHING_HEADERS 為false。

較舊的預設快取行為 old-caching-behavior

AEM層預設不會快取blob內容。

NOTE
將Cloud Manager環境變數AEM_BLOB_ENABLE_CACHING_HEADERS設定為true,以將較舊的預設行為變更為與新的行為(高於65000的程式ID)一致。 如果程式已上線,請務必確認在變更後,內容會如預期般運作。

現在,在Blob儲存空間中標示為私用的影像無法使用在Dispatcher上快取 許可權敏感型快取. 系統會一律向AEM來源要求影像,並在使用者獲得授權時提供影像。

NOTE
其他方法,包括 dispatcher-ttl AEM ACS Commons專案時,請勿成功覆寫值。

節點存放區中的其他內容檔案型別 other-content

  • 無預設快取
  • 無法設定預設值 EXPIRATION_TIME 用於html/文字檔案型別的變數
  • 透過指定適當的規則運算式,可以使用html/text一節中所述的相同LocationMatch策略來設定快取有效期

進一步最佳化 further-optimizations

  • 避免使用 User-Agent 做為 Vary 標頭。 舊版預設Dispatcher設定(在原型版本28之前)包含該引數,Adobe建議您透過以下步驟將其移除。

    • 在中找到vhost檔案 <Project Root>/dispatcher/src/conf.d/available_vhosts/*.vhost
    • 移除或註解該行: Header append Vary User-Agent env=!dont-vary 來自所有vhost檔案,但default.vhost為唯讀檔案除外
  • 使用 Surrogate-Control 標頭可獨立於瀏覽器快取控制CDN快取

  • 考慮套用 stale-while-revalidatestale-if-error 指示可允許背景重新整理並避免快取遺漏,讓使用者可以快速且新鮮地保留您的內容。

    • 有許多方式可套用這些指示,但新增30分鐘即可 stale-while-revalidate 對於所有快取控制標題來說,這是個不錯的起點。
  • 以下是各種內容型別的範例,在設定自己的快取規則時,這些範例可作為指南。 請仔細考慮並測試您的特定設定和需求:

    • 快取可變的使用者端程式庫資源達12小時,並在12小時後重新整理背景。

      code language-none
      <LocationMatch "^/etc\.clientlibs/.*\.(?i:json|png|gif|webp|jpe?g|svg)$">
         Header set Cache-Control "max-age=43200,stale-while-revalidate=43200,stale-if-error=43200,public" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      
    • 透過背景重新整理來快取不可變的使用者端程式庫資源長期(30天)以避免遺漏。

      code language-none
      <LocationMatch "^/etc\.clientlibs/.*\.(?i:js|css|ttf|woff2)$">
         Header set Cache-Control "max-age=2592000,stale-while-revalidate=43200,stale-if-error=43200,public,immutable" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      
    • 在瀏覽器上快取HTML頁面5分鐘,並在背景重新整理1小時,在CDN上重新整理12小時。 請一律新增Cache-Control標頭,因此請務必確保/content/*底下相符的html頁面為公開頁面。 如果沒有,請考慮使用更具體的規則運算式。

      code language-none
      <LocationMatch "^/content/.*\.html$">
         Header unset Cache-Control
         Header always set Cache-Control "max-age=300,stale-while-revalidate=3600" "expr=%{REQUEST_STATUS} < 400"
         Header always set Surrogate-Control "stale-while-revalidate=43200,stale-if-error=43200" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      
    • 快取內容服務/Sling模型匯出程式json回應達5分鐘,瀏覽器背景重新整理一小時,CDN背景重新整理十二小時。

      code language-none
      <LocationMatch "^/content/.*\.model\.json$">
         Header set Cache-Control "max-age=300,stale-while-revalidate=3600" "expr=%{REQUEST_STATUS} < 400"
         Header set Surrogate-Control "stale-while-revalidate=43200,stale-if-error=43200" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      
    • 使用背景重新整理來長期(30天)快取核心影像元件中的不可變URL,以避免MISS。

      code language-none
      <LocationMatch "^/content/.*\.coreimg.*\.(?i:jpe?g|png|gif|svg)$">
         Header set Cache-Control "max-age=2592000,stale-while-revalidate=43200,stale-if-error=43200,public,immutable" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      
    • 快取來自DAM的可變資源(例如影像和影片)24小時,並在12小時後重新整理背景以避免遺漏。

      code language-none
      <LocationMatch "^/content/dam/.*\.(?i:jpe?g|gif|js|mov|mp4|png|svg|txt|zip|ico|webp|pdf)$">
         Header set Cache-Control "max-age=43200,stale-while-revalidate=43200,stale-if-error=43200" "expr=%{REQUEST_STATUS} < 400"
         Header set Age 0
      </LocationMatch>
      

分析CDN快取命中率 analyze-chr

請參閱 快取命中率分析教學課程 如需有關下載CDN記錄檔及使用控制面板分析網站快取百分比的資訊。

HEAD請求行為 request-behavior

當在AdobeCDN收到資源的HEAD要求時,該資源 經過快取後,該請求會進行轉換,並由Dispatcher和/或AEM執行個體接收為GET請求。 如果回應可快取,則會從CDN提供後續HEAD請求。 如果回應無法快取,則會將後續HEAD請求傳遞給Dispatcher或AEM執行個體(或兩者),所需時間取決於 Cache-Control 總計

行銷活動引數 marketing-parameters

網站URL常包含用來追蹤促銷活動成功的行銷活動引數。

對於在2023年10月或之後建立的環境,為了更好的快取要求,CDN將移除常見的行銷相關查詢引數,特別是符合下列規則運算式模式的引數:

^(utm_.*|gclid|gdftrk|_ga|mc_.*|trk_.*|dm_i|_ke|sc_.*|fbclid)$

如果您希望停用此行為,請提交支援票證。

對於2023年10月之前建立的環境,建議設定Dispatcher設定的 ignoreUrlParams 屬性為 在此處記錄.

忽略行銷引數有兩種可能性。 (其中第一個偏好使用查詢引數來忽略防快取):

  1. 忽略所有引數,並選擇性地允許使用的引數。
    僅限下列範例中 pageproduct 不會忽略引數,並將請求轉送給發佈者。
/ignoreUrlParams {
   /0001 { /glob "*" /type "allow" }
   /0002 { /glob "page" /type "deny" }
   /0003 { /glob "product" /type "deny" }
}
  1. 允許行銷引數以外的所有引數。 檔案 marketing_query_parameters.any 會定義將忽略的常用行銷引數清單。 Adobe將不會更新此檔案。 使用者可依其行銷提供者來擴充。
/ignoreUrlParams {
   /0001 { /glob "*" /type "deny" }
   $include "../cache/marketing_query_parameters.any"
}

Dispatcher快取失效 disp

一般而言,不需要讓Dispatcher快取失效。 實際上,您應該依賴Dispatcher在內容重新發佈時重新整理其快取,並且CDN遵循快取到期標頭。

Dispatcher快取在啟用/停用期間失效 cache-activation-deactivation

和舊版AEM一樣,發佈或取消發佈頁面會從Dispatcher快取中清除內容。 如果懷疑有快取問題,您應重新發佈有問題的頁面,並確保有符合的虛擬主機可用 ServerAlias Dispatcher快取失效所需的localhost。

NOTE
為了讓Dispatcher正確失效,請確定來自「127.0.0.1」、「localhost」、「*.local」、「*.adobeaemcloud.com」和「*.adobeaemcloud.net」的請求都符合,並由vhost設定進行處理,以便提供請求。 您可以依照參照中的模式,在全域比對所有vhost組態中的「*」來執行此工作 AEM原型. 或者,您也可以確保前述清單是由其中一個主機擷取。

當發佈執行個體收到來自作者的新版本頁面或資產時,它會使用排清代理程式來使其Dispatcher上的適當路徑失效。 更新的路徑會與其父項一起從Dispatcher快取中移除,直到某個層級為止(您可以使用 statfileslevel)。

Dispatcher快取明確失效 explicit-invalidation

Adobe建議您仰賴標準快取標頭來控制內容傳送生命週期。 不過,如有需要,可以直接使Dispatcher中的內容失效。

下列清單包含您想要明確讓快取失效的情況(同時選擇性地接聽讓失效完成):

  • 發佈體驗片段或內容片段等內容後,讓參考這些元素的已發佈和快取內容失效。
  • 在參照的頁面成功失效時通知外部系統。

有兩種方式可明確讓快取失效:

  • 偏好使用的方法是使用Author的Sling Content Distribution (SCD)。
  • 另一種方法是使用復寫API來叫用發佈Dispatcher Flush復寫代理程式。

方法因階層可用性、去除重複事件的能力及事件處理保證而異。 下表總結了這些選項:

不適用
階層可用性
去重複化
保證
動作
影響
說明
Sling內容發佈(SCD) API
作者
可能使用Discovery API或啟用 去重複化模式.
至少一次。
  1. 新增
  2. 刪除
  3. 失效
  1. 階層/統計層級
  2. 階層/統計層級
  3. 僅層次資源
  1. 發佈內容並讓快取失效。
  2. 移除內容並讓快取失效。
  3. 讓內容失效而不發佈。
復寫API
發佈
不可能,事件會在每個發佈執行個體上引發。
盡力而為。
  1. 啟用
  2. 停用
  3. 刪除
  1. 階層/統計層級
  2. 階層/統計層級
  3. 階層/統計層級
  1. 發佈內容並讓快取失效。

  2. 從作者/發佈層 — 移除內容並使快取失效。

  3. 從作者階層 — 移除內容並使快取失效(如果從發佈代理程式上的AEM製作層觸發)。

    從發佈階層 — 僅讓快取失效(如果從Flush或Resource-only-flush代理程式上的AEM發佈層觸發)。

與快取失效直接相關的兩個動作是Sling內容發佈(SCD) API失效和復寫API停用。

此外,從表格中,您可以觀察到:

  • 當每個事件都必須得到保證時(例如,與需要精確知識的外部系統同步),就需要SCD API。 如果在失效呼叫時存在發佈層級升級事件,則在每個新發佈處理失效時會引發額外事件。

  • 使用復寫API不是常見的使用案例,但可用於讓快取失效的觸發器來自發佈層級,而非製作層級的情況。 如果已設定Dispatcher TTL,此方法可能會相當實用。

總而言之,如果您想要讓Dispatcher快取失效,建議的選項是使用Author的SCD API失效動作。 此外,您也可以接聽事件,以便觸發後續的下游動作。

Sling內容發佈(SCD) sling-distribution

NOTE
使用下列指示時,請在AEM Cloud Service開發環境中測試自訂程式碼,而不是在本機測試。

使用Author的SCD動作時,實施模式如下:

  1. 從Author編寫自訂程式碼以叫用Sling內容發佈 API,使用路徑清單來傳遞失效動作:
@Reference
private Distributor distributor;

ResourceResolver resolver = ...; // the resource resolver used for authorizing the request
String agentName = "publish";    // the name of the agent used to distribute the request

String pathToInvalidate = "/content/to/invalidate";
DistributionRequest distributionRequest = new SimpleDistributionRequest(DistributionRequestType.INVALIDATE, false, pathToInvalidate);
distributor.distribute(agentName, resolver, distributionRequest);
  • (可選)接聽反映所有Dispatcher執行個體失效的資源事件:
package org.apache.sling.distribution.journal.shared;

import org.apache.sling.discovery.DiscoveryService;
import org.apache.sling.distribution.journal.impl.event.DistributionEvent;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Reference;
import org.osgi.service.event.Event;
import org.osgi.service.event.EventHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import static org.apache.sling.distribution.DistributionRequestType.INVALIDATE;
import static org.apache.sling.distribution.event.DistributionEventProperties.DISTRIBUTION_PATHS;
import static org.apache.sling.distribution.event.DistributionEventProperties.DISTRIBUTION_TYPE;
import static org.apache.sling.distribution.event.DistributionEventTopics.AGENT_PACKAGE_DISTRIBUTED;
import static org.osgi.service.event.EventConstants.EVENT_TOPIC;

@Component(immediate = true, service = EventHandler.class, property = {
        EVENT_TOPIC + "=" + AGENT_PACKAGE_DISTRIBUTED
})
public class InvalidatedHandler implements EventHandler {
    private static final Logger LOG = LoggerFactory.getLogger(InvalidatedHandler.class);

    @Reference
    private DiscoveryService discoveryService;

    @Override
    public void handleEvent(Event event) {

        String distributionType = (String) event.getProperty(DISTRIBUTION_TYPE);

        if (INVALIDATE.name().equals(distributionType)) {
            boolean isLeader = discoveryService.getTopology().getLocalInstance().isLeader();
            // process the OSGi event on the leader author instance
            if (isLeader) {
                String[] paths = (String[]) event.getProperty(DISTRIBUTION_PATHS);
                String packageId = (String) event.getProperty(DistributionEvent.PACKAGE_ID);
                invalidated(paths, packageId);
            }
        }
    }

    private void invalidated(String[] paths, String packageId) {
        // custom logic
        LOG.info("Successfully applied package with id {}, paths {}", packageId, paths);
    }
}
  • (選擇性)在中執行商業邏輯 invalidated(String[] paths, String packageId) 方法。
NOTE
當Dispatcher失效時,不會排清AdobeCDN。 Adobe管理的CDN遵守TTL,因此不需要清除。

復寫API replication-api

以下顯示的是使用復寫API停用動作時的實作模式:

  1. 在發佈層上,呼叫復寫API以觸發發佈Dispatcher Flush復寫代理程式。

無法設定排清代理程式端點,而是預先設定為指向Dispatcher,與隨排清代理程式執行的發佈服務相符。

排清代理程式通常可由根據OSGi事件或工作流程的自訂程式碼觸發。

String[] paths = …
ReplicationOptions options = new ReplicationOptions();
options.setSynchronous(true);
options.setFilter( new AgentFilter {
  public boolean isIncluded (Agent agent) {
   return agent.getId().equals("flush");
  }
});

Replicator.replicate (session,ReplicationActionType.DELETE,paths, options);

使用者端程式庫和版本一致性 content-consistency

頁面由HTML、JavaScript、CSS和影像組成。 建議客戶使用 使用者端資料庫(clientlibs)架構 若要將JavaScript和CSS資源匯入HTML頁面,請考慮JS程式庫之間的相依性。

clientlibs架構提供自動版本管理。 這表示開發人員可以在原始檔控制中籤入JS程式庫的變更,而且當客戶推送其版本時,就可以使用最新版本。 若沒有此工作流程,開發人員必須手動變更參照至新版程式庫的HTML,若相同程式庫共用許多HTML範本,則尤其會造成負擔。

將程式庫的新版本發佈到生產環境時,會更新參考HTML頁面,並包含這些已更新程式庫版本的新連結。 指定HTML頁面的瀏覽器快取過期後,就不必擔心舊程式庫會從瀏覽器快取中載入。 原因是因為重新整理的頁面(來自AEM)現在保證會參考資料庫的新版本。 也就是說,重新整理的HTML頁面會包含所有最新程式庫版本。

此功能背後的機制是序列化雜湊,會附加至使用者端程式庫連結。 這可確保瀏覽器擁有版本控制的唯一URL來快取CSS/JS。 只有在使用者端程式庫的內容變更時,才會更新序列化雜湊。 這表示如果發生不相關的更新(也就是說,不會變更使用者端程式庫的基礎css/js),即使使用新部署,參照仍會維持不變。 反過來,它可確保對瀏覽器快取的中斷較少。

啟用使用者端程式庫的Longcache版本 — AEMas a Cloud ServiceSDK快速入門 enabling-longcache

預設clientlib包含在HTML頁面上看起來像下面的範例:

<link rel="stylesheet" href="/etc.clientlibs/wkndapp/clientlibs/clientlib-base.css" type="text/css">

啟用嚴格的clientlib版本設定時,會將長期雜湊金鑰作為選取器新增至使用者端程式庫。 因此,clientlib參照看起來像這樣:

<link rel="stylesheet" href="/etc.clientlibs/wkndapp/clientlibs/clientlib-base.lc-7c8c5d228445ff48ab49a8e3c865c562-lc.css" type="text/css">

在所有AEMas a Cloud Service環境中,預設會啟用嚴格clientlib版本設定。

若要在本機SDK快速入門中啟用嚴格的clientlib版本設定,請執行以下操作:

  1. 導覽至OSGi Configuration管理員 <host>/system/console/configMgr

  2. 尋找AdobeGraniteHTML庫管理員的OSGi設定:

    • 核取核取方塊,以啟用嚴格版本設定
    • 在標示為的欄位中 長期使用者端快取金鑰,輸入/的值。*;雜湊
  3. 儲存變更。 不需要在原始檔控制中儲存此設定,因為AEMas a Cloud Service會自動在開發、中繼和生產環境中啟用此設定。

  4. 只要使用者端資料庫的內容有所變更,就會產生新的雜湊金鑰並更新HTML參考。

recommendation-more-help
fbcff2a9-b6fe-4574-b04a-21e75df764ab