API設計:REST、gRPC、OpenAPI

googleからタイトルについて書かれた記事が出たので読んでいた

cloud.google.com

これらについて自分でもなんとなく考えていたことがあったけれど良い機会なのでまとめておく

記事での注目ポイント

冒頭より引用。

私としては、HTTP を使用する API のビルドには、重要かつ特徴のあるアプローチが 3 つあると考えています。次のようなアプローチです。 1. REST 2. gRPC(および Apache Thrift など) 3. OpenAPI(およびその競合製品)

なるほど、と思うかもしれないが、読み進めていくとRESTについてはこう書かれていた。

このスタイルの API の特徴的な性質は、クライアントが他の情報から URL を構築せず、サーバーから渡された URL をそのまま使用することです

何の話かと思ったけれど、REST APIにはLv3までありこの記事ではLv3のHypermedia controlsまで満たしているもののことを指しているっぽい。

RESTとは何か - Qiita Richardson Maturity Model Hypermedia Controls - REST Framework

つまり、この3つの手法というのは言い換えると

  1. サーバでURLを指定(ビルド)し、クライアントは言われたURLにそのままアクセスを行う
  2. サーバ・クライアント間のやりとりはIDLを用いて定義を行い、クライアントは専用のスタブを使ってリクエストを行う
  3. サーバはOpenAPI等のスキームでHTTPでのやり取りに必要なパラメータを提示し、クライアントはスキームに従ってリクエストのビルドを行う

ということである。 この時点で完全ではない(lv3を満たさない)RESTで構築され、リクエスト方法などをいわゆるAPI Documentationを提示しただけのAPIのビルドは「重要かつ特徴のあるアプローチ」からは外されている (※完全ではないRESTがここでいうRESTから外されているのは、関連する技術としてハイパーリンクを扱うJSON APIやHAL、JSON Hyper Schemaなどが挙げられていることからも推察できる)

APIコモディティ化やマイクロサービス化が進むにつれて、サービス間通信の開発コスト削減が重要視されるようになってきているのが時代の流れとしてあるんだろうな、という感想。

API開発コストのウェイトアップ

今や公開されているAPIを利用する時代から、自分達が日常的にAPIを開発する時代となり、APIが公開されているのは珍しくなくなってきている。

また、マイクロサービスのように一つのサービスを提供するのに複数のサーバが通信を行う必要が出てきたこともあり、サービス間通信の開発コストが重要視されていると思う。

もちろん、リクエストのしやすさなどがAPIを通じたサービスの利用にもつながるなどもありそう。

ここでいうサービス間通信の開発コストとは、

  1. 基礎的な通信の実装
  2. どういった方法で通信を行うのか(HTTP、HTTP2、RPCなど)
  3. クライアントリクエストのビルドの実装

などのこと。

サービスを立ち上げる度に、サービスに対してこれらを一々実装していたのでは開発がスケールしないし、活用もしにくい。

gRPCやOpenAPI、GraphQLなどが注目されている背景には、(完全ではない)RESTの欠点が明らかになるにつれてこういった開発コストに対するIDLとRPCの良さが見直されているんじゃないだろうか。

また、OpenAPIに関してもプログラムによるパースが可能で、クライアントの自動生成がサポートされているため、HTTPに対してのIDLの代用として評価がされていったように思う。

Rails

Railsに触れておくと、railsは完全ではないRESTを採用しているわけだが、これは上記の記事にも

API に gRPC を使用しているか OpenAPI を使用しているかに関係なく、エンティティ指向のスタイルで API を整理している場合、プロシージャ名を標準化している場合(たとえば、作成、取得、更新、削除などの動詞に忠実になることにより)、他の命名規則を設定している場合、REST API の利点の一部(すべてではなく)を得られます

と書かれていて、RailsはCoCによって開発コストの問題を自身に収まる範囲では解決してきた。

ただ、一番最初に書いたようにAPIコモディティ化やマイクロサービス化や、Reactの台頭などによってRailsAPIが外から叩かれる機会が増え、外向けのAPIをどうやって開発・提供していくのかが問われる機会が増えてきたように思う。

(つまりReactを採用してRailsAPIとして使う場合はこれらの問題をどう解決するかと向き合わなければならない)

まとめ

完全なRESTはさておき、OpenAPIやgRPC、上記の記事では触れられていないGraphQLなどが注目されているのは個人的にはIDLとしての用途だと考えている。

これらの技術を採用することで、Interface Description Languageを得ることが最大のメリットであり、また今の時代でAPIを利用する・利用してもらうためのスタートラインでもあると思う。

ではどれを使うのかというと、言いたいことは記事に全部(それ以上も)書いてあるので、記事を読んでくれ。

最後に丸投げなのはどうかと思うけど権威に頼れるときには頼っていきたいので。

現場からは以上です。

おまけ

ちなみにgoogleAPI設計ガイドもおすすめ cloud.google.com