NancyFxでWebAPIを作るときに必ず参照すべきライブラリ
1年以上ぶりにNancyFxネタ。日本語の情報があまりないので、色々書いて行こうと思います。
ユーザが増えてくれれば嬉しいですね。
さてNancyFxでは、デフォルトでJsonレスポンスを返すことが出来ます。
Get["/json"] = _ => { var data = new { Id = 1, Name = "rabitarochan", BlogUrl = "http://rabitarochan.hatenablog.com/" }; return Response.AsJson(data); };
ブラウザからこのURLにアクセスすると、以下のようなJsonが返ります。
{
Id: 1,
Name: "rabitarochan",
BlogUrl: "http://rabitarochan.hatenablog.com/"
}
よくよく見てみると、キーがC#のプロパティ名と同じUpperCamelCaseとなっていますね。
そのため、JavaScript側でも同じくUpperCamelCaseで扱う必要があります。
ただし、JavaScriptではほとんどの場合、lowerCamelCaseが使われていると思いますので、JavaScript側がちょっと気持ち悪い感じになってしまいます。
できればNancyFxからJsonを返す際に、キーをlowerCamelCaseに変換してくれればベストです。
NancyFxのソースを読んでみましたが、残念ながらキーとなる文字列を変換するオプション等はありませんでした。
(ちなみに、NancyFxは独自のJsonシリアライザを使っています。)
そこでNancy.Serialization.JsonNetの出番です!
リポジトリはこちら。NuGetからもインストール可能です。
https://github.com/NancyFx/Nancy.Serialization.JsonNet
このライブラリは、Jsonレスポンスを返す際のシリアライザとして、C#からJsonを扱う際に一番使われていると思われるライブラリJson.Netを使うように変更してくれるだけのものです。
そして、Json.NetのJsonSerializerクラスを少し変更するだけで、キーをlowerCamelCaseに変換することが可能です!!
設定方法
設定はとても簡単で、シリアライザを継承したクラスを1つ作成することと、それをDIコンテナに登録することだけです。
シリアライザを継承したクラスを作成する
Json.Net用のシリアライザを継承したクラスを作成します。今回と同じ目的の場合は、以下のコードをコピペでOKです。
詳細については、Json.Netのドキュメントを参照してください。
public class CustomJsonSerializer : JsonSerializer { public CustomJsonSerializer() { this.ContractResolver = new CamelCasePropertyNamesContractResolver(); } }
DIコンテナに登録する
Bootstrapperクラスにて、DIコンテナのTinyIocに先ほど作成したクラスを登録します。
public class Bootstrapper : DefaultNancyBootstrapper { protected override void ConfigureApplicationContainer(Nancy.TinyIoc.TinyIoCContainer container) { base.ConfigureApplicationContainer(container); container.Register(typeof(JsonSerializer), typeof(CustomJsonSerializer)); } }
仕組み
Nancy.Serialization.JsonNetは、JsonのシリアライザとしてJson.Netを利用するように変更してくれるプラグインのようなものです。
NancyFxでは、コンテントタイプ毎に任意のシリアライザが登録できる仕組みになっているようです。
(その仕組みまではまだ見ていません。)
デフォルトではJson.NetのJsonSerializerをそのまま使用しますが、BootStrapperクラスにて今回作成したようなクラスを登録してあげることで、そちらのクラスが使用される、ということです。
最初に書いたソースはそのままで同じURLにアクセスすると、ちゃんとlowerCamelCaseに変換されていることが分かります。
{
id: 1,
name: "rabitarochan",
blogUrl: "http://rabitarochan.hatenablog.com/"
}
デシリアライズは??
PostされたJsonをC#のクラスに変換する場合は、UpperCamelCase、lowerCamelCase関係なく変換してくれます。
変換には、NancyFxが提供しているModelBindingという仕組みを利用します。
以下の例では、フォームからPostされたパラメータをクラスに変換し、そのままJsonレスポンスとして返しています。
namespace NancyJsonTest.Modules
{
using Nancy;
using Nancy.ModelBinding; // クラスに変換するための拡張メソッド用。
public class HomeModule : NancyModule
{
// フォーム値用のクラス
class TestForm
{
// input type=text name=userName
public string UserName { get; set; }
// input type=password name=password
public string Password { get; set; }
}
public HomeModule()
{
Get["/json"] = _ => {
var data = new {
Id = 1,
Name = "rabitarochan",
BlogUrl = "http://rabitarochan.hatenablog.com/"
};
return Response.AsJson(data);
};
Post["/json"] = _ => {
var form = this.Bind<TestForm>();
return Response.AsJson(form);
};
}
}
}
まとめ
このライブラリを利用することで、C#とJavaScriptのプロパティ名の違いがほぼ吸収できると思います。
NancyFxでWebAPIを作成するときは、ぜひこのライブラリを利用してみてください。