APIドキュメントを支える技術

最近のウェブ開発では各機能ごとをAPIでつなぎ込む時代になっています。
そのため、各チームが開発をしていく上で、
他のチームにAPIの仕様を伝える方法をきちんとまとめておく必要が出てきています。

そんな中でAPIドキュメントにどのような役割が求められていて
どのような選択肢があるか、一旦自分の把握している知識をまとめています。

(ここで書いているAPIは、httpでアクセスしたら、JSON形式でレスポンスを返すウェブサービスのAPIを指しています)

# APIドキュメントを用意する上で、すぐにぶつかる壁

APIドキュメントを用意する場合に、何も考えずにExcelやwikiにまとめると、早い段階で **メンテナンスのコスト** の問題にぶつかります。

>『APIドキュメントを書く時間がない』
>『本当にドキュメント通りの結果が返ってくるか、試してみないとわからない』
>『実際に返ってくるAPIとレスポンスが違う』
>『ドキュメントはあるが、まだ実際に動くものがウェブサーバに実装されていない』

などです。APIを中心としたウェブサービスを開発していると
早い段階で、これらを出来るだけ少ないコスト、可能ならば一箇所の修正ですべてを対応できればと思うようになります。

そのコストを可能な限り下げるために、今のところ以下のようなライブラリであったり、サービスがあります。

* [swagger](http://swagger.io/)
* [API Blueprint](https://apiblueprint.org/)
* [JSON Schema](http://json-schema.org/)

それぞれ主としている機能は違いますが、周辺のライブラリで色々な用途に利用することができます。

# 各必要な機能

APIドキュメントで必要となるもの、もしくはあったら便利な機能に以下のような項目があります。

* ドキュメント
* クライアント化
* バリデーション
* モックサーバ

それぞれの用途と、上で挙げたツールでどのように実現していけるかを記載していきます。

## ドキュメント

他のチームの人やiOSやAndroid開発の人向けが参照する資料です。
主な用途としては、以下のようなものが挙げられます。

* エンドポイントの説明
* エンドポイントの内容の説明
* エンドポイントに使えるパラメータの説明

swaggerは[Swagger Editor](http://editor.swagger.io/)というエディタが用意されており、そこでYAMLを編集することでドキュメントを作成することができます。
![image](https://qiita-image-store.s3.amazonaws.com/0/3163/6b5399c0-7103-9762-1d52-500956a29742.png)
http://editor.swagger.io/

閲覧には[Swagger UI](https://github.com/swagger-api/swagger-ui)を利用します。

API Blueprintは、決められたmarkdown形式でドキュメントを記載することで、他の使い方ができるようになります。
![image](https://qiita-image-store.s3.amazonaws.com/0/3163/7dfe6da4-b454-227a-8d48-aba8afe42b27.png)
https://apiblueprint.org/#full_api

また、[apiary](http://apiary.io/)でサイト上で管理することも可能です。

JSON Schemaの場合は、[Prmd](https://github.com/interagent/prmd)などを使うことで、JSON Schemaを構造の定義+ドキュメントにすることができます。
Prmdは、markdownやhtml出力に対応しています。htmlのテンプレートはerbで書かれており、テンプレートのカスタマイズは難しくありません。

## クライアント

* ドキュメントから実際にAPIを送信するのに利用します

swaggerの場合、[Swagger UI](https://github.com/swagger-api/swagger-ui)で、ドキュメントに合わせたパラメータでリクエストを送信して結果を確認することができます。
![image](https://qiita-image-store.s3.amazonaws.com/0/3163/35790e33-7ab2-9e23-da6b-0f445802c1bf.png)

API Blueprintの場合、[Blueman](https://github.com/pixelfusion/blueman)を使えば、API BluePrintから[Postman](https://chrome.google.com/webstore/detail/postman-rest-client/fdmmgilgnpjigdojojpjoooidkmcomcm)用のJSONを出力し、Postman経由でリクエストが可能になります。

## バリデーション

* APIの出力の構造をチェックし、ドキュメントと実際のフォーマットの差異を無くします

JSON SchemaはJSONの構造をチェックするためのものです。

様々な言語でバリデーション用のライブラリが用意されています
![image](https://qiita-image-store.s3.amazonaws.com/0/3163/7dd78cd6-e6c6-8b6f-69b5-751db7a09836.png)
http://json-schema.org/implementations.html

API Blueprintの場合は、[dredd](https://github.com/apiaryio/dredd)を使えば、Blueprintの定義のスキーマが正しいかを確認することが出来ます。
![screen.gif](https://qiita-image-store.s3.amazonaws.com/0/3163/9c7dd1f4-2b8d-fbdc-8afd-d6fd644556fc.gif)

## モックサーバ

初期のプロトタイプ時に、サーバーの本実装が終わっていない場合や、認証などを省略して、アクセスを確認したい場合に、ドキュメントと同じJSONを返すサーバーを用意したい場合があります。

[api-mock](https://github.com/localmed/api-mock)は、API Blueprintを元に、記載されたドキュメントをそのままhttpサーバーとして立ち上げることが出来ます。

Swagger Editorには、Generate Serverというものがあり、そこでnode.jsなどのパッケージをダウンロードすると、記載したレスポンスを返すサーバースクリプトが出てきます。

![image](https://qiita-image-store.s3.amazonaws.com/0/3163/d976a0f9-d3e3-b5a4-166c-7743e055bb6b.png)
今のところこの機能はAlphaのようです。

# まとめ: どれを使うべきか

実のところ、どれも一長一短があります。

|               | メリット                                                                       | デメリット                                                                                                                                                   |
|---------------|--------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------|
| swagger       | swaggerだけでクライアントとドキュメントとモックサーバをまかなえる            | ドキュメント確認するのになんでも良いもののウェブサーバー立ち上げる必要がある。APIに独自仕様の認証などがあった場合にswagger UIをカスタマイズする必要がある |
| API Blueprint | apiary.ioで外部サービスのみで記載を完結できる                                | Markdown拡張にクセがあり、それを覚えるのが大変。細かいフィールドのバリデーションをかけることができない                                                    |
| JSON Schema   | 元々がバリデーションのためのものなので、フィールドの値を細かくチェックが可能 | あくまもバリデーションのためのものなので、ドキュメント化やモック化する場合は、自力でフローを実装しなければいけない。                                       |

**柔軟性が高いのはJSON Schema**で、**導入コストが低いのはswagger**です。

API Blueprintは、様々なツールがあるものの、一番最初に書くことになるMarkdown拡張を覚えるコストが意外にかかったので、自分が入っていたプロジェクトでは、API BlueprintからJSON Schema+Prmdに変更したことがあります。

またE2Eテストを行う場合にも、柔軟性が高いのがJSON Schemaです。swaggerはe2eテストの用途から外れてしまいます。

goのフレームワークの[revel](http://revel.github.io/)では、E2Eテストが用意されており、このレスポンス結果をJSON Schemaを使ってバリデーションを行うようにしていました。それで、テストを書く => JSON Schemaを書く => 結果、ドキュメントができる という流れを作っていました。

(正確には、Prmdからサービス全体のschema.jsonを作成できるので、それを元に各エンドポイント用のschemaを作成し、それでバリデーションを行っていました)

用途や何に重点を置くか、どれを使うかキチンと検討しておかないと管理がズサンになります。
それを避けるために、ひとつで複数の役割を担うべきだと思います。