(「こんなふうにAPIつくりたい話」改め)
@tkawa
Sendagaya.rb 2017-12-18
※まだ実装がないので構想(妄想)の話になりますがご了承ください
RubyKaigi 2017
API Development in 2017 onkさん
スキーマ
正直、スキーマの必要性をあまり感じていなかった
特定のフォーマット使えば良い派だったから
でも、HALなどがあまり普及していないところをみると、求められているものはスキーマなのかも
スキーマ
JSON Schema は「JSON の構造を定義できる」だけで、「API として使う JSON」の定義は JSON Schema の上にもう一つレイヤーが必要。
- JSON Schema / Hyper-Schema
- API Blueprint
- OpenAPI (Swagger)
- RAML
だいたい全て
* markdown とか YAML とかの書き易いツールで API 定義を書いたら
* ドキュメントがめっちょ綺麗に出力されて
* mock サーバも勝手にできて
* ドキュメントの HTML 上からでも request/response を実際に投げてチェックできる
例えば Swagger の場合
https://swagger.io/specification/
サンプル
https://github.com/OAI/OpenAPI-Specification/blob/master/examples/v3.0/petstore-expanded.yaml
https://github.com/OAI/OpenAPI-Specification/blob/master/examples/v3.0/uber.yaml
パス、メソッド、パラメータ(型)、レスポンスの構造など
これがそのままAPIドキュメントになりそうな記述。
良いように思えるが…
だからパス、メソッド、パラメータは動的なんだって。
動的にしないと変化させることができない。
一応、「リソースタイプ」についての記述ととらえられなくもない。
パス定義は余計だが、「特定のリソースタイプは特定のパスに置かれる」という制約だと解釈できなくもない。(再利用を阻害するけど)
スキーマは動的に(実行時に)解釈できなければならない
RESTful Web APIs 12章より
しかし、「リソースの抽象セマンティックタイプ」と「私のデータモデルでのクラスの実装の詳細」を混同する強い誘惑があります。HydraコンテキストやODataメタデータドキュメントやWADLドキュメントは、サーバサイドのAPI開発者を誘惑して、標準の語彙を再利用する代わりに、それらの内部データモデルに基づいた1回限りの語彙を自動的に生成させます。
そして、私が第9章で前述した大きな問題があります。これらのドキュメントはあまり頻繁に変更されないので、クライアントサイドのAPI開発者は、APIのアプリケーションセマンティクスの完全な概要を提供することが可能なサービス記述ドキュメントとしてそれらを扱うという誘惑にかられます。ユーザは、Hydraコンテキストに基づいてクライアントコードを生成する誘惑にかられるでしょう。それはコンテキストが変化すると壊れてしまうクライアントコードです。
JSON Hyper-Schema
今までの使い方が間違い
- リソースごとの記述にして、それぞれをリンクさせて実行時に解決できるようにする
- HTMLに対するCSSのように、JSONに対するスキーマ
- JSON Schemaをフォームとしても使う。リクエスト・レスポンスどちらの構造もカバーできる
フォーマットとの組み合わせ
- JSON + JHS
みんなが最初にやる形。でも結局ルールが決まってないのでやりづらい。 - HAL + JHS
HALに欠けているフォームがJHSで補える。コレクションの扱いに難。 - JSON-LD + JHS
JSON-LDでやりたいならなぜHydra使わないの?という話ではある
Railsでの実装アイデア
- JSON Schema をビューテンプレート(app/views)にしてJSONを生成する。
- JSON Schema を assets(app/assets) として asset pipeline にのせる
- JSON Schema を assets(app/javascripts) として Webpack にのせる
JSON Schemaはリソースごとに用意する必要があるため、どこでunify(&参照解決)するか。
react-jsonschema-form
react-jsonschema-form playground
JSON Schema (+ UI Schema) に対応するHTMLフォームを組み立てる React component
すでにこれだけできてるから、可能なのでは
懸念
JSON Schema が本当にフォームの代わりに使えるのか
readonly, default, required, disabled, example(placeholder) みたいなもののサポート
バリデーションのコンテキストが必要?
JSON Schemaのセマンティックボキャブラリ拡張になるのかも。
HTMLでやればいいじゃん
その通り
…だけど、React Native版ができたりすると夢がある