web-dev-qa-db-ja.com

GETリクエストが最も適切な場合に、JSONオブジェクトをhttpリクエストで渡す正しい方法は何ですか?

1つのシナリオは、検索エンドポイントを作成する場合です。以下の例では、会社のデータベースを検索したいのですが、クエリが複雑になることがあります。パラメータをフラットリストではなくJSONオブジェクトとして渡したい場合は十分です。

var hapi = require('hapi');
var joi = require('joi');

var server = new hapi.Server();
server.connection({port: 5555});

var simpleRoute = {
    method: 'GET',
    path: '/company/search',
    config: {
        validate: {
            query: {
                company: joi.object().keys({
                    name: joi.string(),
                    address: joi.string()
                })
            }
        }
    },
    handler: (request, reply) => {
        reply({
            input: request.query,
            results: 'SOME RESULTS'
        });
    }
};

server.route(simpleRoute);

server.start(() => {
    console.log('server started -- ' + server.info.uri);
});

そして、このURLはhttp://localhost:5555/company/search?company=%7B%22name%22%3A%22Cuthbert%22%2C%22address%22%3A%22123%20Main%20St%22%7Dのようになります。

URLは乱雑で見栄えがよくないため、クライアント向けのWebサイトでは、ユーザーが検索をやり直したい場合、ユーザーがこれを再作成するのは難しい場合があります。

URLには 文字制限 もあります。ヒットする可能性は低いですが、GETリクエストに対してクエリが複雑になりすぎるとどうなりますか?ルートをPOST/PUTに変更できますが、検索によってサーバー上のデータが変更されることもありません。

では、GET、PUT、POSTなどを正しく使用しながら、複雑なオブジェクトをhttp経由で渡すにはどうすればよいですか?

4
Cuthbert

Elastic Search にもこの問題があり、それらの解決策は bodyでのGETリクエストを許可することでした

$ curl -XGET 'http://localhost:9200/Twitter/Tweet/_search' -d '{
    "query" : {
        "term" : { "user" : "kimchy" }
    }
}
'

標準ではありませんが、技術的にはHTTP/1.1の違反ではありません:

リクエスト内のメッセージ本文の存在は、Content-LengthまたはTransfer-Encodingヘッダーフィールドによって通知されます。メソッドでメッセージ本文の使用が定義されていない場合でも、要求メッセージのフレーミングはメソッドのセマンティクスとは無関係です。

ただし、RFC 7321 は、GETリクエストの本文にセマンティクスが定義されていないことを確認 します。

GETリクエストメッセージ内のペイロードにはセマンティクスが定義されていません。 GETリクエストでペイロードボディを送信すると、一部の既存の実装がリクエストを拒否する可能性があります。

このため、クライアントは技術的に本文でのGETリクエストをサポートする必要がありません。そのため、Elastic SearchはPOSTを介して検索クエリも受け入れます。

3
Evan

あなたはurl paramsを使用することができます: http:// localhost:5555/company/name/cuthbert/address/mainst

またはjsonオブジェクトを文字列クエリパラメータとして渡します

1
NimChimpsky