We do this by extending the CayenneDataObject class and introducing a HashMap that tracks the original value of the properties that have changed. Override the writeProperty/setToOneTarget (we only care about auditing attributes and belongsTo relationships.
Then when it comes time to Insert/Update then you can loop over the properties you want to “audit” and check if they are modified This map gets reset after commits. protected Map<String,Object> originalPropertyMap = new HashMap<String,Object>(); @PostPersist @PostUpdate public void initializeOriginalPropertyMap() { this.originalPropertyMap.clear(); } @Override public void writeProperty(String property, Object value) { if (!this.originalPropertyMap.containsKey(property)) { this.originalPropertyMap.put(property, this.readProperty(property)); } super.writeProperty(property, value); } @Override public void setToOneTarget(String relationship, org.apache.cayenne.DataObject value, boolean reverse) { if (!this.originalPropertyMap.containsKey(relationship)) { this.originalPropertyMap.put(relationship, this.readProperty(relationship)); } super.setToOneTarget(relationship, value, reverse); } @Override public Boolean isPropertyModified(String property) { Object original = this.getOriginalProperty(property); Object current = this.readProperty(property); // if property is an attribute and array, then use array compares PropertyDescriptor propertyDescriptor = Cayenne.getProperty(this, property); if(propertyDescriptor instanceof AttributeProperty) { if(((AttributeProperty)propertyDescriptor).getAttribute().getJavaClass().isArray()) { return !Objects.deepEquals(original, current); } } return !Objects.equals(original, current); } > On Aug 7, 2015, at 7:16 AM, Hugi Thordarson <h...@karlmenn.is> wrote: > > Hi all. > > I’m attempting to implement an audit log using Cayenne, automatically storing > information on modifications alongside every insert, update and delete. > > I’m currently doing this by adding a listener on the DataDomain that watches > for the lifecycle events PrePersist, PreUpdate and PreRemove, and there I log > what’s happening with the objects. Works perfectly. > > One thing I’m wondering though. How can I find what has changed in an object > in PreUpdate (i.d. when logging modifications)? For those familiar with EOF, > I do it there by looking at the > EOEditingContext’s.commitedSnapshotForObject() and comparing the values found > there with the object’s current values—but I can’t find how to to do > something similar in Cayenne. > > Am I maybe going about this in a completely wrong way (and there’s perhaps a > much better, more Cayenne-ish way to do this)? If so, I’d be grateful if > someone could point me in the correct direction :). > > Thanks once again, > - hugi > > // Hugi Thordarson > // http://www.loftfar.is/ <http://www.loftfar.is/> > // s. 895-6688