しばやん雑記

Azure とメイドさんが大好きなフリーランスのプログラマーのブログ

クロスドメイン通信に必要なヘッダを出力する属性

XMLHttpRequest Level 2 と XDomainRequest でクロスドメイン通信を行うためには Access-Control-Allow-Origin などのヘッダを返す必要があります。

こういうのはアクションフィルタで実装するに限りますね。というわけで AccessControl というそれっぽいような属性を作りました。

[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = false)]
public class AccessControl : ActionFilterAttribute
{
    public string AllowOrigin { get; set; }
    public string AllowHeaders { get; set; }
    public string AllowMethods { get; set; }

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        var response = filterContext.RequestContext.HttpContext.Response;

        if (!string.IsNullOrEmpty(AllowOrigin))
        {
            response.Headers["Access-Control-Allow-Origin"] = AllowOrigin;
        }

        if (!string.IsNullOrEmpty(AllowHeaders))
        {
            response.Headers["Access-Control-Allow-Headers"] = AllowHeaders;
        }

        if (!string.IsNullOrEmpty(AllowMethods))
        {
            response.Headers["Access-Control-Allow-Methods"] = AllowMethods;
        }

        base.OnActionExecuting(filterContext);
    }
}

使い方は普通のアクションフィルタと同じです。グローバルフィルタとして登録しても大丈夫。

[AccessControl(AllowOrigin = "*", AllowHeaders = "X-Requested-With")]
public ActionResult Details()
{
    return Json(new { data = "hauhau" }, JsonRequestBehavior.AllowGet);
}

これだけでクロスドメイン通信が可能なアクションが完成です。IE9 の F12 開発者ツールでレスポンスヘッダを確認してみます。

ちゃんとヘッダが出力されていますね。