Quantcast
Channel: かずきのBlog@hatena
Viewing all articles
Browse latest Browse all 1387

ASP.NET WebAPIでAPIを作ってJavaScriptから呼ぶまで

$
0
0

ということで、タイトル通りのことをしてみようと思います。空のASP.NETのプロジェクトからいろいろ足していく形でやろうと思います。

プロジェクトの作成とAPIの作成

まず、空のASP.NETのプロジェクトを作ります。

f:id:okazuki:20140102152258p:plain

ASP.NET WebAPIに必要なアセンブリを追加します。特に縛りがない限りは最新を利用したほうがいいのでNuGetからMicrosoft ASP.NET Web API 2 Web Hostをインストールします。ぱっと見た感じ以下のアセンブリが参照に追加されました。

  • Nwetonsoft.Json
  • System.Net.Http
  • System.Net.Http.Formatting
  • System.Web.Http
  • System.Web.Http.WebHost

次にプロジェクトに以下のものを追加します。

  • プロジェクトの右クリックメニューから「追加」→「フォルダ」を選びControllersという名前のフォルダを作成
  • Controllerフォルダの右クリックメニューから「追加」→「クラス」でHelloWorldControllerという名前のクラスを作成

WebAPIのコントローラはApiControllerクラスを継承しないといけないので継承します。

ここまでのコードを以下に示します。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Http; // こいつの追加を忘れずにnamespace HelloWebApi.Controllers
{
    publicclass HelloWorldController : ApiController
    {

    }
}

次に、コントローラを作っただけでは呼ばれないのでAPIが呼ばれるようにルーティングの設定を行います。Global.asax(グローバル アプリケーション クラス)を作成して、Application_Startメソッドに以下の定義を追加します。

using System.Web.Http; // これを頭に追加protectedvoid Application_Start(object sender, EventArgs e)
{
    GlobalConfiguration.Configure(config =>
        {
            config.Routes.MapHttpRoute(
                name:"DefaultApi",
                routeTemplate:"api/{controller}/{id}",
                defaults:new { id = RouteParameter.Optional });
        });
}

routeTemplateで使用している{controller}や{id}は予約語みたいなもので、コントローラ名やURLに含まれるリソースを一意に識別するためのidを指定するためのプレースホルダーみたいなものだと思っておけばOKです。自分でいろいろ細かくカスタマイズすることもできます。詳しくは味噌先生の以下の記事を参照してみてください。

プロジェクトの新規作成のときにWebAPIを使うようにしている場合は、参照設定や、ルートの設定はすでにされています。Application_StartメソッドからWebApiConfigクラスのメソッドが呼ばれていて、そのなかで上記のようなコードが記載されているはずなので確認してみてください。

APIを作ってブラウザから叩いてみよう

APIのControllerクラスは作りましたが、中身がからっぽなので、簡単に以下のような記述を足してGETメソッドに対応するものを作ります。

// /api/HelloWorldpublicstring Get()
{
    return"Hello world";
}

実行してブラウザのURLでhttp://localhost:ポート番号/api/HelloWorldというURLにアクセスすると以下のようなJSONファイルをダウンロードできるはずです。

"Hello world"

では、ブラウザから叩いてみます。生のJavaScriptから叩くのは正直つらいのでNuGetからjQueryをインストールします。プロジェクトにDefualt.htmlという名前のHTMLファイルを作成して、以下のように書きます。jQueryのajaxメソッドで単純にHelloWorldのAPIを叩いて結果をspanの中に流し込んでいます。

<!DOCTYPE html><html xmlns="http://www.w3.org/1999/xhtml"><head><metahttp-equiv="Content-Type"content="text/html; charset=utf-8"/><title></title></head><body><h1>Hello WebAPI</h1><div><!-- ボタンを押すとAPIを呼ぶ --><buttononclick="callHelloWorld()">GET /api/HelloWorld</button><br/><spanid="helloWorldResultPlaceHolder">ここにHelloWorldAPIの結果が入ります</span></div><scriptsrc="Scripts/jquery-2.0.3.min.js"></script><scripttype="text/javascript">function callHelloWorld(){// jQueryを使って呼ぶだけ            $.ajax("/api/HelloWorld").then(function(r){                $("#helloWorldResultPlaceHolder").text(r);});}</script></body></html>

実行すると、以下のような画面が表示されます。

f:id:okazuki:20140102163620p:plain

ボタンを押してしばらくすると、APIから返された文字列が画面に表示されます。

f:id:okazuki:20140102163722p:plain

POSTのメソッドも作ってみよう

次にPOSTのメソッドを受け取るAPIを作ってみます。こいつは、フォームのテキストボックスに入力した内容を送って、それにHello worldをくっつけて返すものにします。POSTで単純に文字列の引数を受け取るだけの方法がちょっとわからなかったので妥協してオブジェクトを受け取るようにしました・・・。

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Http;

namespace HelloWebApi.Controllers
{
    publicclass HelloWorldController : ApiController
    {
        // /api/HelloWorldpublicstring Get()
        {
            return"Hello world";
        }

        // POST /api/HelloWorldpublicstring Post(Data data)
        {
            return data.Name + " Hello world";
        }
    }

    /// <summary>/// JSONのデータの入れ物/// </summary>publicclass Data
    {
        publicstring Name { get; set; }
    }
}

JavaScriptの呼び出し側は以下の通り。

<div><inputtype="text"id="inputText" /><buttononclick="callPostMethod()">POST /api/HelloWorld</button><br /><spanid="helloWorldPostResultPlaceHolder">ここにHelloWorldAPI(POST)の結果が入ります</span></div><scripttype="text/javascript">function callPostMethod(){var data = {};        data.name = $("#inputText").val();// jQueryを使って呼ぶだけ        $.ajax("/api/HelloWorld", { type: "POST", data: data }).then(function(r){            $("#helloWorldPostResultPlaceHolder").text(r);}, function(e){alert("error: " + e);});}</script>

ちなみに、戻り値もオブジェクトの形にしたい場合は以下のようにします。JavaScriptからアクセスしたときに不自然な名前にならないように、JsonProperty属性をつけて小文字はじまりの名前を指定してあげるとよさげ。

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Http;

namespace HelloWebApi.Controllers
{
    publicclass HelloWorldController : ApiController
    {
        // /api/HelloWorldpublicstring Get()
        {
            return"Hello world";
        }

        // POST /api/HelloWorldpublic Data Post(Data data)
        {
            returnnew Data { Name = data.Name + " Hello world" };
        }
    }

    /// <summary>/// JSONのデータの入れ物/// </summary>publicclass Data
    {
        [JsonProperty(PropertyName = "name")]
        publicstring Name { get; set; }
    }
}

JavaScriptは以下のようになります。

function callPostMethod() {
    var data = {};
    data.name = $("#inputText").val();
    // jQueryを使って呼ぶだけ
    $.ajax("/api/HelloWorld", { type: "POST", data: data }).then(function (r) {
        $("#helloWorldPostResultPlaceHolder").text(r.name);
    }, function (e) {
        alert("error: " + e);
    });
}

まとめ

Postメソッドをstring Post(string name)みたいにしてJSから呼ぶ方法はどうやるんだろう。[FromBody]とかつけてみたりしたけどあかんかった。


Viewing all articles
Browse latest Browse all 1387

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>