0

これはデザイン/パターンの問題です。私は、RESTfulWebサービスとしても公開する必要があるサービスを持っています。

既存のコード内で、私はRequestの概念、可能なServiceOperations(戦略)のスイートを持っており、ServiceOperationの戻り値はResponseオブジェクトです。このアプローチは、サービスの内部動作をプレゼンテーションメディア(カスタムTCPサーバー、HTTP REST、HTTP SOAPなど)から切り離します。

これで、次のようなMyServiceRESTfulServletの実装を開始しました。

public void doGet(HttpRequest httpRequest, HttpResponse httpResponse) throws ServletException, IOException {
    try {
        /* Wrap an http servlet request with an adapter which hides all
         * the messy details of an HttpRequest and exposes a nice interface
         * for working with MyService
         */
        IRequest serviceRequest = new MyServiceRESTfulRequest(httpRequest);

        /* There's nothing HTTP related in this part, it's the exact same
         * code you'd find in other presentation formats. A Response has
         * no idea about HTTP, TCP Servers or the like.
         */
        Response serviceResponse = dispatchRequest(serviceRequest);

        /* A static helper which knows the interface of a Response
         * and can translate that into REST-speak for feeding back via
         * an HttpServletResponse.
         */
        renderRESTfulResponse(serviceResponse, httpResponse);
    } catch (Exception e) {
        throw new ServletExcetion(e);   // Caught by a seperate
                                        // RESTfulErrorServlet
                                        // configured in web.xml
                                        // Rendering an appropriate
                                        // response.
    }
}

私の問題は、応答が現在2種類のいずれかになり得ることです。

public enum ResponseKind() {
    BINARY, METADATA;
}

バイナリの場合、RESTful Response Helperは一方向にレンダリングします。メタデータの場合、メタデータを適切に提示する必要があります(HTMLテーブル、JSONブロブなど)。

どのタイプが簡単かを理解する-ResponseオブジェクトはgetOriginalRequest()を公開し、適切なチェックの後、.getAcceptablePresentation()を公開するMyServiceRESTfulRequestにキャストできます-列挙型:

public enum RESTPresentationKind() {
    HTML, JSON, XML, PROTOBUF_MYSERV_0.1;
}

このレンダリングコードをResponseオブジェクトから切り離しておくにはどうすればよいでしょうか。将来的には、他の種類の対応も可能になることは間違いありません。現状では、renderRESTfulResponse()はRequestオブジェクトをレイドし、データを適切に書き込みます。それは両方のResponseインターフェース(私は大丈夫です)と非常に緊密に結合されていますが、Requestオブジェクトを突っ込むことも知っています。

私は、このサービスの残りの部分と同じように、このビットをクリーンで保守可能な方法で実行したとは感じていません。私は、可能な応答タイプのそれぞれ、および可能な応答形式のそれぞれの「特別なケーシング」です。ユーバーハッキーな感じ。

プレゼンテーションにとらわれないRequestオブジェクトを指定して、RESTful応答のレンダリングをクリーンに処理する方法を提案できますか?

4

1 に答える 1

0

RepsonseKind 列挙型 (列挙型は実際にはクラスです) にレンダリングを実装したり、ity を完全に省いたりしませんか? case/switch ステートメントを取り除こうとしていることに気付いた場合、その答えは通常、コンポジション + オーバーロード + コマンド パターンまたはビジター パターンです。

于 2012-12-03T08:41:21.260 に答える