3

複数のアスペクトを特定の順序で起動するのに問題があります。RequestProcessor を使用して、特定のパラメーターを持つコントローラーのすべての着信要求で特定のことを行います

次に、コントローラー内の特定のメソッドにのみ追加する特定の注釈がいくつかあります。

参考までに、Eclipse、Tomcat、Maven、Spring を Java/Annotation ベースの構成で使用しています。Tomcat と WebApplicationInitializer を使用して、コンテキスト、ディスパッチャー、リスナーなどをロードします。web.xml はありません。必要に応じて、それまたは pom.xml も投稿できます。

私が得ている問題は、ProcessRequestポイントカットとポイントカットの両方を満たすメソッドが、最初にsomeAnnotation起動someAnnotationするように指定されているにもかかわらず、メソッドを最初に起動していることProcessRequestです。ProcessRequestには、他の注釈で必要ないくつかのプロパティが設定されています。

これが私のコードの簡略版です。

Spring 構成クラス

@Configuration  // Enable Spring Annotation Configuration. Equivalent to <context:annotation-config/>
@EnableAspectJAutoProxy
@EnableCaching  // Enable Spring caching
@EnableWebMvc   // Enable Spring MVC Annotation. Equivalent to <mvc:annotation-driven />.
@ComponentScan(basePackages = {"xxx.yyy.zzz"}) // Scan for Spring Components.      Equivalent to <context:component-scan>
public class WebAppConfig extends WebMvcConfigurerAdapter {

    // Other Bean logic here

    @Bean
    public RequestProcessor requestProcessor() {
        return new RequestProcessor();
    }

    @Bean
    public AnnotationAspect annotationAspect() {
        return new AnnotationAspect();
    }
}

側面#1

@Aspect
@Order(0)
public class RequestProcessor {

    @Pointcut("execution(* xxx.yyy.zzz.api..*.*(xxx.yyy.zzz.objects.api.Request,..)) && args(request)")
    public void pointcut(Request<?> request) {}

    @Before("pointcut(request)")
    public void processRequest(Request<?> request) throws IOException, BadSignatureException {
        // Some logic here that is independent of other and needs to run before other aspect which references annotation
    }
}

側面#2

@Aspect
@Order(1)
public class AnnotationAspect {

    @Before("@annotation(xxx.yyy.zzz.annotation.SomeAnnotation)")
    public void someAnnotation() {
        // Log for this annotation
    }

    // Some other annotation methods here
}

このフォーマットも試しましたimplements Ordered

@Aspect
public class RequestProcessor implements Ordered {

    @Override
    public int getOrder() {
        return 0;
    }

    @Pointcut("execution(* xxx.yyy.zzz.api..*.*(xxx.yyy.zzz.objects.api.Request,..)) && args(request)")
    public void pointcut(Request<?> request) {}

    @Before("pointcut(request)")
    public void processRequest(Request<?> request) throws IOException, BadSignatureException {
        // Some logic here that is independent of other and needs to run before other aspect which references annotation
    }
}

この投稿と他の投稿を読みましたが、関連するものは見つかりませんでした。

Spring AOP && MVC による順序付けの側面

****アップデート****

だから私は優先順位の宣言に関するAspectJのドキュメントを読んでいたので、試してみようと思いました。優先順位のみを宣言する単純なアスペクトを作成しましたが、問題なく動作します。

ここに私の優先度の側面があります:

public aspect AspectPrecedence {
    declare precedence : RequestProcessor, SomeAspect;
}

注釈または「注文された実装」がプロジェクトで適切に機能しない理由を理解したいので、これを回答として提出するつもりはありません。

どんな洞察も大歓迎です。ありがとう!

****更新 2****

参考までに、これは私のEclipse環境でローカルに機能し、WARファイルを介してAWSにデプロイすると機能するように見えました.

@Aspect
@DeclarePrecedence("RequestProcessor, SomeAspect")
public class RequestProcessor {

    @Pointcut("execution(* xxx.yyy.zzz.api..*.*(xxx.yyy.zzz.objects.api.Request,..)) && args(request)")
    public void pointcut(Request<?> request) {}

    @Before("pointcut(request)")
    public void processRequest(Request<?> request) throws IOException, BadSignatureException {
        // Some logic here that is independent of other and needs to run before other aspect which references annotation
    }
}
4

2 に答える 2

3

IDE でのコンパイル時のウィービングを自動的に有効にする AspectJ サポートで Eclipse を使用する場合。これは、プロキシを使用してアスペクトを適用する Spring とは対照的に、アスペクトがバイト コードに織り込まれることを意味します。

アスペクトを使用して優先順位を宣言したり、使用したりする@DeclarePrecedenceことは、コンパイル時またはロード時のウィービングを使用する場合にのみ機能します (後者は<context:load-time-weaver/> 、コンテナーに応じて指定することで有効にできます)。追加の構成が必要になる場合があります)。ただし、どちらも機能するはずです (デフォルトの Java コンパイラーではなく、AspectJ コンパイラーを @Aspect クラスのコンパイラーとして指定する必要がある場合があります)。

@OrderプロキシベースのソリューションでOrderedのみ機能し、AspectJ では無視されます。

于 2013-11-01T19:19:23.373 に答える