カスタムRouteBase
実装と[OutputCache]
. URL が特定のコンテンツ ページにマッピングされる CMS があります。各タイプのコンテンツ ページは、異なるコントローラー (および異なるビュー) によって処理されます。URL は完全に無料で、さまざまなコントローラーが必要なため、「キャッチオール」ルートは使用できません。そのため、データベースを呼び出してすべての URL を検索するカスタム RouteBase 実装を構築します。データベースは、使用するコントローラとアクションを (コンテンツ ページ タイプに基づいて) 認識しています。
これはうまく機能します。
ただし、これを [OutputCache] 属性と組み合わせると、出力キャッシュは機能しません (ページは引き続き機能します)。[OutputCache] が「通常の」ルートで機能することを確認しました。
outputcaching をデバッグするのは非常に困難です。属性はそこにありますが、機能しません...これにアプローチする方法のアイデアは、正しい答えと同様に大歓迎です!
コントローラーは次のようになります。
public class TextPageController : BaseController
{
private readonly ITextPageController textPageController;
public TextPageController(ITextPageController textPageController)
{
this.textPageController = textPageController;
}
[OutputCache(Duration = 300)]
public ActionResult TextPage(string pageid)
{
var model = textPageController.GetPage(pageid);
return View(model);
}
}
カスタム ルートは次のようになります。
public class CmsPageRoute : RouteBase
{
private IRouteService _routeService;
private Dictionary<string, RouteData> _urlsToRouteData;
public CmsPageRoute(IRouteService routeService)
{
this._routeService = routeService;
this.SetCmsRoutes();
}
public void SetCmsRoutes()
{
var urlsToRouteData = new Dictionary<string, RouteData>();
foreach (var route in this._routeService.GetRoutes()) // gets RouteData for CMS pages from database
{
urlsToRouteData.Add(route.Url, PrepareRouteData(route));
}
Interlocked.Exchange(ref _urlsToRouteData, urlsToRouteData);
}
public override RouteData GetRouteData(System.Web.HttpContextBase httpContext)
{
RouteData routeData;
if (_urlsToRouteData.TryGetValue(httpContext.Request.Path, out routeData))
return routeData;
else
return null;
}
public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
{
return null;
}
private RouteData PrepareRouteData(ContentRouteData contentRoute)
{
var routeData = new RouteData(this, new MvcRouteHandler());
routeData.Values.Add("controller", contentRoute.Controller);
routeData.Values.Add("action", contentRoute.Action);
routeData.Values.Add("area", contentRoute.Area);
routeData.Values.Add("pageid", contentRoute.Constraints["pageid"]); // variable for identifying page id in controller method
routeData.DataTokens.Add("Namespaces", new[] { contentRoute.Namespace });
routeData.DataTokens.Add("area", contentRoute.Area);
return routeData;
}
// routes get periodically updated
public void UpdateRoutes()
{
SetCmsRoutes();
}
}
最後まで読んでいただきありがとうございました!