Rails考古学：WebAPIを取り巻く環境の変化とRailsの対応

去年調べごとしたときのメモ書きをせっかくなので公開。あまり真に受けずゆるい読み物としてお楽しみください。

 Rail 1.0から干支を一回り
常に進化し、アップグレード地獄を引き起こしながらも 環境の変化に適応し続けてきたRails
今回はWebAPIに注目して時代の流れを追いながらRailsはどうだったかみていきたいと思います。
 ※僕の観測範囲と憶測によるものなので勘違いや抜けなどあればご指摘頂けるとありがたいです

| 年 | Railsバージョン | 機能 |
| --- | ------------- | ----- |
| 2005 | 1.0～1.2 | ActionWebService (XML-RPC, SOAP Server / Client ) |
| 2007 | 1.2～    | resources routes (REST) |
| 2007 | 2.0～3.2 | ActiveResource (REST API / ～3.0 XML / 3.1～ JSON ) |
| 2009 | 2.3のみ   | Rails Metal |
| 2010 | 3.0～    | Metal controller / ActionDispatch::ParamsParser |
| 2016 | 5.0～    | Rails API / Action Cable / parameter_parsers |

# APIの時代背景

## 2000年前後～

- XML-PRC
  - プロトコル
  - システム間連携や企業間取引などが中心
  - SOAP
    - WSDL: Web Services Description Language
  - Blogger API
  - MetaWeblog
    - https://codex.wordpress.org/XML-RPC_MetaWeblog_API
- REST
  - 設計思想
  - REST は 2000年にカリフォルニア大学 Irvine 校 (University of California, Irvine) の Roy Fielding による博士論文「Architectural Styles and the Design of Network-based Software Architectures」の中で最初に紹介されましたが、その時には REST はそれほど注目されませんでした
    https://www.ibm.com/developerworks/jp/webservices/library/ws-restful/index.html
- RSS 1.0

## 2005年頃～

- Web 2.0
  - [ティム・オライリー](https://ja.wikipedia.org/wiki/%E3%83%86%E3%82%A3%E3%83%A0%E3%83%BB%E3%82%AA%E3%83%A9%E3%82%A4%E3%83%AA%E3%83%BC)によって提唱された概念であり、狭義には、旧来は情報の送り手と受け手が固定され送り手から受け手への一方的な流れであった状態が、送り手と受け手が流動化し、誰もが[ウェブサイト](https://ja.wikipedia.org/wiki/%E3%82%A6%E3%82%A7%E3%83%96%E3%82%B5%E3%82%A4%E3%83%88)を通して、自由に情報を発信できるように変化した[ウェブ](https://ja.wikipedia.org/wiki/%E3%82%A6%E3%82%A7%E3%83%96)の利用状態のこと。
    https://ja.wikipedia.org/w/index.php?title=Web_2.0&oldid=64283976
  - ブログの台頭
- マッシュアップ
  - **マッシュアップ**（Mashup）とは、[ウェブ](https://ja.wikipedia.org/wiki/World_Wide_Web)上に公開されている情報を加工、編集することで新たなサービスとすること。
    マッシュアップの語源は異なる音源からトラックの一部をそれぞれ取り出してミックスし、一つの曲にする音楽の手法である。ウェブにおけるマッシュアップも同様に複数の情報源からの情報から関連のあるものだけを取り出して加工し、一つのウェブサービスとして仕立てあげる。
    マッシュアップが注目されるようになったのはさまざまな企業や団体が所有する[データベース](https://ja.wikipedia.org/wiki/%E3%83%87%E3%83%BC%E3%82%BF%E3%83%99%E3%83%BC%E3%82%B9)を公開する[WebAPI](https://ja.wikipedia.org/wiki/Web%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9)を整備するようになったためである。これにより情報技術に対する深い造詣がなくとも新たなサービスを立ち上げることができるようになった。
- AJaxの発見（2005）
  - GoogleMapなどによりJavaScriptによる非同期通信の有用性が認識された
- RESTをWeb APIに適用する考え方
  - 2006年にWEB+DB Pressでも特集が組まれはじめた
    - Web APIを用いれば，構築中のWebアプリケーションにGoogleやYahoo!の機能を簡単に盛り込むことができます。また，RESTというWebアプリケーション／Webサービスのためのアーキテクチャスタイルは，HTTPとURIの正しい使い方を教えてくれます。
      http://gihyo.jp/magazine/wdpress/archive/2006/vol32
  - RESTful API
    - RESTの設計原則をWeb APIに適用したもの
    - オライリー本『RESTful Webサービス』
    - 複雑で重厚なXML-RPC/SOAPよりも開発しやすいREST
    - 複数のRESTfulアプリケーションによる分散システム
  - Twitter API
    - 2016年サービス開始
    - 当初から閲覧・投稿などの仕組みの多くをAPIで公開し話題に。多くのクライアントアプリが登場
- Atom Publishing Protocol（2007）
  - http://gihyo.jp/dev/feature/01/atompub
- OpenSocial API（2007）
  - SNSのためのWeb APIの標準規格としてGoogleがリリース
- OAuth 1.0（2008）
  - APIアクセス権限の委譲についての標準規格を作ろうという流れ
- HATEOAS（2008?）
  - RESTful APIへの制約
    - Hypermedia as the Engine of Application State (HATEOAS) is a constraint of the REST application architecture that distinguishes it from other network application architectures.
      https://en.wikipedia.org/w/index.php?title=HATEOAS&oldid=795761076
- JSON Schema draft 1 (2009)
  - [適切なJSONか調べるためのJSON Schemaを試す](http://news.mynavi.jp/articles/2010/11/29/json-schema/)

## 2010年頃～

- スマートフォンの台頭（日本）
  - 2008年のiPhone 3G、2010年のSO-01Bなどを皮切りにiOS/Android端末が急速に普及
  - スマートフォンアプリとサーバとの間をつなぐWeb APIの必要性増大
- Facebook Graph API 1.0（2010）
  - RESTful
  - それまでもWebAPIはあったがRESTfulではなかった
- 『マイクロサービス』という言葉が一人歩きをはじめる
- GraphQL（2015）
- OpenAPI（2016）
  - [RESTful APIの記述標準化を目指す「Open API Initiative」をマイクロソフト、Google、IBMらが立ち上げ。Swaggerをベースに](http://www.publickey1.jp/blog/15/open_api_initiative.html)
  - [スキーマファースト開発のススメ](https://blog.onk.ninja/2017/09/21/schema_first_development)

# Ruby on RailsでのAPIサポート

## ActionWebService

- Rails 1.0～1.2
- 略してAWS（Amazon Web Service登場は2006年）
- Railsアプリケーションにおいて、SOAPプロトコルとXML-RPCプロトコルをサポート（『RailsによるアジャイルWebアプリケーション開発第2版』より引用）
  - RailsのブログアプリケーションにBlogger APIやmetaWeblog APIのサポートを追加
  - 独自のAPIを実装し、.NET開発者がAWSで生成されたWSDLからそのAPIを使うためのクラスを生成できるようにする
  - SOAPバックエンドとXML-RPCバックエンドを同じコードでサポートする
- このプロシージャ呼び出しがあったらこのコードを呼ぶみたいな規約を整備した（うろおぼえ）

## resources

- Rails 1.2
- RESTに対応するインタフェースの直接のサポートが追加されました。このバージョンでは、resourcesと呼ばれる、ルート機能のマクロの一種が追加されています。（『RailsによるアジャイルWebアプリケーション開発第2版』より引用）
  - RESTfulなルート一式を作成
    - 各RESTfulアクションに対して1つのアクション
- `respond_to`ブロック
  - リクエストした形式に基づくレスポンスの種類の選択

## ActiveResource

- Rails 2.0～3.2
- ネットワークを介してリモートのモデルに接続して利用する
- Railsのresourcesの作法に沿って作られたRESTful API
  - そうでない場合は設定を書くことで（ある程度）対応できる
- アプリケーションを超えてActiveRecordと同様に扱える

## Rails Metal

- Rails 2.3 でcgiからRackベースに変更した際に抽象化レイヤとして導入された
  - `Rails::Rack::Metal`
  - Rack middleware あるいはRackアプリケーションをRailsに実装できるようになった
- RailsのroutingやControllerをbypassして高速化する
- Rails 3.0からは、Rackミドルウェアへの対応や、`config/routes.rb`でRackアプリケーションをマウントできるようになったので不要になった
  - Since Rails 3 is closer to Rack, the Metal abstraction is no longer needed.
    https://github.com/rails/rails/commit/ed34652d1aca148fea61c5309c1bd5ff3a55abfa
  - `Rails::Rack::Metal`が無くても、POROやSinatraなどで書けるようになったということ

## Metal controller

- Rails 3.0～
- Rails Metalに替わって、最も簡単なControllerとして`ActionController::Metal`が追加された
  - ActionController::Metal is the simplest possible controller, providing a valid Rack interface without the additional niceties provided by ActionController::Base.
    http://api.rubyonrails.org/v5.1.4/classes/ActionController/Metal.html
  - コールバックやContent-Type制御、`render`、HTTP認証など`ActionController::Base`の多くの基本的な機能を省いたもの
    - モジュールの読み込みやビュー層を省略して高速化
    - `ActionController::Base`の親クラスである

## ActionDispatch::ParamsParser

- Rails 3.0～4.2
- Content-Typeに従ってリクエストボディのパーサーを選択させる機能
- Web APIで生のJSONやXMLをPOSTで受け、paramsでアクセスできるようになった
  - それまでは`request.body.read`で生の
- Rails 5.0からは`ActionDispatch::Request`が受け持つようになった（parameter_parsers）

## Rails API

- Rails 5.0 でコアにマージされた
- 通常のRailsアプリケーションからビュー層とビューに関係の深いいくつかのmiddlewareを取り除いて高速化を狙うというもの
  - `ActionController::API`は`ActionController::Base`と同じく`ActionController::Metal`の子クラス
- Metal Controllerと比べて、キャッシュやHTTPレスポンス、HTTP認証、URLヘルパーなどRailsらしい便利機能はそのまま

## Action Cable

- WebSockets


# 最近の細々したもの

## ActionDispatch::IntegrationTest.register_encoder

- Rails 5.0
- `ActionDispatch::Request.parameter_parsers`とあわせて、Integration TestでAPIリクエスト＆応答のテストを書きやすくなった
  - `JSON.parse(response.body)`などのようにする必要がなくなった

# その他

- 仕様の文書化
  - いろいろな試み
    - JSON Schema
    - Open API
  - Rails標準としてこれ、というのは今のところ無い
    - Gemsはありそう
      - Railsの外の世界とのやりとりになるので、Railsコアとして何かやるのはちょっと違うのかも？どうなのかな
      - Rails API などで基盤としては整えた感じ、あとの実装は案件によりけり
      - Rails中心で進められるプロジェクトかどうかでどう進めるかがちがう
      - Rails 中心ならRails RESTful規約でよいとおもう


# 自由な働き方をしたいRailsエンジニア募集

当社は自由に働けることを何より重視しているRuby on Rails受託会社です。 

完全リモート、地方在住OK、完全フレックスで働きたいRailsエンジニアを募集中です。

週3日ぐらいからでも働けて、好きな日に開発できます。

一緒にRuby/Rails開発をしませんか？

[自宅で黙々と開発したいRailsエンジニアを募集！フリーランスもOK！ - タケユー・ウェブ株式会社のWeb エンジニア中途・契約・委託の求人 - Wantedly](https://www.wantedly.com/projects/99879)