2016-03-25 5 views
0

Java EE - JAX-RS 2.0技術を使用してモバイルバックエンドAPIを構築しています。私たちは常に非同期JAX-RSリソースを使用すべきですか?

モバイルクライアントの消費のほとんどは非同期HTTPはので、私の質問は

を呼び出しています私はすべてのJAX-RSリソースの非同期機能を使用する必要がありますか?そして、そうでなければ理由は?

以下は、テンプレートモバイル非同期API

@Path("/async_api") 
public class AsyncResource { 

    @GET 
    @Path("/loadUsers") 
    @Produces(MediaType.APPLICATION_JSON) 
    public void loadUsers(@Suspended AsyncResponse asyncResponse) { 

     //TODO: ManagedExecutorService 

     new Thread(new Runnable() { 

      @Override 
      public void run() { 
       List users = loadBigUsers(); 
       asyncResponse.resume(users); 
      } 

      private List loadBigUsers() { 
       return null; // Return big list 
      } 

     }).start(); 
    } 
} 

ありがとうです!

+1

いいえ、クライアント側の非同期はサーバー側で非同期を意味するわけではありません。逆もまた同様です。 – EJP

+2

長時間実行されているタスクではサーバー上でasyncを使用して、コンテナスレッドを保持しないようにする必要があります。 –

答えて

5

JAX-RSでは、@Suspend注釈とAsyncResponseは、特定の典型的なシナリオでのみ必要です。最初のシナリオは、コード例ですでに識別されています。これは長時間実行されるタスクです。この場合、AsyncResponseを使用して、バックグラウンドスレッドで長期実行コードを実行することができます。一見するとこれは意味をなさないが、アプリケーションサーバー/コンテナが要求をどのように処理するかについて考える必要がある。通常、クライアント要求を受け入れて処理するスレッドのプールがあります。 JAX-RSサービスメソッドで高価なオペレーションをインラインで実装すると、プール内のスレッドの1つが実行時全体でブロックされます。 AsyncResponseを使用すると、エグゼキュータ・スレッドがプールに戻され、他のリクエストを並行して処理できます。

@Path("/users") 
public class UserRestService { 

    @GET 
    public void getAllUsers(@Suspend final AsyncResponse asyncResponse) { 
     new Thread(new Runnable(
      @Override 
      public void run() { 
       List<Users> users = UserDAO.loadAllUsers(); 
       asyncResponse.resume(users); 
      } 
     ) {}).start(); 
    } 
} 

AsyncResponseための第二のアプリケーション・シナリオでは、プロデューサ、コンシューマパターンのしばしば見られるパターンです。キューhttps://yourservice.at/queue/nextにバインドされているキューがあるとしたら、@GETメソッドをブロックtake()に使用すると、LinkedBlockingQueueと言うことができます。同じURLには、@POSTメソッドをバインドして、データをキューに追加することができます。この場合、AsyncResponsetake()操作の機能をまとめます。これらの説明から、

@Path("/queue/next") 
public class MessageQueueService { 

    private static final LinkedBlockingQueue<AsyncResponse> suspendedResponses = new LinkedBlockingQueue<AsyncResponse>(); 

    @GET 
    public void getNextMessage(@Suspend final AsyncResponse asyncResponse) { 
     MessageQueueService.suspendedResponses.put(asyncResponse); 
    } 

    @POST 
    public void putNewMessage(final String message) throws InterruptedException { 
     AsyncResponse asyncResponse = suspendedResponses.take(); // note how this could also block a thread 
     asyncResponse.resume(message); 
    } 
} 

あなたはまた、JAX-RS @Suspendedメカニズムは、非同期サーバー側のタスクを作成するために使用されていることを、見ることができます。クライアント上で同じリクエストが非同期で実行されるかどうかは、まったく別の話です。

+0

ありがとう、マティアス・スタインバウアー! – Loc

関連する問題