2

追跡が困難な奇妙な問題に遭遇しました。@AspectXML 構成を介してシングルトン Bean としてインスタンス化されるクラス (ServiceErrorInterceptor) が定義されています。XML 構成により、依存する Bean を注入できます。

私の通常のワークフローでは、すべて正常に動作します。アスペクト クラスは適切にインスタンス化され、アドバイスが呼び出されるたびに、注入された Bean は期待どおりになります。

ただし、JUnit テストを実行すると、注入されたすべての Bean が null になります。これにより、Spring によってインスタンス化された同じシングルトン Bean ではなく、別の Bean からアドバイスが呼び出されたという結論に至ります。私の仮説をさらに検証するために、インスタンス化中に呼び出されるセッターにブレークポイントを配置し、アドバイスにブレークポイントを配置した場合、Bean ID が Bean ID と同じではないことを確認します。

これを修正するために JUnit クラスで有効にする必要がある特別な構成はありますか? 私のテストクラスにはすでに注釈が付けられています:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { 
        "classpath:spring/applicationContext-base.xml", 
        "classpath:spring/applicationContext-calculateServices.xml", 
        "classpath:spring/applicationContext-dom.xml"})
public class LendingSimulationServiceImplTest {
...
...
}

ログを調べました (Spring トレース ログを有効にしました) が、目立ったものは何も表示されません。ここにログ全体を投稿するのは、おそらくやり過ぎでしょう。ログの特定の部分に価値がある場合はお知らせください。投稿します。

役立つ場合は、アスペクト、junit、構成のコードを投稿できます。

application-context.xml スニペット:

<!-- SPRING ASPECT BEAN.  POINTCUT DEFINED IN BEAN WITH ANNOTATION -->
<bean id="serviceErrorInterceptor" class="com.cws.cs.lendingsimulationservice.error.ServiceErrorInterceptor" scope="singleton">
    <property name="errorMessageProvider" ref="resourceBundleProviderImpl"/>
    <property name="defaultLocale">
        <util:constant static-field="java.util.Locale.ENGLISH" />
    </property>
</bean>

任意の提案をいただければ幸いです。

編集

私のBeanは次のように実装されています:

@Aspect
public class ServiceErrorInterceptor {

    /**
     * Logger
     */
    private static final Logger logger = LoggerFactory.getLogger(ServiceErrorInterceptor.class);

    /**
     * SOAP Header data
     */
    @Autowired
    private SOAPHeaderData soapHeaderData;

    public ServiceErrorInterceptor(){
        int x = 0;
        x=x+1;

    }

    /**
     * Exception Interceptor. 
     * @param ex
     */
    @AfterThrowing(pointcut = "execution(* com.cws.cs.lendingsimulationservice.process.CalculatorProcess.calculate (..))", throwing = "ex")
    public void errorInterceptor(Exception ex) {
        if (logger.isDebugEnabled()) {
            logger.debug("Error Message Interceptor started");
        }

    }

私のpomの関連部分:

    <!-- Aspect Oriented Programming (AOP) Framework (depends on spring-core, 
        spring-beans) Define this if you use Spring AOP APIs (org.springframework.aop.*) -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-aop</artifactId>
        <version>${org.springframework.version}</version>
    </dependency>

    <!-- Support for AspectJ Annotations -->
    <dependency>
        <groupId>org.aspectj</groupId>
        <artifactId>aspectjweaver</artifactId>
        <version>${org.aspectj}</version>
    </dependency>

さらにデバッグを行い、ダミー コンストラクターにブレークポイントを設定すると、次の結果が得られます。

  • @Aspect および XML 構成では、コンストラクターが 2 回呼び出されます (異なる Bean ID)。
  • @Aspect アノテーションを削除すると、一度だけ呼び出されます。
  • @Aspect を残して XML 構成を削除すると、コンストラクターは呼び出されません。
  • @Component アノテーションを @Aspect と組み合わせて (ただし XML 構成なしで) 使用すると、Bean が 2 回作成されます。
  • しかし、奇妙なことに、@Component および @Aspect アノテーションと XML 構成の両方を使用してもコンストラクターはまだ 2 回しか呼び出されません。

では、XML 構成と @Aspect アノテーションの両方を使用すると、コンストラクターが 2 つの異なる Bean ID で 2 回呼び出されるのはなぜでしょうか?

さらに、AOP 定義全体を XML 構成に移動すると (@Aspect および @Pointcut アノテーションを削除)、Bean が 1 回だけ構築されることを確認しました。

編集終了

ありがとう、

エリック

4

3 に答える 3

1

あなたのアスペクトには、@Aspect とは別に、自動検出アノテーション (@Component、@Service) などがありますか?構成。

また、すべての構成をスキャンして、この Bean を他の場所で宣言していないことを確認してください。

私が認識している Junit レベルで実行する必要がある特別なことはありません。

于 2012-04-12T20:53:58.253 に答える
1

SpringSource STS フォーラム (このスレッドを参照) で人々と多くの議論を行った結果、この問題は AJDT 構成に関連していることが判明しました。現在、AJ はアスペクトを織り込んでおり、Spring はクラスパス上のアスペクトを特定しているため、両方が実行されています。

残念ながら、AJ maven プラグインには、ウィービングの除外を許可する構成パラメーターがありません。現在の構成では、LTW と CTW の両方が除外されています。

そのため、現時点での回避策は-xmlConfigured、AJ コンパイラ フラグに追加し、プロジェクトに含めたい AJ アスペクトのみをリストする aop.xml 管理で aop.xml ファイルを指定することです。

これを機能させるには、「-xmlConfigured」をプロジェクト プロパティの「非標準コンパイラ オプション」に追加し、AspectJBuild >「aop.xml 管理」で単純な aop.xml ファイルを指定します。

<aspectj> 
    <aspects> 
       <aspect name="com.fooMyNewNoneSpringAspect"/>
    </aspects> 
</aspectj>

この発見と回避策について、STS フォーラムの Andy Clement に感謝します。彼は、maven プラグインのこの欠点にさらに対処するために、JIRA の問題を提起する予定です。

于 2012-04-20T14:35:21.510 に答える