cayenne-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From aadamc...@apache.org
Subject svn commit: r1052020 - in /cayenne/sandbox/cayenne-mixin/trunk: ./ src/main/java/org/apache/cayenne/mixin/audit/
Date Wed, 22 Dec 2010 18:31:32 GMT
Author: aadamchik
Date: Wed Dec 22 18:31:31 2010
New Revision: 1052020

URL: http://svn.apache.org/viewvc?rev=1052020&view=rev
Log:
@AuditableChild

Added:
    cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AuditableChild.java
Modified:
    cayenne/sandbox/cayenne-mixin/trunk/README.txt
    cayenne/sandbox/cayenne-mixin/trunk/pom.xml
    cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AbstractAuditableHandler.java
    cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/Auditable.java

Modified: cayenne/sandbox/cayenne-mixin/trunk/README.txt
URL: http://svn.apache.org/viewvc/cayenne/sandbox/cayenne-mixin/trunk/README.txt?rev=1052020&r1=1052019&r2=1052020&view=diff
==============================================================================
--- cayenne/sandbox/cayenne-mixin/trunk/README.txt (original)
+++ cayenne/sandbox/cayenne-mixin/trunk/README.txt Wed Dec 22 18:31:31 2010
@@ -1,9 +1,11 @@
 TODO:
 
 1. A reverse of @MixinRelationship - injecting mixin records into objects annotated with
some mixin annotation.
+2. Transactional auditable processing (with a mix of AuditableChild changes, multiple audit
events are generated for the same object)
 
 IMPLEMENTED:
 
+5. @AuditableChild
 4. Changeset tracking functionality
 3. @MixinRelationship and MixinRelationshipFilter to batch-fault and inject related objects
into mixin entity (e.g. Audit entity)
 2. @Auditable mixin with abstract handler allowing to store audit records in an arbitrary
format.

Modified: cayenne/sandbox/cayenne-mixin/trunk/pom.xml
URL: http://svn.apache.org/viewvc/cayenne/sandbox/cayenne-mixin/trunk/pom.xml?rev=1052020&r1=1052019&r2=1052020&view=diff
==============================================================================
--- cayenne/sandbox/cayenne-mixin/trunk/pom.xml (original)
+++ cayenne/sandbox/cayenne-mixin/trunk/pom.xml Wed Dec 22 18:31:31 2010
@@ -8,7 +8,7 @@
 		<version>3.1M1</version>
 	</parent>
 	<artifactId>cayenne-mixin</artifactId>
-	<version>3.1.0.8</version>
+	<version>3.1.0.11</version>
 	<name>Library: cayenne-mixin</name>
 	<packaging>jar</packaging>
 	<properties>

Modified: cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AbstractAuditableHandler.java
URL: http://svn.apache.org/viewvc/cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AbstractAuditableHandler.java?rev=1052020&r1=1052019&r2=1052020&view=diff
==============================================================================
--- cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AbstractAuditableHandler.java
(original)
+++ cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AbstractAuditableHandler.java
Wed Dec 22 18:31:31 2010
@@ -18,34 +18,79 @@
  ****************************************************************/
 package org.apache.cayenne.mixin.audit;
 
+import org.apache.cayenne.DataObject;
 import org.apache.cayenne.annotation.PostPersist;
 import org.apache.cayenne.annotation.PostRemove;
 import org.apache.cayenne.annotation.PostUpdate;
 
 /**
- * A superclass of application specific handlers of the {@link Auditable} mixin
- * that provides basic needed callbacks.
+ * A superclass of application specific handlers of the {@link Auditable} mixin that
+ * provides basic needed callbacks.
  */
 public abstract class AbstractAuditableHandler {
 
-	/**
-	 * A worker method that creates audit records, as appropriate in a given
-	 * application. Subclasses may insert audit records, log a message, etc.
-	 */
-	protected abstract void audit(Object object, AuditableOperation operation);
-
-	@PostPersist(entityAnnotations = Auditable.class)
-	void insertAudit(Object object) {
-		audit(object, AuditableOperation.INSERT);
-	}
-
-	@PostRemove(entityAnnotations = Auditable.class)
-	void deleteAudit(Object object) {
-		audit(object, AuditableOperation.DELETE);
-	}
-
-	@PostUpdate(entityAnnotations = Auditable.class)
-	void updateAudit(Object object) {
-		audit(object, AuditableOperation.UPDATE);
-	}
+    /**
+     * A worker method that creates audit records, as appropriate in a given application.
+     * Subclasses may insert audit records, log a message, etc.
+     */
+    protected abstract void audit(
+            Object auditRoot,
+            Object auditSource,
+            AuditableOperation operation);
+
+    @PostPersist(entityAnnotations = Auditable.class)
+    void insertAudit(Object object) {
+        audit(object, object, AuditableOperation.INSERT);
+    }
+
+    @PostRemove(entityAnnotations = Auditable.class)
+    void deleteAudit(Object object) {
+        audit(object, object, AuditableOperation.DELETE);
+    }
+
+    @PostUpdate(entityAnnotations = Auditable.class)
+    void updateAudit(Object object) {
+        audit(object, object, AuditableOperation.UPDATE);
+    }
+
+    // only catching child updates... child insert/delete presumably causes an event on
+    // the owner object
+
+    @PostUpdate(entityAnnotations = AuditableChild.class)
+    void updateAuditChild(Object object) {
+
+        Object parent = getParent(object);
+
+        if (parent != null) {
+            audit(parent, object, AuditableOperation.UPDATE);
+        }
+        else {
+            // at least og this fact... shouldn't normally happen, but I can imagine
+            // certain combinations of object graphs, disconnected relationships, delete
+            // rules, etc. may cause this
+        }
+    }
+
+    protected Object getParent(Object object) {
+
+        if (object == null) {
+            throw new NullPointerException("Null object");
+        }
+
+        if (!(object instanceof DataObject)) {
+            throw new IllegalArgumentException("Object is not a DataObject: "
+                    + object.getClass().getName());
+        }
+
+        DataObject dataObject = (DataObject) object;
+
+        AuditableChild annotation = dataObject.getClass().getAnnotation(
+                AuditableChild.class);
+        if (annotation == null) {
+            throw new IllegalArgumentException("No 'AuditableChild' annotation found");
+        }
+
+        // support for nested paths
+        return dataObject.readNestedProperty(annotation.value());
+    }
 }

Modified: cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/Auditable.java
URL: http://svn.apache.org/viewvc/cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/Auditable.java?rev=1052020&r1=1052019&r2=1052020&view=diff
==============================================================================
--- cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/Auditable.java
(original)
+++ cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/Auditable.java
Wed Dec 22 18:31:31 2010
@@ -28,9 +28,9 @@ import java.lang.annotation.Target;
 import org.apache.cayenne.mixin.ref.Referenceable;
 
 /**
- * A built-in mixin annotation that adds auditable behavior to DataObjects. All
- * Auditable objects must be also tagged with {@link Referenceable} annotation,
- * as audit records are based on UUIDs.
+ * A built-in annotation that adds auditable behavior to DataObjects. All Auditable
+ * objects must be also tagged with {@link Referenceable} annotation, as audit records are
+ * based on UUIDs.
  */
 @Target(ElementType.TYPE)
 @Retention(RetentionPolicy.RUNTIME)

Added: cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AuditableChild.java
URL: http://svn.apache.org/viewvc/cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AuditableChild.java?rev=1052020&view=auto
==============================================================================
--- cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AuditableChild.java
(added)
+++ cayenne/sandbox/cayenne-mixin/trunk/src/main/java/org/apache/cayenne/mixin/audit/AuditableChild.java
Wed Dec 22 18:31:31 2010
@@ -0,0 +1,26 @@
+package org.apache.cayenne.mixin.audit;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Inherited;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * A built-in annotation used to tag an object that is not auditable on its own, but whose
+ * changes should be tracked together with changes of another ("parent") object. This
+ * annotation allows to group changes in a closely related subtree of objects.
+ */
+@Target(ElementType.TYPE)
+@Retention(RetentionPolicy.RUNTIME)
+@Documented
+@Inherited
+public @interface AuditableChild {
+
+    /**
+     * Returns the name of a to-one relationship from an annotated object to the "parent"
+     * object that should be audited when annotated object is changed.
+     */
+    String value();
+}



Mime
View raw message