RailsでAPIを作るならGrapeを使うってのが定番っぽいので使ってみました。

参考にしたのはこのへん

Grapeの導入〜Hello World

インストールはgem installすればOKです。次にAPIの実装コードを書くファイルを用意します。僕は#{Rails.root}/app/api/api.rbとしました。

 1# app/api/api.rb
 2class API < Grape::API
 3  format :json
 4
 5  resource :items do
 6    get '/hello' do
 7      {hello: "world"}
 8    end
 9  end
10end

そしてroutes.rbにてGrapeをマウントします。

1# routes.rb
2mount API => "/api"

APIは↑で定義したクラス名です。

以上のコードでhttp://domain.com/api/items/helloというURLに対するGETで{hello:"world"}というレスポンスが得られます。これが概要。

mountとプレフィックス

mount API => "/api"としましたがこれは自由に変更できます。mount API => "/"と、ルートを指定できます。

この他にAPIクラスにprefixを付けることができるようになっていて、

1class API < Grape::API
  format :json
2  prefix "api" #この行
3  
4  # ...
5end

↑のように書くとAPIクラスに定義されているAPIのURLにapiと付けられるようになります。

ところで、マウントパスとprefixの両方定義できます。Grapeの使い始めで色々いじっていたときに両方に"api"という値を入れてしまい、/api/api/items/helloというURLでアクセスしなければならないことに気が付かず、/api/items/helloが404になってしまうことにしばらくハマりました。

JbuilderでViewを書く

さきほどのサンプルではレスポンスのjsonを直書きしましたが、プロダクションレベルではさすがにそんなことはしません。htmlのViewを作るときのように別ファイルを使って書きます。

Rails4にはjsonを作るためのjbuilderというgemがデフォルトで含まれるのでそれを使うと良いでしょう。他にはRablというものがあります。

GrapeでJbuilderを使うにはgrape-jbuilderというgemを導入します。

milkcocoa/grape-jbuilder

導入はGemfilegem 'grape-jbuilderでおk。

すると、Grape::Formatter::Jbuilderが使えるようになります。FormatterはAPIクラスで次のように指定できます。

1class API < Grape::API
2  format :json
  formatter :json, Grape::Formatter::Jbuilder
3end

あとはjbuilderを使うAPIにどのViewを対応させるかを書いてあげれば使えるようになります。

app/views/api/items.jbuilderファイルを使う場合、apiのほうにはjbuilder:'items'と書きます。

1# app/api/api.rb
2resource :items do
3  get '/', jbuilder:'items' do
4    @items = Item.all
5  end
6end

Viewのほうには、@itemsを使うようなコードを書くと動的にViewを生成できるようになるわけです。シンタックスは違えど、ERBと同じような感じです。

1# app/views/api/items.jbuilder
2json.items do
3  json.array!(@items) do |item|
    json.(item, :id, :title, ..などなど..)
4  end
5end

例えばこのようなjsonが得られるわけですね。

 1{
 2    "items": [
 3        {
 4            "title": "hogehoge",
 5            "id": 1
 6        },
 7        {
 8            "title": "foobar",
 9            "id": 2
10        }
11    ]
12}