You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@polygene.apache.org by ni...@apache.org on 2015/04/17 18:42:56 UTC

[17/28] zest-qi4j git commit: tools/model-detail is now a VisitableHierarchy

tools/model-detail is now a VisitableHierarchy

Clarified api around Transients, it was left inconsistent.
Updated Envisage code to follow theses changes.

The visited hierarchy is structure/activators/composites only for now.
We could be more exhaustive by visiting down to each fragment details.


Project: http://git-wip-us.apache.org/repos/asf/zest-qi4j/repo
Commit: http://git-wip-us.apache.org/repos/asf/zest-qi4j/commit/70924bff
Tree: http://git-wip-us.apache.org/repos/asf/zest-qi4j/tree/70924bff
Diff: http://git-wip-us.apache.org/repos/asf/zest-qi4j/diff/70924bff

Branch: refs/heads/develop
Commit: 70924bffa47beb82e1d722e29e8df92ec4affc71
Parents: ae58d0d
Author: Paul Merlin <pa...@nosphere.org>
Authored: Sat Jan 24 17:57:06 2015 +0100
Committer: Paul Merlin <pa...@nosphere.org>
Committed: Sat Jan 24 17:57:06 2015 +0100

----------------------------------------------------------------------
 .../qi4j/envisage/detail/DetailModelPane.java   |   4 +-
 .../org/qi4j/envisage/detail/GeneralPane.java   |  10 +-
 .../org/qi4j/envisage/graph/GraphBuilder.java   |   8 +-
 .../java/org/qi4j/envisage/print/PDFWriter.java |   6 +-
 .../envisage/tree/StructureModelBuilder.java    |   6 +-
 .../envisage/tree/TreeModelCellRenderer.java    |   2 +-
 .../qi4j/envisage/tree/TypeModelBuilder.java    |   4 +-
 .../descriptor/ActivatorDetailDescriptor.java   |  15 +-
 .../descriptor/ApplicationDetailDescriptor.java |  34 ++++-
 .../ApplicationDetailDescriptorBuilder.java     |   7 +-
 .../descriptor/CompositeDetailDescriptor.java   |  15 +-
 .../descriptor/ConstructorDetailDescriptor.java |   3 +
 .../descriptor/EntityDetailDescriptor.java      |  16 +-
 .../ImportedServiceDetailDescriptor.java        |  29 +++-
 .../model/descriptor/LayerDetailDescriptor.java |  36 ++++-
 .../MethodConcernDetailDescriptor.java          |   6 +-
 .../descriptor/ModuleDetailDescriptor.java      |  85 +++++++++--
 .../descriptor/ObjectDetailDescriptor.java      |  15 +-
 .../descriptor/ServiceDetailDescriptor.java     |  28 +++-
 .../descriptor/TransientDetailDescriptor.java   |  40 +++++
 .../model/descriptor/ValueDetailDescriptor.java |  14 ++
 .../org/qi4j/tools/model/util/SPIFinder.java    |  50 +++----
 .../model/util/ServiceConfigurationFinder.java  |   8 +-
 .../tools/model/util/ServiceUsageFinder.java    |  28 ++--
 .../qi4j/tools/model/VisitableDetailTest.java   | 148 +++++++++++++++++++
 25 files changed, 519 insertions(+), 98 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/detail/DetailModelPane.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/detail/DetailModelPane.java b/tools/envisage/src/main/java/org/qi4j/envisage/detail/DetailModelPane.java
index deb4ee7..c92886b 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/detail/DetailModelPane.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/detail/DetailModelPane.java
@@ -26,13 +26,13 @@ import javax.swing.JTabbedPane;
 import javax.swing.SwingUtilities;
 import org.qi4j.envisage.event.LinkEvent;
 import org.qi4j.envisage.event.LinkListener;
-import org.qi4j.tools.model.descriptor.CompositeDetailDescriptor;
 import org.qi4j.tools.model.descriptor.EntityDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ImportedServiceDetailDescriptor;
 import org.qi4j.tools.model.descriptor.LayerDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ModuleDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 
 public final class DetailModelPane
@@ -163,7 +163,7 @@ public final class DetailModelPane
             tabPane.add( bundle.getString( "CTL_DependencyTab.Text" ), dependencyPane );
             tabPane.add( bundle.getString( "CTL_MethodTab.Text" ), methodPane );
         }
-        else if( objectDescriptor instanceof CompositeDetailDescriptor ) // this is transient
+        else if( objectDescriptor instanceof TransientDetailDescriptor )
         {
             tabPane.add( bundle.getString( "CTL_GeneralTab.Text" ), generalPane );
             tabPane.add( bundle.getString( "CTL_DependencyTab.Text" ), dependencyPane );

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/detail/GeneralPane.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/detail/GeneralPane.java b/tools/envisage/src/main/java/org/qi4j/envisage/detail/GeneralPane.java
index 0e70b6a..233bfe8 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/detail/GeneralPane.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/detail/GeneralPane.java
@@ -32,12 +32,12 @@ import org.qi4j.api.object.ObjectDescriptor;
 import org.qi4j.api.service.ServiceDescriptor;
 import org.qi4j.api.value.ValueDescriptor;
 import org.qi4j.envisage.util.TableRow;
-import org.qi4j.tools.model.descriptor.CompositeDetailDescriptor;
 import org.qi4j.tools.model.descriptor.EntityDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ImportedServiceCompositeDescriptor;
 import org.qi4j.tools.model.descriptor.ImportedServiceDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 
 import static org.qi4j.functional.Iterables.first;
@@ -200,15 +200,15 @@ import static org.qi4j.functional.Iterables.first;
                 rows.add( new TableRow( 2, moduleRow, ( (ObjectDetailDescriptor) objectDesciptor ).module() ) );
                 rows.add( new TableRow( 2, layerRow, ( (ObjectDetailDescriptor) objectDesciptor ).module().layer() ) );
             }
-            else if( objectDesciptor instanceof CompositeDetailDescriptor )
+            else if( objectDesciptor instanceof TransientDetailDescriptor )
             {
-                CompositeDescriptor descriptor = ( (CompositeDetailDescriptor) objectDesciptor ).descriptor();
+                CompositeDescriptor descriptor = ( (TransientDetailDescriptor) objectDesciptor ).descriptor();
                 Class<?> type = first( descriptor.types() );
                 rows.add( new TableRow( 2, nameRow, type.getSimpleName() ) );
                 rows.add( new TableRow( 2, classRow, type.getName() ) );
                 rows.add( new TableRow( 2, visibilityRow, descriptor.visibility().toString() ) );
-                rows.add( new TableRow( 2, moduleRow, ( (CompositeDetailDescriptor) objectDesciptor ).module() ) );
-                rows.add( new TableRow( 2, layerRow, ( (CompositeDetailDescriptor) objectDesciptor ).module().layer() ) );
+                rows.add( new TableRow( 2, moduleRow, ( (TransientDetailDescriptor) objectDesciptor ).module() ) );
+                rows.add( new TableRow( 2, layerRow, ( (TransientDetailDescriptor) objectDesciptor ).module().layer() ) );
             }
 
             fireTableDataChanged();

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/graph/GraphBuilder.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/graph/GraphBuilder.java b/tools/envisage/src/main/java/org/qi4j/envisage/graph/GraphBuilder.java
index 351cacc..656c96b 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/graph/GraphBuilder.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/graph/GraphBuilder.java
@@ -21,13 +21,13 @@ import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
 import org.qi4j.tools.model.descriptor.ApplicationDetailDescriptor;
-import org.qi4j.tools.model.descriptor.CompositeDetailDescriptor;
 import org.qi4j.tools.model.descriptor.EntityDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ImportedServiceDetailDescriptor;
 import org.qi4j.tools.model.descriptor.LayerDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ModuleDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 import org.qi4j.tools.model.util.DescriptorNameComparator;
 import prefuse.data.Edge;
@@ -143,7 +143,7 @@ import prefuse.data.Table;
             buildServicesNode( childNode, descriptor.services() );
             buildImportedServicesNode( childNode, descriptor.importedServices() );
             buildEntitiesNode( childNode, descriptor.entities() );
-            buildTransientsNode( childNode, descriptor.composites() );
+            buildTransientsNode( childNode, descriptor.transients() );
             buildValuesNode( childNode, descriptor.values() );
             buildObjectsNode( childNode, descriptor.objects() );
         }
@@ -214,14 +214,14 @@ import prefuse.data.Table;
         }
     }
 
-    private void buildTransientsNode( Node parent, Iterable<CompositeDetailDescriptor> iter )
+    private void buildTransientsNode( Node parent, Iterable<TransientDetailDescriptor> iter )
     {
         sortTypeChildren( iter );
 
         boolean first = true;
         for( Object obj : childList )
         {
-            CompositeDetailDescriptor descriptor = (CompositeDetailDescriptor) obj;
+            TransientDetailDescriptor descriptor = (TransientDetailDescriptor) obj;
             if( first )
             {
                 String name = "Transients";

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/print/PDFWriter.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/print/PDFWriter.java b/tools/envisage/src/main/java/org/qi4j/envisage/print/PDFWriter.java
index 3d1a177..da95957 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/print/PDFWriter.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/print/PDFWriter.java
@@ -210,7 +210,7 @@ public class PDFWriter
             writeServicesPage( descriptor.services() );
             writeImportedServicesPage( descriptor.importedServices() );
             writeEntitiesPage( descriptor.entities() );
-            writeTransientsPage( descriptor.composites() );
+            writeTransientsPage( descriptor.transients() );
             writeValuesPage( descriptor.values() );
             writeObjectsPage( descriptor.objects() );
         }
@@ -257,9 +257,9 @@ public class PDFWriter
         }
     }
 
-    private void writeTransientsPage( Iterable<CompositeDetailDescriptor> iter )
+    private void writeTransientsPage( Iterable<TransientDetailDescriptor> iter )
     {
-        for( CompositeDetailDescriptor descriptor : iter )
+        for( TransientDetailDescriptor descriptor : iter )
         {
             setFont( header4Font, header4FontSize );
             writeString( descriptor.toString(), headerLineSpace );

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/tree/StructureModelBuilder.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/tree/StructureModelBuilder.java b/tools/envisage/src/main/java/org/qi4j/envisage/tree/StructureModelBuilder.java
index 55f0c19..b19f359 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/tree/StructureModelBuilder.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/tree/StructureModelBuilder.java
@@ -64,7 +64,7 @@ import org.qi4j.tools.model.util.DescriptorNameComparator;
             buildServicesNode( node, descriptor.services() );
             buildImportedServicesNode( node, descriptor.importedServices() );
             buildEntitiesNode( node, descriptor.entities() );
-            buildTransientsNode( node, descriptor.composites() );  // This is transient type
+            buildTransientsNode( node, descriptor.transients() );
             buildValuesNode( node, descriptor.values() );
             buildObjectsNode( node, descriptor.objects() );
             parent.add( node );
@@ -117,10 +117,10 @@ import org.qi4j.tools.model.util.DescriptorNameComparator;
         addTypeChildren( parent, tempList );
     }
 
-    private void buildTransientsNode( DefaultMutableTreeNode parent, Iterable<CompositeDetailDescriptor> iter )
+    private void buildTransientsNode( DefaultMutableTreeNode parent, Iterable<TransientDetailDescriptor> iter )
     {
         tempList.clear();
-        for( CompositeDetailDescriptor descriptor : iter )
+        for( TransientDetailDescriptor descriptor : iter )
         {
             tempList.add( descriptor );
         }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/tree/TreeModelCellRenderer.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/tree/TreeModelCellRenderer.java b/tools/envisage/src/main/java/org/qi4j/envisage/tree/TreeModelCellRenderer.java
index 64f32a9..551bcca 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/tree/TreeModelCellRenderer.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/tree/TreeModelCellRenderer.java
@@ -105,7 +105,7 @@ import org.qi4j.tools.model.descriptor.*;
         {
             icon = valueIcon;
         }
-        else if( userObject instanceof CompositeDetailDescriptor )
+        else if( userObject instanceof TransientDetailDescriptor )
         {
             icon = transientIcon;
         }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/envisage/src/main/java/org/qi4j/envisage/tree/TypeModelBuilder.java
----------------------------------------------------------------------
diff --git a/tools/envisage/src/main/java/org/qi4j/envisage/tree/TypeModelBuilder.java b/tools/envisage/src/main/java/org/qi4j/envisage/tree/TypeModelBuilder.java
index 6bd9111..7b50aee 100644
--- a/tools/envisage/src/main/java/org/qi4j/envisage/tree/TypeModelBuilder.java
+++ b/tools/envisage/src/main/java/org/qi4j/envisage/tree/TypeModelBuilder.java
@@ -33,7 +33,7 @@ import org.qi4j.tools.model.util.DescriptorNameComparator;
     private final List<ServiceDetailDescriptor> serviceList = new ArrayList<>();
     private final List<ImportedServiceDetailDescriptor> importedServiceList = new ArrayList<>();
     private final List<EntityDetailDescriptor> entityList = new ArrayList<>();
-    private final List<CompositeDetailDescriptor> transientList = new ArrayList<>();
+    private final List<TransientDetailDescriptor> transientList = new ArrayList<>();
     private final List<ValueDetailDescriptor> valueList = new ArrayList<>();
     private final List<ObjectDetailDescriptor> objectList = new ArrayList<>();
 
@@ -131,7 +131,7 @@ import org.qi4j.tools.model.util.DescriptorNameComparator;
             }
 
             // Transient
-            for( CompositeDetailDescriptor child : descriptor.composites() )
+            for( TransientDetailDescriptor child : descriptor.transients() )
             {
                 transientList.add( child );
             }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ActivatorDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ActivatorDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ActivatorDetailDescriptor.java
index fdd04b0..e894d6e 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ActivatorDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ActivatorDetailDescriptor.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -20,6 +20,8 @@ package org.qi4j.tools.model.descriptor;
 import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.activation.ActivatorDescriptor;
+import org.qi4j.functional.Visitable;
+import org.qi4j.functional.Visitor;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
@@ -27,9 +29,8 @@ import static org.qi4j.api.util.NullArgumentException.validateNotNull;
  * Activator Detail Descriptor.
  */
 public class ActivatorDetailDescriptor
-    implements InjectableDetailDescriptor
+    implements InjectableDetailDescriptor, Visitable<ActivatorDetailDescriptor>
 {
-
     private final ActivatorDescriptor descriptor;
     private final List<ConstructorDetailDescriptor> constructors;
     private final List<InjectedMethodDetailDescriptor> injectedMethods;
@@ -161,9 +162,15 @@ public class ActivatorDetailDescriptor
     }
 
     @Override
+    public <ThrowableType extends Throwable> boolean accept( Visitor<? super ActivatorDetailDescriptor, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        return visitor.visit( this );
+    }
+
+    @Override
     public String toString()
     {
         return descriptor.toString();
     }
-
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptor.java
index bd7510f..1ec8b46 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptor.java
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -21,11 +21,18 @@ package org.qi4j.tools.model.descriptor;
 import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.structure.ApplicationDescriptor;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.functional.VisitableHierarchy;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Application Detail Descriptor.
+ * <p>
+ * Visitable hierarchy with Activators and Layers children.
+ */
 public final class ApplicationDetailDescriptor
-    implements ActivateeDetailDescriptor
+    implements ActivateeDetailDescriptor, VisitableHierarchy<Object, Object>
 {
     private final ApplicationDescriptor descriptor;
     private final List<ActivatorDetailDescriptor> activators = new LinkedList<>();
@@ -80,4 +87,27 @@ public final class ApplicationDetailDescriptor
         return descriptor.name();
     }
 
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( HierarchicalVisitor<? super Object, ? super Object, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        if( visitor.visitEnter( this ) )
+        {
+            for( ActivatorDetailDescriptor activator : activators )
+            {
+                if( !activator.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( LayerDetailDescriptor layer : layers )
+            {
+                if( !layer.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+        }
+        return visitor.visitLeave( this );
+    }
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptorBuilder.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptorBuilder.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptorBuilder.java
index e78565e..4d4e0cc 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptorBuilder.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ApplicationDetailDescriptorBuilder.java
@@ -2,7 +2,7 @@
  * Copyright (c) 2008, Rickard Öberg. All Rights Reserved.
  * Copyright (c) 2008, Sonny Gill. All Rights Reserved.
  * Copyright (c) 2008, Niclas Hedhman. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -208,8 +208,9 @@ public final class ApplicationDetailDescriptorBuilder
             }
             else if( visited instanceof TransientDescriptor )
             {
-                currCompositeDescriptor = new CompositeDetailDescriptor<>( (TransientDescriptor) visited );
-                currModuleDescriptor.addComposite( currCompositeDescriptor );
+                TransientDetailDescriptor descriptor = new TransientDetailDescriptor( (TransientDescriptor) visited );
+                currModuleDescriptor.addTransient( descriptor );
+                currCompositeDescriptor = descriptor;
             }
             else if( visited instanceof MethodDescriptor )
             {

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/CompositeDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/CompositeDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/CompositeDetailDescriptor.java
index 95643d8..02cb99b 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/CompositeDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/CompositeDetailDescriptor.java
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -25,7 +26,12 @@ import org.qi4j.api.composite.MethodDescriptor;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
-public class CompositeDetailDescriptor<T extends CompositeDescriptor>
+/**
+ * Composite Detail Descriptor.
+ *
+ * @param <T> CompositeDescriptor type
+ */
+public abstract class CompositeDetailDescriptor<T extends CompositeDescriptor>
 {
     protected final T descriptor;
     protected ModuleDetailDescriptor module;
@@ -37,8 +43,8 @@ public class CompositeDetailDescriptor<T extends CompositeDescriptor>
         validateNotNull( "aDescriptor", aDescriptor );
 
         descriptor = aDescriptor;
-        methods = new LinkedList<CompositeMethodDetailDescriptor>();
-        mixins = new LinkedList<MixinDetailDescriptor>();
+        methods = new LinkedList<>();
+        mixins = new LinkedList<>();
     }
 
     /**
@@ -130,8 +136,9 @@ public class CompositeDetailDescriptor<T extends CompositeDescriptor>
         mixins.add( aDescriptor );
     }
 
+    @Override
     public String toString()
     {
         return descriptor.toString();
     }
-}
\ No newline at end of file
+}

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ConstructorDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ConstructorDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ConstructorDetailDescriptor.java
index 764b624..646e80e 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ConstructorDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ConstructorDetailDescriptor.java
@@ -22,6 +22,9 @@ import org.qi4j.api.composite.ConstructorDescriptor;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Constructor Detail Descriptor.
+ */
 public final class ConstructorDetailDescriptor
 {
     private final ConstructorDescriptor descriptor;

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/EntityDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/EntityDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/EntityDetailDescriptor.java
index 9bb72da..7bfef2a 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/EntityDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/EntityDetailDescriptor.java
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -18,12 +19,25 @@
 package org.qi4j.tools.model.descriptor;
 
 import org.qi4j.api.entity.EntityDescriptor;
+import org.qi4j.functional.Visitable;
+import org.qi4j.functional.Visitor;
 
+/**
+ * Entity Detail Descriptor.
+ */
 public final class EntityDetailDescriptor
     extends CompositeDetailDescriptor<EntityDescriptor>
+    implements Visitable<EntityDetailDescriptor>
 {
     EntityDetailDescriptor( EntityDescriptor aDescriptor )
     {
         super( aDescriptor );
     }
-}
\ No newline at end of file
+
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( Visitor<? super EntityDetailDescriptor, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        return visitor.visit( this );
+    }
+}

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ImportedServiceDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ImportedServiceDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ImportedServiceDetailDescriptor.java
index 21b26da..a7fea24 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ImportedServiceDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ImportedServiceDetailDescriptor.java
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2009, Tonny Kohar. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -20,14 +20,20 @@ package org.qi4j.tools.model.descriptor;
 
 import java.util.LinkedList;
 import java.util.List;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.functional.VisitableHierarchy;
+
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
 /**
- * TODO need to refactor later, but wait until Qi4J core/spi have proper and consistent API for ImportedService.
+ * Imported Service Detail Descriptor.
+ * <p>
+ * Visitable hierarchy with Activators children.
  */
+// TODO need to refactor later, but wait until Qi4J core/spi have proper and consistent API for ImportedService.
 public class ImportedServiceDetailDescriptor
     extends CompositeDetailDescriptor<ImportedServiceCompositeDescriptor>
-    implements ActivateeDetailDescriptor
+    implements ActivateeDetailDescriptor, VisitableHierarchy<Object, Object>
 {
     private final List<ActivatorDetailDescriptor> activators = new LinkedList<>();
 
@@ -48,4 +54,21 @@ public class ImportedServiceDetailDescriptor
         descriptor.setImportedService( this );
         activators.add( descriptor );
     }
+
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( HierarchicalVisitor<? super Object, ? super Object, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        if( visitor.visitEnter( this ) )
+        {
+            for( ActivatorDetailDescriptor activator : activators )
+            {
+                if( !activator.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+        }
+        return visitor.visitLeave( this );
+    }
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/LayerDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/LayerDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/LayerDetailDescriptor.java
index 0de0c4e..8842de6 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/LayerDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/LayerDetailDescriptor.java
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -21,11 +21,18 @@ package org.qi4j.tools.model.descriptor;
 import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.structure.LayerDescriptor;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.functional.VisitableHierarchy;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Layer Detail Descriptor.
+ * <p>
+ * Visitable hierarchy with Activators and Modules children.
+ */
 public final class LayerDetailDescriptor
-    implements ActivateeDetailDescriptor
+    implements ActivateeDetailDescriptor, VisitableHierarchy<Object, Object>
 {
     private final LayerDescriptor descriptor;
     private ApplicationDetailDescriptor application;
@@ -125,9 +132,32 @@ public final class LayerDetailDescriptor
     }
 
     @Override
+    public <ThrowableType extends Throwable> boolean accept( HierarchicalVisitor<? super Object, ? super Object, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        if( visitor.visitEnter( this ) )
+        {
+            for( ActivatorDetailDescriptor activator : activators )
+            {
+                if( !activator.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( ModuleDetailDescriptor module : modules )
+            {
+                if( !module.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+        }
+        return visitor.visitLeave( this );
+    }
+
+    @Override
     public final String toString()
     {
         return descriptor.name();
     }
-
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/MethodConcernDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/MethodConcernDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/MethodConcernDetailDescriptor.java
index 6354cc0..8a2fa2d 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/MethodConcernDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/MethodConcernDetailDescriptor.java
@@ -40,9 +40,9 @@ public final class MethodConcernDetailDescriptor
 
         descriptor = aDescriptor;
 
-        constructors = new LinkedList<ConstructorDetailDescriptor>();
-        injectedMethods = new LinkedList<InjectedMethodDetailDescriptor>();
-        injectedFields = new LinkedList<InjectedFieldDetailDescriptor>();
+        constructors = new LinkedList<>();
+        injectedMethods = new LinkedList<>();
+        injectedFields = new LinkedList<>();
     }
 
     /**

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ModuleDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ModuleDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ModuleDetailDescriptor.java
index 9aada05..55625f9 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ModuleDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ModuleDetailDescriptor.java
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -21,11 +21,18 @@ package org.qi4j.tools.model.descriptor;
 import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.structure.ModuleDescriptor;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.functional.VisitableHierarchy;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Module Detail Descriptor.
+ * <p>
+ * Visitable hierarchy with Activators and Composites children.
+ */
 public final class ModuleDetailDescriptor
-    implements ActivateeDetailDescriptor
+    implements ActivateeDetailDescriptor, VisitableHierarchy<Object, Object>
 {
     private final ModuleDescriptor descriptor;
     private LayerDetailDescriptor layer;
@@ -33,7 +40,7 @@ public final class ModuleDetailDescriptor
     private final List<ServiceDetailDescriptor> services = new LinkedList<>();
     private final List<ImportedServiceDetailDescriptor> importedServices = new LinkedList<>();
     private final List<EntityDetailDescriptor> entities = new LinkedList<>();
-    private final List<CompositeDetailDescriptor> composites = new LinkedList<>();
+    private final List<TransientDetailDescriptor> transients = new LinkedList<>();
     private final List<ValueDetailDescriptor> values = new LinkedList<>();
     private final List<ObjectDetailDescriptor> objects = new LinkedList<>();
 
@@ -91,11 +98,11 @@ public final class ModuleDetailDescriptor
     }
 
     /**
-     * @return Composites of this {@code ModuleDetailDescriptor}. Never return {@code null}.
+     * @return Transients of this {@code ModuleDetailDescriptor}. Never return {@code null}.
      */
-    public final Iterable<CompositeDetailDescriptor> composites()
+    public final Iterable<TransientDetailDescriptor> transients()
     {
-        return composites;
+        return transients;
     }
 
     /**
@@ -156,11 +163,11 @@ public final class ModuleDetailDescriptor
         values.add( descriptor );
     }
 
-    final void addComposite( CompositeDetailDescriptor descriptor )
+    final void addTransient( TransientDetailDescriptor descriptor )
     {
-        validateNotNull( "CompositeDetailDescriptor", descriptor );
+        validateNotNull( "TransientDetailDescriptor", descriptor );
         descriptor.setModule( this );
-        composites.add( descriptor );
+        transients.add( descriptor );
     }
 
     final void addObject( ObjectDetailDescriptor descriptor )
@@ -171,9 +178,67 @@ public final class ModuleDetailDescriptor
     }
 
     @Override
+    public <ThrowableType extends Throwable> boolean accept( HierarchicalVisitor<? super Object, ? super Object, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        if( visitor.visitEnter( this ) )
+        {
+            for( ActivatorDetailDescriptor activator : activators )
+            {
+                if( !activator.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( ServiceDetailDescriptor service : services )
+            {
+                if( !service.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( ImportedServiceDetailDescriptor importedService : importedServices )
+            {
+                if( !importedService.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( EntityDetailDescriptor entity : entities )
+            {
+                if( !entity.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( ValueDetailDescriptor value : values )
+            {
+                if( !value.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( TransientDetailDescriptor composite : transients )
+            {
+                if( !composite.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+            for( ObjectDetailDescriptor object : objects )
+            {
+                if( !object.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+        }
+        return visitor.visitLeave( this );
+    }
+
+    @Override
     public final String toString()
     {
         return descriptor.name();
     }
-
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ObjectDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ObjectDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ObjectDetailDescriptor.java
index 49c1887..595e8e5 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ObjectDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ObjectDetailDescriptor.java
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -20,11 +21,16 @@ package org.qi4j.tools.model.descriptor;
 import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.object.ObjectDescriptor;
+import org.qi4j.functional.Visitable;
+import org.qi4j.functional.Visitor;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Object Detail Descriptor.
+ */
 public final class ObjectDetailDescriptor
-    implements InjectableDetailDescriptor
+    implements InjectableDetailDescriptor, Visitable<ObjectDetailDescriptor>
 {
     private final ObjectDescriptor descriptor;
     private ModuleDetailDescriptor module;
@@ -109,6 +115,13 @@ public final class ObjectDetailDescriptor
     }
 
     @Override
+    public <ThrowableType extends Throwable> boolean accept( Visitor<? super ObjectDetailDescriptor, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        return visitor.visit( this );
+    }
+
+    @Override
     public String toString()
     {
         return descriptor.toString();

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ServiceDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ServiceDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ServiceDetailDescriptor.java
index 671ab7e..52625d0 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ServiceDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ServiceDetailDescriptor.java
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2008, Edward Yakop. All Rights Reserved.
- * Copyright (c) 2014, Paul Merlin. All Rights Reserved.
+ * Copyright (c) 2014-2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -22,12 +22,19 @@ import java.util.LinkedList;
 import java.util.List;
 import org.qi4j.api.common.Visibility;
 import org.qi4j.api.service.ServiceDescriptor;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.functional.VisitableHierarchy;
 
 import static org.qi4j.api.util.NullArgumentException.validateNotNull;
 
+/**
+ * Service Detail Descriptor.
+ * <p>
+ * Visitable hierarchy with Activators children.
+ */
 public final class ServiceDetailDescriptor
     extends CompositeDetailDescriptor<ServiceDescriptor>
-    implements ActivateeDetailDescriptor
+    implements ActivateeDetailDescriptor, VisitableHierarchy<Object, Object>
 {
     private final List<ActivatorDetailDescriptor> activators = new LinkedList<>();
 
@@ -72,4 +79,21 @@ public final class ServiceDetailDescriptor
         descriptor.setService( this );
         activators.add( descriptor );
     }
+
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( HierarchicalVisitor<? super Object, ? super Object, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        if( visitor.visitEnter( this ) )
+        {
+            for( ActivatorDetailDescriptor activator : activators )
+            {
+                if( !activator.accept( visitor ) )
+                {
+                    break;
+                }
+            }
+        }
+        return visitor.visitLeave( this );
+    }
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/TransientDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/TransientDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/TransientDetailDescriptor.java
new file mode 100644
index 0000000..f7a39ed
--- /dev/null
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/TransientDetailDescriptor.java
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.qi4j.tools.model.descriptor;
+
+import org.qi4j.api.composite.TransientDescriptor;
+import org.qi4j.functional.Visitable;
+import org.qi4j.functional.Visitor;
+
+/**
+ * Transient Detail Descriptor.
+ */
+public class TransientDetailDescriptor
+    extends CompositeDetailDescriptor<TransientDescriptor>
+    implements Visitable<TransientDetailDescriptor>
+{
+    TransientDetailDescriptor( TransientDescriptor aDescriptor )
+    {
+        super( aDescriptor );
+    }
+
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( Visitor<? super TransientDetailDescriptor, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        return visitor.visit( this );
+    }
+}

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ValueDetailDescriptor.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ValueDetailDescriptor.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ValueDetailDescriptor.java
index ded6934..b09c987 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ValueDetailDescriptor.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/descriptor/ValueDetailDescriptor.java
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2009, Tonny Kohar. All Rights Reserved.
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
  *
  * Licensed  under the  Apache License,  Version 2.0  (the "License");
  * you may not use  this file  except in  compliance with the License.
@@ -18,12 +19,25 @@
 package org.qi4j.tools.model.descriptor;
 
 import org.qi4j.api.value.ValueDescriptor;
+import org.qi4j.functional.Visitable;
+import org.qi4j.functional.Visitor;
 
+/**
+ * Value Detail Descriptor.
+ */
 public class ValueDetailDescriptor
     extends CompositeDetailDescriptor<ValueDescriptor>
+    implements Visitable<ValueDetailDescriptor>
 {
     ValueDetailDescriptor( ValueDescriptor aDescriptor )
     {
         super( aDescriptor );
     }
+
+    @Override
+    public <ThrowableType extends Throwable> boolean accept( Visitor<? super ValueDetailDescriptor, ThrowableType> visitor )
+        throws ThrowableType
+    {
+        return visitor.visit( this );
+    }
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/util/SPIFinder.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/SPIFinder.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/SPIFinder.java
index fd8381f..86adff2 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/SPIFinder.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/SPIFinder.java
@@ -1,25 +1,25 @@
-/*  Copyright 2009 Tonny Kohar.
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
-* implied.
-*
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
+/*
+ * Copyright (c) 2009, Tonny Kohar. All Rights Reserved.
+ *
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ *
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
 package org.qi4j.tools.model.util;
 
 import java.util.ArrayList;
 import java.util.List;
 import org.qi4j.tools.model.descriptor.ApplicationDetailDescriptor;
-import org.qi4j.tools.model.descriptor.CompositeDetailDescriptor;
 import org.qi4j.tools.model.descriptor.EntityDetailDescriptor;
 import org.qi4j.tools.model.descriptor.InjectedFieldDetailDescriptor;
 import org.qi4j.tools.model.descriptor.LayerDetailDescriptor;
@@ -27,27 +27,26 @@ import org.qi4j.tools.model.descriptor.MixinDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ModuleDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 
 /**
- * SPI would be defined as "All service dependencies which
- * are not satisfied from within the module or Layer".
+ * SPI would be defined as "All service dependencies which are not satisfied from within the module or Layer".
  */
 class SPIFinder
 {
-
     private ApplicationDetailDescriptor appDetailDescriptor;
 
     public List<ServiceDetailDescriptor> findModule( ModuleDetailDescriptor descriptor )
     {
         appDetailDescriptor = descriptor.layer().application();
 
-        ArrayList<ServiceDetailDescriptor> list = new ArrayList<ServiceDetailDescriptor>();
+        ArrayList<ServiceDetailDescriptor> list = new ArrayList<>();
 
         findInServices( descriptor.services(), list );
         findInEntities( descriptor.entities(), list );
         findInValues( descriptor.values(), list );
-        findInTransients( descriptor.composites(), list );
+        findInTransients( descriptor.transients(), list );
         findInObjects( descriptor.objects(), list );
 
         return list;
@@ -55,7 +54,7 @@ class SPIFinder
 
     public List<ServiceDetailDescriptor> findLayerSPI( LayerDetailDescriptor descriptor )
     {
-        ArrayList<ServiceDetailDescriptor> list = new ArrayList<ServiceDetailDescriptor>();
+        List<ServiceDetailDescriptor> list = new ArrayList<>();
 
         for( ModuleDetailDescriptor moduleDetailDescriptor : descriptor.modules() )
         {
@@ -124,9 +123,9 @@ class SPIFinder
         }
     }
 
-    private void findInTransients( Iterable<CompositeDetailDescriptor> iter, ArrayList<ServiceDetailDescriptor> list )
+    private void findInTransients( Iterable<TransientDetailDescriptor> iter, ArrayList<ServiceDetailDescriptor> list )
     {
-        for( CompositeDetailDescriptor descriptor : iter )
+        for( TransientDetailDescriptor descriptor : iter )
         {
             findInMixin( descriptor.mixins(), list );
         }
@@ -165,7 +164,6 @@ class SPIFinder
                 break;
             }
         }
-
         return serviceDetailDescriptor;
     }
 }

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceConfigurationFinder.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceConfigurationFinder.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceConfigurationFinder.java
index 7b4577e..999ad28 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceConfigurationFinder.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceConfigurationFinder.java
@@ -24,6 +24,7 @@ import org.qi4j.tools.model.descriptor.LayerDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ModuleDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 
 import static org.qi4j.functional.Iterables.first;
@@ -86,8 +87,7 @@ class ServiceConfigurationFinder
                 break;
             }
 
-            // findInTransients
-            obj = findInTypes( descriptor.composites(), configType );
+            obj = findInTypes( descriptor.transients(), configType );
             if( obj != null )
             {
                 configDescriptor = obj;
@@ -136,6 +136,10 @@ class ServiceConfigurationFinder
             {
                 descriptor = ( (ObjectDetailDescriptor) obj ).descriptor();
             }
+            else if( obj instanceof TransientDetailDescriptor )
+            {
+                descriptor = ( (TransientDetailDescriptor) obj ).descriptor();
+            }
             else
             {
                 descriptor = ( (CompositeDetailDescriptor) obj ).descriptor();

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceUsageFinder.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceUsageFinder.java b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceUsageFinder.java
index 6ba3a3d..3bf2cc0 100644
--- a/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceUsageFinder.java
+++ b/tools/model-detail/src/main/java/org/qi4j/tools/model/util/ServiceUsageFinder.java
@@ -1,16 +1,16 @@
-/*  
- * Copyright 2009 Tonny Kohar.
- * Copyright 2012 Paul Merlin.
+/*
+ * Copyright (c) 2009, Tonny Kohar. All Rights Reserved.
+ * Copyright (c) 2012-2015, Paul Merlin. All Rights Reserved.
  *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
  * You may obtain a copy of the License at
  *
- * http://www.apache.org/licenses/LICENSE-2.0
+ *   http://www.apache.org/licenses/LICENSE-2.0
  *
  * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
  * implied.
  *
  * See the License for the specific language governing permissions and
@@ -25,7 +25,6 @@ import org.qi4j.api.composite.DependencyDescriptor;
 import org.qi4j.api.injection.scope.Service;
 import org.qi4j.api.injection.scope.Uses;
 import org.qi4j.tools.model.descriptor.ApplicationDetailDescriptor;
-import org.qi4j.tools.model.descriptor.CompositeDetailDescriptor;
 import org.qi4j.tools.model.descriptor.EntityDetailDescriptor;
 import org.qi4j.tools.model.descriptor.InjectedFieldDetailDescriptor;
 import org.qi4j.tools.model.descriptor.LayerDetailDescriptor;
@@ -34,6 +33,7 @@ import org.qi4j.tools.model.descriptor.ModuleDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ObjectDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ServiceUsage;
+import org.qi4j.tools.model.descriptor.TransientDetailDescriptor;
 import org.qi4j.tools.model.descriptor.ValueDetailDescriptor;
 
 import static org.qi4j.functional.Iterables.first;
@@ -45,7 +45,7 @@ import static org.qi4j.functional.Iterables.first;
 
     public List<ServiceUsage> findServiceUsage( ServiceDetailDescriptor descriptor )
     {
-        usages = new ArrayList<ServiceUsage>();
+        usages = new ArrayList<>();
 
         this.descriptor = descriptor;
 
@@ -71,7 +71,7 @@ import static org.qi4j.functional.Iterables.first;
             collectInServices( descriptor.services() );
             collectInEntities( descriptor.entities() );
             collectInValues( descriptor.values() );
-            collectInTransients( descriptor.composites() );
+            collectInTransients( descriptor.transients() );
             collectInObjects( descriptor.objects() );
         }
     }
@@ -104,9 +104,9 @@ import static org.qi4j.functional.Iterables.first;
         }
     }
 
-    private void collectInTransients( Iterable<CompositeDetailDescriptor> iter )
+    private void collectInTransients( Iterable<TransientDetailDescriptor> iter )
     {
-        for( CompositeDetailDescriptor descriptor : iter )
+        for( TransientDetailDescriptor descriptor : iter )
         {
             collectInMixin( descriptor.mixins() );
         }
@@ -139,7 +139,7 @@ import static org.qi4j.functional.Iterables.first;
             if( Uses.class.equals( clazz ) || Service.class.equals( clazz ) )
             {
                 boolean used = false;
-                if( dependencyDescriptor.injectionType().equals( first( this.descriptor.descriptor().types() )) )
+                if( dependencyDescriptor.injectionType().equals( first( this.descriptor.descriptor().types() ) ) )
                 {
                     ServiceUsage usage;
                     if( ownerDescriptor instanceof MixinDetailDescriptor )

http://git-wip-us.apache.org/repos/asf/zest-qi4j/blob/70924bff/tools/model-detail/src/test/java/org/qi4j/tools/model/VisitableDetailTest.java
----------------------------------------------------------------------
diff --git a/tools/model-detail/src/test/java/org/qi4j/tools/model/VisitableDetailTest.java b/tools/model-detail/src/test/java/org/qi4j/tools/model/VisitableDetailTest.java
new file mode 100644
index 0000000..b0e5a9b
--- /dev/null
+++ b/tools/model-detail/src/test/java/org/qi4j/tools/model/VisitableDetailTest.java
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2015, Paul Merlin. All Rights Reserved.
+ *
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ *
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.qi4j.tools.model;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import org.junit.Test;
+import org.qi4j.api.activation.ActivationException;
+import org.qi4j.api.activation.ActivatorAdapter;
+import org.qi4j.api.structure.Application;
+import org.qi4j.api.structure.ApplicationDescriptor;
+import org.qi4j.api.structure.Layer;
+import org.qi4j.api.structure.Module;
+import org.qi4j.bootstrap.ApplicationAssembler;
+import org.qi4j.bootstrap.ApplicationAssembly;
+import org.qi4j.bootstrap.ApplicationAssemblyFactory;
+import org.qi4j.bootstrap.AssemblyException;
+import org.qi4j.bootstrap.Energy4Java;
+import org.qi4j.bootstrap.LayerAssembly;
+import org.qi4j.bootstrap.ModuleAssembly;
+import org.qi4j.functional.HierarchicalVisitor;
+import org.qi4j.tools.model.descriptor.ApplicationDetailDescriptor;
+
+import static org.hamcrest.CoreMatchers.equalTo;
+import static org.junit.Assert.assertThat;
+import static org.qi4j.tools.model.descriptor.ApplicationDetailDescriptorBuilder.createApplicationDetailDescriptor;
+
+/**
+ * Visitable Detail Test.
+ */
+public class VisitableDetailTest
+{
+    @Test
+    public void visit()
+        throws AssemblyException, ActivationException
+    {
+        ApplicationDescriptor application = new Energy4Java().newApplicationModel(
+            new ApplicationAssembler()
+            {
+                @Override
+                public ApplicationAssembly assemble( ApplicationAssemblyFactory applicationFactory )
+                throws AssemblyException
+                {
+                    ApplicationAssembly app = applicationFactory.newApplicationAssembly();
+                    app.setName( "UnderTestApp" );
+                    app.withActivators( ApplicationActivator.class );
+
+                    LayerAssembly layer = app.layer( "LayerName" );
+                    layer.withActivators( LayerActivator.class );
+
+                    ModuleAssembly module = layer.module( "ModuleName" );
+                    module.withActivators( ModuleActivator.class );
+
+                    return app;
+                }
+            }
+        );
+        ApplicationDetailDescriptor detail = createApplicationDetailDescriptor( application );
+        Visitor visitor = new Visitor();
+        detail.accept( visitor );
+        assertThat(
+            visitor.events,
+            equalTo( Arrays.asList(
+                    // Application
+                    "visitEnter( UnderTestApp )",
+                    "visit( " + ApplicationActivator.class.getName() + " )",
+                    // Layer
+                    "visitEnter( LayerName )",
+                    "visit( " + LayerActivator.class.getName() + " )",
+                    // Module
+                    "visitEnter( ModuleName )",
+                    "visit( " + ModuleActivator.class.getName() + " )",
+                    // Leaving Structure
+                    "visitLeave( ModuleName )",
+                    "visitLeave( LayerName )",
+                    "visitLeave( UnderTestApp )"
+                )
+            )
+        );
+    }
+
+    private static final class Visitor
+        implements HierarchicalVisitor<Object, Object, RuntimeException>
+    {
+        private final List<String> events = new ArrayList<>();
+
+        @Override
+        public boolean visitEnter( Object visited )
+            throws RuntimeException
+        {
+            String event = "visitEnter( " + visited + " )";
+            events.add( event );
+            System.out.println( event );
+            return true;
+        }
+
+        @Override
+        public boolean visitLeave( Object visited )
+            throws RuntimeException
+        {
+            String event = "visitLeave( " + visited + " )";
+            events.add( event );
+            System.out.println( event );
+            return true;
+        }
+
+        @Override
+        public boolean visit( Object visited )
+            throws RuntimeException
+        {
+            String event = "visit( " + visited + " )";
+            events.add( event );
+            System.out.println( event );
+            return true;
+        }
+    }
+
+    static class ApplicationActivator
+        extends ActivatorAdapter<Application>
+    {
+    }
+
+    static class LayerActivator
+        extends ActivatorAdapter<Layer>
+    {
+    }
+
+    static class ModuleActivator
+        extends ActivatorAdapter<Module>
+    {
+    }
+}