7.10. 观察方法


发生事件时,观察方法会收到通知。

上下文和依赖注入还提供事务观察方法,它在完成之前或交易完成阶段接收事件通知。

7.10.1. 触发和观察事件

示例:Fire a Event

以下代码显示了在方法中注入和使用的事件:

public class AccountManager {
  @Inject Event<Withdrawal> event;

  public boolean transfer(Account a, Account b) {
    ...
    event.fire(new Withdrawal(a));
  }
}
Copy to Clipboard Toggle word wrap

示例:Fire a Event with a Qualifier

您可以使用限定符为事件注入添加注解,使其更具体。有关 限定符 的更多信息,请参阅质量。

public class AccountManager {
  @Inject @Suspicious Event <Withdrawal> event;

  public boolean transfer(Account a, Account b) {
    ...
    event.fire(new Withdrawal(a));
  }
}
Copy to Clipboard Toggle word wrap

示例:观察事件

若要观察事件,可使用 @Observes 注释。

public class AccountObserver {
  void checkTran(@Observes Withdrawal w) {
    ...
  }
}
Copy to Clipboard Toggle word wrap

您可以使用限定符来仅观察特定类型的事件。

public class AccountObserver {
  void checkTran(@Observes @Suspicious Withdrawal w) {
    ...
  }
}
Copy to Clipboard Toggle word wrap

7.10.2. 事务观察器

在交易开始阶段之前或之后,交易处理接收事件通知。事务处理在有状态对象模型中很重要,因为状态通常保留比单个原子交易更长的时间。

交易有五种类型:

  • IN_PROGRESS :默认情况下,会立即调用。
  • AFTER_SUCCESS :观察器在事务完成阶段后会被调用,但前提是事务成功完成。
  • AFTER_FAILURE :观察者在事务完成阶段后会被调用,但前提是事务无法成功完成。
  • AFTER_COMPLETION :观察器在事务完成后被调用。
  • BEFORE_COMPLETION :在事务完成阶段前调用观察者。

以下观察方法刷新应用程序上下文中缓存的查询结果集,但只有在更新 Category 树的操作成功时才会刷新:

public void refreshCategoryTree(@Observes(during = AFTER_SUCCESS) CategoryUpdateEvent event) { ... }
Copy to Clipboard Toggle word wrap

假设您缓存了 Jakarta Persistence 查询结果,请在应用程序范围中设置,如下例所示:

import javax.ejb.Singleton;
import javax.enterprise.inject.Produces;

@ApplicationScoped @Singleton

public class Catalog {
   @PersistenceContext EntityManager em;
   List<Product> products;
   @Produces @Catalog
   List<Product> getCatalog() {
      if (products==null) {
         products = em.createQuery("select p from Product p where p.deleted = false")
            .getResultList();
      }
      return products;
   }
}
Copy to Clipboard Toggle word wrap

有时 会创建 或删除产品。发生这种情况时,您需要刷新 产品 目录。但是,您必须等待事务成功完成,然后才能进行此刷新。

以下是创建和删除 Products 触发事件的 bean 示例:

import javax.enterprise.event.Event;

@Stateless

public class ProductManager {
   @PersistenceContext EntityManager em;
   @Inject @Any Event<Product> productEvent;
   public void delete(Product product) {
      em.delete(product);
      productEvent.select(new AnnotationLiteral<Deleted>(){}).fire(product);
   }

   public void persist(Product product) {
      em.persist(product);
      productEvent.select(new AnnotationLiteral<Created>(){}).fire(product);
   }
   ...
}
Copy to Clipboard Toggle word wrap

Catalog 现在可在成功完成事务后观察事件:

import javax.ejb.Singleton;

@ApplicationScoped @Singleton
public class Catalog {
   ...
   void addProduct(@Observes(during = AFTER_SUCCESS) @Created Product product) {
      products.add(product);
   }

   void removeProduct(@Observes(during = AFTER_SUCCESS) @Deleted Product product) {
      products.remove(product);
   }

}
Copy to Clipboard Toggle word wrap
返回顶部
Red Hat logoGithubredditYoutubeTwitter

学习

尝试、购买和销售

社区

关于红帽文档

通过我们的产品和服务,以及可以信赖的内容,帮助红帽用户创新并实现他们的目标。 了解我们当前的更新.

让开源更具包容性

红帽致力于替换我们的代码、文档和 Web 属性中存在问题的语言。欲了解更多详情,请参阅红帽博客.

關於紅帽

我们提供强化的解决方案,使企业能够更轻松地跨平台和环境(从核心数据中心到网络边缘)工作。

Theme

© 2025 Red Hat