1. RESTとは何か
(:キャラ通常翻訳編集者注)状態転送REST名はのRepresentational State移転、中国の意味表現です。それは2000年に初めて登場し、ロイ・フィールディングの博士論文、ロイ・フィールディングは、HTTP仕様の主な著者の一人です。彼は論文で述べた:「私の文章この記事の目的は、アーキテクチャ設計は、強力な機能、優れたパフォーマンスを得る、通信に適し理解し、Webベースのアプリケーションソフトウェアを評価するためのアーキテクチャの原則に準拠して、にあります建築制約と原則のセットを指し.RESTアーキテクチャ。「フレームワークとRESTの制約と一致原則は、我々はRESTfulなアーキテクチャを呼び出した場合。
アイデアの後ろに隠れてすることはWeb標準を既存のいくつかのガイドラインと制約を使用して、より良い、RESTfulなWebの既存の機能や能力を使用することである一方、REST自体は、新しい技術、コンポーネントやサービスを作成しません。深くRESTのWeb技術そのものの影響を受けますが、しかし、理論的にはRESTアーキテクチャ・スタイルは、HTTPにバインドされたが、現在唯一のHTTP REST関連のインスタンスをされていません。そこでここでは、REST REST HTTPも通じ達成記述する。
2. RESTfulな理解
RESTfulなアーキテクチャを理解するには、のRepresentational State Transferがこのフレーズの意味は終わりであるかを理解する必要があり、それがどのようなすべての単語何らかの意味です。
ここでは、RESTの原則を組み合わせ、リソース、リソース定義、取得、表現、協会、状態遷移展望について議論する、重要な概念のいくつかであると説明しています。
- リソースとURI
- ユニフォーム・リソース・インターフェース
- リソース表現
- リソースへのリンク
- 転送ステータス
2.1リソースとURI
RESTは、のRepresentational State Transferの略本当に表現何を意味するということでしょうか?実際にリソースを参照します。ものは、限り、参照する必要があるように、それがリソースです。リソースは、それだけで抽象的な概念(例えば値)することができ、物理的(例えば、電話番号)とすることができます。ここでは、リソースのいくつかの例は以下のとおりです。
- ユーザーの携帯電話番号
- ユーザーの個人情報
- GPRSパッケージ加入アップ
- 2つの製品間の依存関係
- ユーザーは、パッケージを申請することができます
- 携帯電話番号の潜在的価値
リソースを識別できるようにするには、それが一意の識別を持っていることが必要である、このユニークな識別はURI(Uniform Resource Identifier)は、Web上です。
URIアドレスはどちらかそれはまた、リソースの名前として見ることができ、資源として見ることができます。情報の一部は、URIを表すために使用されていない場合、それは資源とみなすことができない、それだけにのみ、情報資源の一部とみなすことができます。URIの設計は、ニーズを与える形で直感に関連するアドレス可能な、自己記述の原則に従うべきです。ここではgithubのサイトで、例えば、いくつかのかなり良いURIを与えます:
- https://github.com/git
- https://github.com/git/git
- https://github.com/git/git/blob/master/block-sha1/sha1.h
- https://github.com/git/git/commit/e3af72cdafab5993d18fae056f87e1d675913d08
- https://github.com/git/git/pulls
- https://github.com/git/git/pulls?state=closed
- https://github.com/git/git/compare/master...next
さんがデザインURIについていくつかのヒントを見てみましょう:
- _使用するか - 読みやすくするURIを作成します
URIは、より多くの人に見えるしましょう、いくつかの単語を分離するために - 数字の寒さや意味のない文字列ですが、今より多くのサイトが_使用したり、Web上のURI。このようhttp://www.oschina.net/news/38119/oschina-translate-reward-planとしてこのスタイルを使用することで上記のアドレス情報を例えば、より多くの有名な国内の中国オープンソースコミュニティ、。
- リソース階層を表現する/使用します
例えば、上記の/ gitの/ gitのコミット/ / e3af72cdafab5993d18fae056f87e1d675913d08彼は、特定のユーザーの提供するgitのgitを参照するマルチレベルのリソースは、レコードプロジェクトをコミットすることを言いますが、また、例えば/受注/ 10分の2012は、2012年10月表すために使用することができます注文履歴。
- リソースをフィルタリングするには?を使用
多くの人々はちょうど置く?簡単なパラメータが渡されたとして、URIを理解するにはあまりにも複雑であるが発生する可能性があります。/すべてのGitの項目を表すために要求をプッシュプル例えば/ gitの/ gitの、リソースのフィルタリングのために?すること、及び/プル?アイテムを表すために使用される状態=閉鎖Gitは、要求が閉じられた押し、このことができURLは、通常、特定の条件または演算結果の数の結果に相当します。
- それとも、リソースの同じレベルの関係を示すために使用することができます
時々、私たちは、リソースの同じレベルを使用することができな関係を表現するために必要な、あるいは、分割します。例えば、githubの日は、ファイルに比較することができる2つのレコード間の差異を提出すること自由に感じ、URIとして/ gitの/ gitの/block-sha1/sha1.h/compare/e3af72cdafab5993d18fae056f87e1d675913d08;bd63e61bdf38e872d5215c07b264dcc16e4febcaを使用することができます。しかし、現在では、githubのは...例えば、/ gitの/ gitの/比較/マスター、使用する...このことを行うには、次です。
2.2ユニフォーム・リソース・インターフェース
統一されたインタフェースの原則に従うべきでRESTfulなアーキテクチャは、統一されたインタフェースは、操作の事前に定義されたセットは、リソースが同じインタフェースを使用してアクセスされているどのリソースの種類に関係なく、制限されないが含まれています。インタフェースは、GETなどの標準HTTPメソッドを使用してPUTやPOST、およびこれらのメソッドのセマンティクスは従うべきです。
あなたは、リソースを公開するHTTPメソッドのセマンティクスに従っている場合、インターフェイスは、など、セキュリティや電源の特性を持つことになり、GETとHEADリクエストが安全であるなど、どんなに何回リクエスト、サーバーの状態が変化しないことはありません。GETは、HEADは、PUTとDELETE要求が冪等あるにかかわらず、何回リソース操作の、結果は常に同じ、後続の要求であり、第一時間以上影響を与えることはありません。
以下に列挙PUTやPOST、DELETE、GETの一般的な使用されています。
取得する
- 安全でべき等
- 取得
- 変更したとき(キャッシュ)を取得します
- 200(OK) - レスポンスが送信された表します
- 204(コンテンツなし) - 利用できるリソースが表します
- 301(恒久的に移動) - URIが更新されたリソース
- 303(他を参照) - その他(例えば、負荷バランシング)
- 304(変更されない) - リソース変更されない(キャッシュ)
- 400(悪い要求) - 不正な要求を指す(例えば、パラメータ誤差)
- 404(見つかりません) - リソースが存在しません
- (許容できない)406 - サーバーは、必要な表現をサポートしていません
- 500(内部サーバーエラー) - 一般的なエラー応答
- 503(サービス利用不可) - サーバが現在リクエストを処理することができません
役職
- 冪等でない安全でありません
- リソースを作成する(自動的に生成された)サーバ側管理番号の使用例
- 子リソースを作成します。
- 一部の更新リソース
- それが変更されますが、更新されたリソース(楽観的ロック)されていない場合
- 200(OK) - 既存のリソースが変更された場合
- 201(作成) - 新しいリソースが作成された場合
- 処理要求が受け入れられているが、まだ(非同期的に)完了していない - 202(受け入れ)
- 301(恒久的に移動) - URIのリソースが更新されます
- 303(他を参照) - その他(例えば、負荷バランシング)
- 400(不正な要求は) - 不正な要求を指し、
- 404(見つかりません) - リソースが存在しません
- (許容できない)406 - サーバーは、必要な表現をサポートしていません
- 409(競合) - 一般的なコンフリクト
- 412(前提条件が失敗しました) - (例えば、更新条件を実行する際の競合)を前提条件が失敗しました
- 415(サポートされていないメディアタイプ) - 受信した表現がサポートされていません
- 500(内部サーバーエラー) - 一般的なエラー応答
- 503(サービス利用不可) - サービス要求を処理するために、現在できません
プット
- しかし、危険な冪等
- クライアント管理のインスタンス番号を持つリソースを作成します
- 交換の方法により、リソースを更新
- 変更されていない場合、更新リソース(楽観的ロック)
- 200(OK) - すでに変更されたリソースがある場合
- 201(作成) - 新しいリソースが作成された場合
- 301(恒久的に移動) - URIが変更されたリソース
- 303(他を参照) - その他(例えば、負荷バランシング)
- 400(不正な要求は) - 不正な要求を指し、
- 404(見つかりません) - リソースが存在しません
- (許容できない)406 - サーバーは、必要な表現をサポートしていません
- 409(競合) - 一般的なコンフリクト
- 412(前提条件が失敗しました) - (例えば、更新条件を実行する際の競合)を前提条件が失敗しました
- 415(サポートされていないメディアタイプ) - 受信した表現がサポートされていません
- 500(内部サーバーエラー) - 一般的なエラー応答
- 503(サービス利用不可) - サービス要求を処理するために、現在できません
DELETE
- しかし、危険な冪等
- リソースを削除します。
- 200(OK) - リソースが削除されています
- 301(恒久的に移動) - URIが変更されたリソース
- 303(その他を参照してください) - など、ロードバランシングなどの他、
- 400(不正な要求は) - 不正な要求を指し、
- 404(見つかりません) - リソースが存在しません
- 409(競合) - 一般的なコンフリクト
- 500(内部サーバーエラー) - 一般的なエラー応答
- 503(サービス利用不可) - サーバが現在リクエストを処理することができません
のは、実際には一般的な問題のいくつかを見てみましょう:
- リソースを作成するための違いPOSTとPUTとは何ですか?
(URI)作成されたリソースの名前はどうか、クライアントによって決定されたリソースを作成するに違いをPOSTやPUT。このような結果のパスは、カテゴリ名/カテゴリ/ javaので、私のブログのためのJavaの分類を増やすよう、あなたが使用した方法を置くことができます。しかし、多くのPOSTに直接人、GET、PUT、直接CRUDに対応DELETEは、例えば、レールに実装され、典型的なRESTfulなアプリケーションではなかったです。
私はレールのデフォルトのIDは、URIの酒としてサーバーを使用して生成されたためであると思いますが、多くの人がRESTレールの実践を通してあるので、それは、この誤解のために簡単です。
- クライアントは右、これらのHTTPメソッドをサポートしていないかもしれませんか?
確かにこれはそうである、より多くの古代のブラウザベースのクライアントのいくつかの特に、唯一のGETとPOSTメソッドをサポートすることができます。
実際には、クライアントとサーバは、いくつかの妥協をする必要があるかもしれません。例えばフレームレールDELETE =隠れパラメータ要求方法_methodを通過するトランザクションをサポートするために、等MVCクライアントフレーム送信そのようなバックボーンは、送信および配置された_method X-HTTP-メソッドオーバーライドヘッドは、この問題を回避することを可能にします。
- それは、統一されたインターフェイスメソッドは、特別な意味を持つ拡張することができないということですか?
統一されたインタフェースは、拡張メソッドからあなたを防ぐことはできません限り、リソースの操作方法は、特定の持っているとして、識別可能なセマンティクスをすることができ、全体のインターフェースの統一を維持することができます。
それのようなWebDAV HTTPメソッドは、LOCKを増やし、拡張することが、他の方法をアップロック。そして、githubのAPIには、次のような、更新を発行するために使用するPATCHメソッドをサポートしています。
PATCH / レポ/:所有者/:レポ/ 問題/:数
しかし、HTTPのPATCHのように、これは、サーバはクライアントがサポートできるかどうかの問題を考慮する必要がある標準的な方法ではないことに留意すべきです。
- ユニフォーム・リソース・インタフェースURIのためにどのような指導?
リソースを操作するために、標準のHTTPメソッドを使用してのUniform Resourceインターフェースの要件は、それが唯一のURIであるべきリソースの名前を表し、経営資源を含めるべきではありません。
口語、URIアクションを記述するために使用すべきではありません。例えば、ここでいくつかは、統一されたインタフェースURIの要件を満たしていない、次のとおりです。
- GET / getUserメソッド/ 1
- POST /のcreateUser
- PUT / updateUser / 1
- DELETE /は、deleteuser / 1
GETリクエストは、カウンタ、安全性の違反がある場合に向上させますか?
セキュリティは、要求が、それは要求フローを制限し、多くのAPIのために、このような開発プラットフォームなどの副作用を起こさないことを意味するものではありません。githubのように、それは時間あたりの認証要求せずにわずか60回の要求が制限されます。
GETやHEADリクエストを発行しながら、しかし、クライアントはこれらの副作用の追求ではなく、サーバーの副作用はの「アップフロント」です。
クライアントは、これらの要求が副作用ではないと考えているので、また、設計時にサーバーには、あまりにも副作用を聞かせてはいけません。
- 直接キャッシュそれを無視することをお勧め?
あなたがそれらを使用するために、各動詞の本来の意図を押した場合でも、簡単にキャッシュメカニズムを無効にすることができます。キャッシュコントロール:キャッシュなしの最も簡単な方法は、HTTPヘッダー内のあなたの応答を高めることです。しかし、同時に、あなたも(のEtagメカニズムを使用して)効率的なキャッシュと再検証の支援を失いました。
毎回表現を再取得しないようにクライアントを達成するために、RESTスタイルのサービスプログラムも、既存のキャッシュメカニズムをフルに活用すべきであるクライアントについて。
- 必要な応答コードを処理しますか?
HTTPレスポンスコードは、さまざまな状況に対処するために使用することができ、これらのステータスコードの適切な使用は、クライアントとサーバが豊富なセマンティックレベルで通信できることを意味します。
例えば、201(「作成者」)応答コードを使用すると、事前に場所の応答パケットに新しいリソース、そのURIを作成していることを示しています。
あなたはHTTPステータスコードに豊富なアプリケーションのセマンティクスを使用しない場合は、再利用性、強化された相互運用性と昇進の機会の疎結合を改善欠場します。
これらのいわゆるRESTfulなアプリケーションがエンティティに対応して、エラーメッセージを与える必要がある場合は、SOAPは、このような一つであり、それは会うことができます。
表現2.3リソース
前述したように、クライアントはHTTPメソッドを介してリソースにアクセスすることができ、そうではありませんか?いいえ、むしろ、クライアントはリソースのみの表現のみを取得します。特定のプレゼンテーション外部リソースは、複数の式(または発現、表現として)クライアントとサーバの間で転送形態、も発現のリソースではなく、リソース自体を有することができます。このようなテキストリソースはHTML、XML、JSON形式、PNGまたはJPG画像を使用することができますように表示するために使用することができます。
記述データを含むリソースデータおよびメタデータの表現、例えば、HTTPヘッダの「Content-Type」は、そのようなメタデータ属性です。
それでは、どのようにそれを提供するクライアント側のプレゼンテーションサービスの形を知っていますか?
答えはHTTPコンテンツの交渉であり、クライアントがAcceptヘッダーによって特定のプレゼンテーション形式を要求することができ、コンテンツタイプを介してサーバーは、クライアントのリソースの表現形式を伝えます。
githubのために、例えば、組織のリソースの要求のJSON形式で表現:
githubのは、出力形式のXMLフォーマットをサポートできる場合、結果はこれです:
のは、いくつかの一般的な設計の練習を見てみましょう:
内部URIにバージョン番号を持参
例えば内側バンドバージョン番号の一部のAPI URI:
- http://api.example.com/1.0/foo
- http://api.example.com/1.2/foo
- http://api.example.com/2.0/foo
アプリケーション/ vnd.githubの[を:私たちはリソースの表現の異なる形として理解バージョン番号を置く場合は、あなただけのURLを使用して、Acceptヘッダーによって、またはgithubのに区別する必要があり、例えば、完全なフォーマットは、その受け入れています。バージョン] .PARAM [+ JSON]
アプリケーション/ vnd.github.v3を:v3のバージョンの場合は、それが受け入れています。上記の例では、同じトークンは、次のヘッダーを使用して使用することができます。
- 受け入れ:vnd.example-com.foo + JSONを。バージョン= 1.0
- 受け入れ:vnd.example-com.foo + JSONを。バージョン= 1.2
- 受け入れ:vnd.example-com.foo + JSONを。バージョン= 2.0
出力フォーマットであるURIサフィックスを使用します
像rails框架,就支持使用/users.xml或/users.json来区分不同的格式。 这样的方式对于客户端来说,无疑是更为直观,但混淆了资源的名称和资源的表述形式。 我个人认为,还是应该优先使用内容协商来区分表述格式。
如何处理不支持的表述格式
当服务器不支持所请求的表述格式,那么应该怎么办?若服务器不支持,它应该返回一个HTTP 406响应,表示拒绝处理该请求。下面以github为例,展示了一个请求XML表述资源的结果:
2. 4 资源的链接
我们知道REST是使用标准的HTTP方法来操作资源的,但仅仅因此就理解成带CURD的Web数据库架构就太过于简单了。
这种反模式忽略了一个核心概念:"超媒体即应用状态引擎(hypermedia as the engine of application state)"。 超媒体是什么?
当你浏览Web网页时,从一个连接跳到一个页面,再从另一个连接跳到另外一个页面,就是利用了超媒体的概念:把一个个把资源链接起来.
要达到这个目的,就要求在表述格式里边加入链接来引导客户端。在《RESTful Web Services》一书中,作者把这种具有链接的特性成为连通性。下面我们具体来看一些例子。
下面展示的是github获取某个组织下的项目列表的请求,可以看到在响应头里边增加Link头告诉客户端怎么访问下一页和最后一页的记录。 而在响应体里边,用url来链接项目所有者和项目地址。
又例如下面这个例子,创建订单后通过链接引导客户端如何去付款。
上面的例子展示了如何使用超媒体来增强资源的连通性。很多人在设计RESTful架构时,使用很多时间来寻找漂亮的URI,而忽略了超媒体。所以,应该多花一些时间来给资源的表述提供链接,而不是专注于"资源的CRUD"。
2. 5 状态的转移
有了上面的铺垫,再讨论REST里边的状态转移就会很容易理解了。
不过,我们先来讨论一下REST原则中的无状态通信原则。初看一下,好像自相矛盾了,既然无状态,何来状态转移一说?
其实,这里说的无状态通信原则,并不是说客户端应用不能有状态,而是指服务端不应该保存客户端状态。
2. 5.1 应用状态与资源状态
实际上,状态应该区分应用状态和资源状态,客户端负责维护应用状态,而服务端维护资源状态。
客户端与服务端的交互必须是无状态的,并在每一次请求中包含处理该请求所需的一切信息。
服务端不需要在请求间保留应用状态,只有在接受到实际请求的时候,服务端才会关注应用状态。
这种无状态通信原则,使得服务端和中介能够理解独立的请求和响应。
在多次请求中,同一客户端也不再需要依赖于同一服务器,方便实现高可扩展和高可用性的服务端。
但有时候我们会做出违反无状态通信原则的设计,例如利用Cookie跟踪某个服务端会话状态,常见的像J2EE里边的JSESSIONID。
这意味着,浏览器随各次请求发出去的Cookie是被用于构建会话状态的。
当然,如果Cookie保存的是一些服务器不依赖于会话状态即可验证的信息(比如认证令牌),这样的Cookie也是符合REST原则的。
2. 5.2 应用状态的转移
状态转移到这里已经很好理解了, "会话"状态不是作为资源状态保存在服务端的,而是被客户端作为应用状态进行跟踪的。客户端应用状态在服务端提供的超媒体的指引下发生变迁。服务端通过超媒体告诉客户端当前状态有哪些后续状态可以进入。
这些类似"下一页"之类的链接起的就是这种推进状态的作用——指引你如何从当前状态进入下一个可能的状态。
3. 总结
今、広東省XXXバージョン、XXXとJSONフォーマットの使用が相互作用するものの、XXXXベースプロジェクトバック南に移動、まだRPCスタイルに属しながら、伝統的なRPC、WebサービスのSOAPメソッドの使用の両方で他のプロジェクト、。すぐにRESTfulなアーキテクチャの背後にある概念を理解しようとするリソース、収集、表現、協会、状態遷移の視点、の定義から。などの伝統的なRPC、SOAP、とRESTfulなアーキテクチャをコンセプトに非常に異なっている、私はあなたがRESTを理解するために、これは役立ちます願っています。