简体   繁体   English

如何在Intershop7中注册ORMObjectListener

[英]How to register ORMObjectListener in Intershop7

We have implemented several custom ORM objects in our webshop implementation that have references (dependencies) to Intershop Product system object. 我们已经在Webshop实施中实现了几个自定义ORM对象,这些对象具有对Intershop Product系统对象的引用(依赖性)。

When a user tries to delete a certain product in back-office, it causes problems because references to that product may still exist in our custom objects. 当用户尝试在后台删除某个产品时,这会引起问题,因为在我们的自定义对象中可能仍然存在对该产品的引用。 Naturally, deleting a product that is referenced from one of our custom objects generates an exception like this: 自然地,删除从我们的自定义对象之一引用的产品会生成如下异常:

java.sql.SQLTransactionRollbackException: ORA-02091: transaction rolled back ORA-02292: integrity constraint (INTERSHOP.A1POSTPAIDPRICE_CO_002) violated - child record found  

We have figured that we could solve that by implementing an ORMObjectListener and overriding objectDeleting method to delete all the references before the product actually gets deleted. 我们已经发现,可以通过实现ORMObjectListener并重写objectDeleting方法来删除所有引用,然后实际删除产品来解决此问题。

Intershop cookbook for ORM layer states: 关于ORM层的Intershop食谱指出:

"Instances must implement the interface ORMObjectListener for a given ORM object type and register at the factory. The listener is called when instances of the given type are created, changed or removed." “实例必须为给定的ORM对象类型实现接口ORMObjectListener并在工厂注册。在创建,更改或删除给定类型的实例时,将调用侦听器。”

( https://support.intershop.com/kb/index.php/Display/2G3270#Cookbook-ORMLayer-Recipe:NotificationofPersistentObjectChanges ) https://support.intershop.com/kb/index.php/Display/2G3270#Cookbook-ORMLayer-Recipe:NotificationofPersistentObjectChanges

However, we cannot find a cookbook for registering the listener at the factory. 但是,我们在工厂找不到用于注册侦听器的食谱。 What do we need to do to register the listener? 我们需要做些什么来注册侦听器?

Also, if there is some better way for handling dependencies to system objects on our custom objects during delete event, I'm open to suggestions. 另外,如果在删除事件期间有更好的方法来处理对自定义对象的系统对象的依赖关系,我欢迎您提出建议。

UPDATE: 更新:

This is the listener class I have tried with so far: 到目前为止,这是我尝试过的侦听器类:

public class ProductDeleteListener implements ORMObjectListener<ProductPO> {

  @Inject
  ProductPOFactory productPOFactory;

  /** The Constant LOGGER. */
  private static final Logger LOGGER = LoggerFactory.getLogger(ProductDeleteListener.class);

  public ProductDeleteListener() {
    productPOFactory.addObjectListener(this, new AttributeDescription[0]);
  }

  @Override
  public boolean isOldStateNeeded() {
    // TODO Auto-generated method stub
    return false;
  }

  @Override
  public void objectChanged(ProductPO object, Map<AttributeDescription, Object> previousValues) {
    if (LOGGER.isDebugEnabled()) {
      LOGGER.debug("PRODUCT LISTENER TEST - CHANGE");
    }

  }

  @Override
  public void objectChanging(ProductPO object, Map<AttributeDescription, Object> previousValues) {
    // TODO Auto-generated method stub

  }

  @Override
  public void objectCreated(ProductPO object) {
    // TODO Auto-generated method stub

  }

  @Override
  public void objectCreating(ProductPO object) {
    // TODO Auto-generated method stub

  }

  @Override
  public void objectDeleted(ORMObjectKey objectKey) {
    // TODO Auto-generated method stub

  }

  @Override
  public void objectDeleting(ProductPO object) {
    if (LOGGER.isDebugEnabled()) {
      LOGGER.debug("PRODUCT LISTENER TEST - PRE DELETE");
    }

  }

}

But it is not working. 但这是行不通的。 Nothing gets logged when object changes or gets deleted. 对象更改或删除时,不会记录任何内容。

In addition to what Willem Evertse wrote you need to place your registration code in a class that gets instantiated via Intershop Component Framework. 除了Willem Evertse编写的内容外,您还需要将注册代码放在通过Intershop Component Framework实例化的类中。

implementation.component: implementation.component:

<components xmlns="http://www.intershop.de/component/2010" scope="global">
<implementation name="ProductDeleteListenerRegistrar"
    class="your.fullqualifed.ProductDeleteRegistrar" start="start" stop="stop"></implementation>

instances.component: instances.component:

<components xmlns="http://www.intershop.de/component/2010"> <instance name="ORMValidator" with="ORMValidator" scope="global"/></components>

You need to write a class, eg ProductDeleteRegistrar and provide start method in which you can add registration calls like Willem described. 您需要编写一个类,例如ProductDeleteRegistrar,并提供start方法,您可以在其中添加类似于Willem所述的注册调用。 As for stop method you need to safely unregister your object listener. 至于停止方法,您需要安全地注销您的对象侦听器。 Make sure both methods are declared to be synchronized. 确保两个方法都声明为同步。

I think registering a listen would be the right approach. 我认为注册听众是正确的方法。 Maybe just look out for performance problems. 也许只是寻找性能问题。

You are right that there are no examples of this, but here is an example. 没错,这里没有示例,但这是一个示例。 Get the factory that you want to receive messages from. 获取要从中接收消息的工厂。 In your case, it is ProductPOFactory 您的情况是ProductPOFactory

ProductPOFactory productFactory = (ProductPOFactory) NamingMgr.getInstance().lookupFactory(ProductPO.class);
productFactory.addObjectListener(new MyProductChangeListener());

MyProductChangeListener needs to extend AbstractORMObjectListener<ProductPO> and implement the method public void objectDeleting(T object) MyProductChangeListener需要扩展AbstractORMObjectListener<ProductPO>并实现方法public void objectDeleting(T object)

Every time a product gets deleted your listener should be called and then you can clean up your custom orm objects. 每次删除产品时,都应调用您的侦听器,然后您可以清理您的自定义orm对象。 You can have a look at ImageSetDefinitionPOListener as an example 您可以看一下ImageSetDefinitionPOListener作为示例

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM