2017-08-23 10 views
1

を呼び出されていない特定のシナリオでHttpErrorHandlerメカニズムを使用して例外を処理しようとしているときに、私はプレイフレームワーク(2.6)で問題に直面しています。プレイフレームワーク - のErrorHandlerが

私はルートパッケージに簡単なのErrorHandlerを持っている:

import play.Logger; 
import play.http.HttpErrorHandler; 
import play.mvc.Http; 
import play.mvc.Result; 
import play.mvc.Results; 

import java.util.concurrent.CompletableFuture; 
import java.util.concurrent.CompletionStage; 

public class ErrorHandler implements HttpErrorHandler { 

    @Override 
    public CompletionStage<Result> onClientError(Http.RequestHeader request, int statusCode, String message) { 
     Logger.error("client error"); 
     return CompletableFuture.completedFuture(Results.status(statusCode, "A client error occurred: " + message)); 
    } 

    @Override 
    public CompletionStage<Result> onServerError(Http.RequestHeader request, Throwable exception) { 
     Logger.error("server error"); 

     return CompletableFuture.completedFuture(
       Results.internalServerError("A server error occurred: " + exception.getMessage())); 
    } 
} 

私は資産を処理するためのカスタムコントローラを作成しました:

package controllers; 

import org.apache.commons.lang3.StringUtils; 
import play.api.mvc.Action; 
import play.api.mvc.AnyContent; 
import play.mvc.Controller; 

import javax.inject.Inject; 

public class AssetsCustomController extends Controller { 

    private final Assets assets; 

    @Inject 
    public AssetsCustomController(Assets assets) { 
     this.assets = assets; 
    } 

    public Action<AnyContent> at(String path, String file) { 
     if (StringUtils.isEmpty(path)) { 
      throw new IllegalArgumentException(); 
     } 
     return assets.at(path, file, false); 
    } 
} 

私はのErrorHandlerをチェックしましたこのメソッドから例外がスローされた場合を除いて、すべてのケースで正常に動作していますAssetsCu stomController:例えば

public Action<AnyContent> at(String path, String file) { 
     if (StringUtils.isEmpty(path)) { 
      throw new IllegalArgumentException(); 
     } 
     return assets.at(path, file, false); 
    } 

はIllegalArgumentExceptionがスローされ、私ののErrorHandlerは無視され、プレイは彼のネイティブエラーハンドラを使用しています。ここでスタックトレースは次のとおりです。

play.api.http.HttpErrorHandlerExceptions$$anon$1: Execution exception[[IllegalArgumentException: null]] 
     at play.api.http.HttpErrorHandlerExceptions$.throwableToUsefulException(HttpErrorHandler.scala:255) 
     at play.api.http.DefaultHttpErrorHandler.onServerError(HttpErrorHandler.scala:182) 
     at play.api.http.DefaultHttpErrorHandler$.onServerError(HttpErrorHandler.scala:286) 
     at play.core.server.Server.logExceptionAndGetResult$1(Server.scala:53) 
     at play.core.server.Server.getHandlerFor(Server.scala:83) 
     at play.core.server.Server.getHandlerFor$(Server.scala:49) 
     at play.core.server.AkkaHttpServer.getHandlerFor(AkkaHttpServer.scala:42) 
     at play.core.server.AkkaHttpServer.getHandler(AkkaHttpServer.scala:215) 
     at play.core.server.AkkaHttpServer.handleRequest(AkkaHttpServer.scala:195) 
     at play.core.server.AkkaHttpServer.$anonfun$createServerBinding$3(AkkaHttpServer.scala:107) 
Caused by: java.lang.IllegalArgumentException: null 
     at controllers.AssetsCustomController.at(AssetsCustomController.java:20) 
     at router.Routes$$anonfun$routes$1.$anonfun$applyOrElse$10(Routes.scala:183) 
     at play.core.routing.HandlerInvokerFactory$$anon$6$$anon$7.call(HandlerInvoker.scala:61) 
     at play.core.routing.GeneratedRouter$$anon$2.call(GeneratedRouter.scala:251) 
     at router.Routes$$anonfun$routes$1.$anonfun$applyOrElse$9(Routes.scala:183) 
     at play.core.routing.GeneratedRouter.$anonfun$call$5(GeneratedRouter.scala:99) 
     at scala.util.Either.fold(Either.scala:118) 
     at play.core.routing.GeneratedRouter.call(GeneratedRouter.scala:99) 
     at router.Routes$$anonfun$routes$1.applyOrElse(Routes.scala:182) 
     at router.Routes$$anonfun$routes$1.applyOrElse(Routes.scala:154) 

[SOLUTION]
答えFlo354のおかげで、私は問題を解決することができたとAssetsCustomControllerは、このようなものです:

package controllers; 

import akka.stream.Materializer; 
import org.springframework.util.StringUtils; 
import play.mvc.Controller; 
import play.mvc.Result; 

import javax.inject.Inject; 
import java.util.concurrent.CompletionStage; 

public class AssetsCustomController extends Controller { 

    private final Assets assets; 
    private final Materializer materializer; 

    @Inject 
    public AssetsCustomController(Materializer materializer, Assets assets) { 
     this.materializer = materializer; 
     this.assets = assets; 
    } 

    public CompletionStage<Result> at(String path, String file) { 
     if (StringUtils.isEmpty(path)) { 
      throw new IllegalArgumentException(); 
     } 
     return assets.at(path, file, false).asJava().apply(request()).run(materializer); 
    } 
} 

答えて

0

Action<AnyContent>はScala APIの一部です。つまり、Java部分を使用しません。

カスタムエラーハンドラは、Javaソースにのみ適用されます。あなたのスタックトレース

play.api.http.HttpErrorHandlerExceptions$$anon$1: Execution exception[[IllegalArgumentException: null]] 
    at play.api.http.HttpErrorHandlerExceptions$.throwableToUsefulException(HttpErrorHandler.scala:255) 
    at play.api.http.DefaultHttpErrorHandler.onServerError(HttpErrorHandler.scala:182) 
    at play.api.http.DefaultHttpErrorHandler$.onServerError(HttpErrorHandler.scala:286) 
.... 

を見てあなたはそれがplay.api.something

があるときは、CompletionStage<Result>

public CompletionStage<Result> test(String path, String file) { 
    if (StringUtils.isEmpty(path)) { 
     throw new IllegalArgumentException(); 
    } 

    return assets.at(path, file, false).asJava().apply(request()).run(materializer); 
} 

そして、あなたのコントローラでを送り返すことにより、この問題を回避することができScalaのことを見ることができ、しませんakka.stream.Materializer

のインスタンスを注入することを忘れないでください!

+0

何らかの例外がスローされたときに、私はErrorHandlerを呼び出すことができました。しかし、成功フローではブラウザの代わりにコンソールにコンテンツが表示されます。この動作はCompletionStage が原因ですか?この問題を回避するにはどうしたらいいですか? [printscreen](https://snag.gy/fi20zs.jpg)に従って、ブラウザがどのように通話を処理しているかを表示します。 – vallim

+0

私の最後に問題を再現できません...私はそれを見ることができるように問題を再現する簡単なgitプロジェクトを提供できますか? – Flo354

+0

遅れて申し訳ありません。私はここでチェックして、私は起こっていた問題を発見した。今それは正常に動作しています。ありがとう! – vallim

関連する問題