2012-02-16 13 views
11

使用ASP.NET MVC 3中的[OutputCacheAttribute],您可以輸出緩存,並具有很大的靈活性。利用'VaryByHeader'屬性按主機名桶緩存很有用。例如:具有OutputCacheAttribute子變量的VaryByHeader

[OutputCache(Duration = 60, VaryByHeader = "host")] 
public ActionResult Foo() 
{ 
    return this.View(); 
} 

但是,對於子操作,不能應用'VaryByHeader'。該框架拋出以下異常:

OutputCacheAttribute兒童行動只支持時間, VaryByCustom是,和的VaryByParam值。請不要設置CacheProfile, 位置,NoStore,SqlDependency,VaryByContentEncoding或 VaryByHeader子操作的值。

我的問題是,爲什麼?

爲什麼我們不能在子操作中使用VaryByHeader,因爲它會提供衝突的變化,因爲父操作可能指定了不同的VaryByHeader值?

如果我想根據主機名緩存不同的子動作,這是什麼意思,我該怎麼辦?

+0

只是好奇,做孩子的行爲會導致另一種HTTP GET?也許這個想法的設計者,因爲沒有_second_回發,所以不需要通過不同的http頭緩存。 – 2012-02-26 11:20:13

+0

不,子動作只是同一個請求中的抽象。 – 2012-02-26 21:08:00

回答

13

VaryByHeader影響實際的HTTP響應頭;所以你可能是正確的,MVC團隊阻止這一點,以防止與父母的行動衝突。

要根據主機名緩存,難道你不能使用VaryByCustom?喜歡的東西(免責聲明:沒有試過在所有):

[OutputCache(Duration = 60, VaryByCustom = "host")] 
public ActionResult Foo() 
{ 
    return View(); 
} 

之後(在你的Global.asax.cs)

public override string GetVaryByCustomString(HttpContext context, string arg) 
{ 
    if (arg == "host") 
    { 
     return context.Request.Headers["host"]; 
    } 

    // whatever you have already, or just String.Empty 
    return String.Empty; 
} 
+1

僅通過使用VaryByHeader就可以實現基於主機名的緩存。例如,在2主機名方案中,子動作將被緩存兩次,一次用於主機A,一次用於主機B.您不需要使用VaryByCustom。 (雖然你的方法確實可以工作,並且可能與VaryByHeader的實現非常相似)。 – 2012-02-26 02:57:33

+1

當然,但是因爲你不能在你的ChildAction中使用'VaryByHeader' ... :) – bhamlin 2012-02-27 22:50:06