You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@brooklyn.apache.org by al...@apache.org on 2014/07/18 12:00:41 UTC

[05/10] git commit: Resolve catalog items and yaml URLs from child entities as well.

Resolve catalog items and yaml URLs from child entities as well.


Project: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/commit/6bc8d49f
Tree: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/tree/6bc8d49f
Diff: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/diff/6bc8d49f

Branch: refs/heads/master
Commit: 6bc8d49f954e4bdbf186fa9581a57766465f1f98
Parents: 201717a
Author: Svetoslav Neykov <sv...@cloudsoftcorp.com>
Authored: Wed Jul 16 13:20:01 2014 +0300
Committer: Svetoslav Neykov <sv...@cloudsoftcorp.com>
Committed: Wed Jul 16 15:13:37 2014 +0300

----------------------------------------------------------------------
 .../BrooklynAssemblyTemplateInstantiator.java   |  78 +++++++-------
 .../BrooklynComponentTemplateResolver.java      |   2 +-
 .../brooklyn/camp/brooklyn/CatalogYamlTest.java | 105 ++++++++++++++++---
 .../camp/brooklyn/ReferencedYamlTest.java       |  24 ++++-
 4 files changed, 150 insertions(+), 59 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/6bc8d49f/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynAssemblyTemplateInstantiator.java
----------------------------------------------------------------------
diff --git a/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynAssemblyTemplateInstantiator.java b/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynAssemblyTemplateInstantiator.java
index d7eaeb3..a5a67ea 100644
--- a/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynAssemblyTemplateInstantiator.java
+++ b/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynAssemblyTemplateInstantiator.java
@@ -204,44 +204,51 @@ public class BrooklynAssemblyTemplateInstantiator implements AssemblyTemplateSpe
         for (ResolvableLink<PlatformComponentTemplate> ctl: template.getPlatformComponentTemplates().links()) {
             PlatformComponentTemplate appChildComponentTemplate = ctl.resolve();
             BrooklynComponentTemplateResolver entityResolver = BrooklynComponentTemplateResolver.Factory.newInstance(loader, appChildComponentTemplate);
-            ManagementContext mgmt = loader.getManagementContext();
+            EntitySpec<?> spec = resolveSpec(entityResolver, encounteredCatalogTypes);
+            
+            result.add(spec);
+        }
+        return result;
+    }
 
-            String brooklynType = entityResolver.getBrooklynType();
-            CatalogItem<Entity, EntitySpec<?>> item = entityResolver.getCatalogItem();
+    private EntitySpec<?> resolveSpec(
+            BrooklynComponentTemplateResolver entityResolver, 
+            Set<String> encounteredCatalogTypes) {
+        ManagementContext mgmt = entityResolver.loader.getManagementContext();
 
-            boolean firstOccurrence = encounteredCatalogTypes.add(brooklynType);
-            boolean recursiveButTryJava = !firstOccurrence;
-                         
-            if (log.isTraceEnabled()) log.trace("Building CAMP template services: type="+brooklynType+"; item="+item+"; loader="+loader+"; template="+template+"; encounteredCatalogTypes="+encounteredCatalogTypes);
+        String brooklynType = entityResolver.getBrooklynType();
+        CatalogItem<Entity, EntitySpec<?>> item = entityResolver.getCatalogItem();
 
-            EntitySpec<?> spec = null;
-            if (BrooklynCampConstants.YAML_URL_PROTOCOL_WHITELIST.contains(Urls.getProtocol(brooklynType))) {
-                spec = tryResolveYamlURLReferenceSpec(brooklynType, loader, encounteredCatalogTypes);
-                if (spec != null) {
-                    entityResolver.populateSpec(spec);
-                }
+        boolean firstOccurrence = encounteredCatalogTypes.add(brooklynType);
+        boolean recursiveButTryJava = !firstOccurrence;
+        
+        if (log.isTraceEnabled()) log.trace("Building CAMP template services: type="+brooklynType+"; item="+item+"; loader="+entityResolver.loader+"; encounteredCatalogTypes="+encounteredCatalogTypes);
+
+        EntitySpec<?> spec = null;
+        if (BrooklynCampConstants.YAML_URL_PROTOCOL_WHITELIST.contains(Urls.getProtocol(brooklynType))) {
+            spec = tryResolveYamlURLReferenceSpec(brooklynType, entityResolver.loader, encounteredCatalogTypes);
+            if (spec != null) {
+                entityResolver.populateSpec(spec);
             }
-            
-            if (spec == null) {
-                if (item == null || item.getJavaType() != null || entityResolver.isJavaTypePrefix()) {
-                    spec = entityResolver.resolveSpec();
-                } else if (recursiveButTryJava) {
-                    if (entityResolver.tryLoadEntityClass().isAbsent()) {
-                        throw new IllegalStateException("Recursive reference to " + brooklynType + " (and cannot be resolved as a Java type)");
-                    }
-                    spec = entityResolver.resolveSpec();
-                } else {
-                    spec = resolveCatalogYamlReferenceSpec(mgmt, item, encounteredCatalogTypes);
-                    entityResolver.populateSpec(spec);
+        }
+        
+        if (spec == null) {
+            if (item == null || item.getJavaType() != null || entityResolver.isJavaTypePrefix()) {
+                spec = entityResolver.resolveSpec();
+            } else if (recursiveButTryJava) {
+                if (entityResolver.tryLoadEntityClass().isAbsent()) {
+                    throw new IllegalStateException("Recursive reference to " + brooklynType + " (and cannot be resolved as a Java type)");
                 }
+                spec = entityResolver.resolveSpec();
+            } else {
+                spec = resolveCatalogYamlReferenceSpec(mgmt, item, encounteredCatalogTypes);
+                entityResolver.populateSpec(spec);
             }
-
-            BrooklynClassLoadingContext newLoader = entityResolver.loader;
-            buildChildrenEntitySpecs(newLoader, spec, entityResolver.getChildren(appChildComponentTemplate.getCustomAttributes()));
-            
-            result.add(spec);
         }
-        return result;
+
+        BrooklynClassLoadingContext newLoader = entityResolver.loader;
+        buildChildrenEntitySpecs(newLoader, spec, entityResolver.getChildren(entityResolver.attrs.getAllConfig()), encounteredCatalogTypes);
+        return spec;
     }
 
     private EntitySpec<?> tryResolveYamlURLReferenceSpec(
@@ -310,17 +317,12 @@ public class BrooklynAssemblyTemplateInstantiator implements AssemblyTemplateSpe
         }
     }
 
-    protected void buildChildrenEntitySpecs(BrooklynClassLoadingContext loader, EntitySpec<?> parent, List<Map<String, Object>> childConfig) {
+    protected void buildChildrenEntitySpecs(BrooklynClassLoadingContext loader, EntitySpec<?> parent, List<Map<String, Object>> childConfig, Set<String> encounteredCatalogTypes) {
         if (childConfig != null) {
             for (Map<String, Object> childAttrs : childConfig) {
                 BrooklynComponentTemplateResolver entityResolver = BrooklynComponentTemplateResolver.Factory.newInstance(loader, childAttrs);
-                EntitySpec<? extends Entity> spec = entityResolver.resolveSpec();
+                EntitySpec<? extends Entity> spec = resolveSpec(entityResolver, encounteredCatalogTypes);
                 parent.child(spec);
-
-                // get the new loader in case the OSGi bundles from parent were added;
-                // not so important now but if we start working with versions this may be important
-                BrooklynClassLoadingContext newLoader = entityResolver.loader;
-                buildChildrenEntitySpecs(newLoader, spec, entityResolver.getChildren(childAttrs));
             }
         }
     }

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/6bc8d49f/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynComponentTemplateResolver.java
----------------------------------------------------------------------
diff --git a/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynComponentTemplateResolver.java b/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynComponentTemplateResolver.java
index 9d3f43c..155342a 100644
--- a/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynComponentTemplateResolver.java
+++ b/usage/camp/src/main/java/io/brooklyn/camp/brooklyn/spi/creation/BrooklynComponentTemplateResolver.java
@@ -395,7 +395,7 @@ public class BrooklynComponentTemplateResolver {
     }
 
     @SuppressWarnings("unchecked")
-    public List<Map<String, Object>> getChildren(Map<String, Object> attrs) {
+    protected List<Map<String, Object>> getChildren(Map<String, Object> attrs) {
         if (attrs==null) return null;
         return (List<Map<String, Object>>) attrs.get("brooklyn.children");
     }

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/6bc8d49f/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/CatalogYamlTest.java
----------------------------------------------------------------------
diff --git a/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/CatalogYamlTest.java b/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/CatalogYamlTest.java
index 6eb8b1e..7cc5235 100644
--- a/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/CatalogYamlTest.java
+++ b/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/CatalogYamlTest.java
@@ -22,10 +22,13 @@ import static org.testng.Assert.assertEquals;
 import static org.testng.Assert.assertTrue;
 import static org.testng.Assert.fail;
 
+import java.util.Collection;
+
 import org.testng.annotations.Test;
 
 import brooklyn.catalog.CatalogItem;
 import brooklyn.entity.Entity;
+import brooklyn.entity.basic.BasicEntity;
 import brooklyn.management.osgi.OsgiStandaloneTest;
 
 import com.google.common.collect.Iterables;
@@ -41,7 +44,6 @@ public class CatalogYamlTest extends AbstractYamlTest {
         
         CatalogItem<?, ?> item = mgmt().getCatalog().getCatalogItem(registeredTypeName);
         assertEquals(item.getRegisteredTypeName(), registeredTypeName);
-        
     }
 
     @Test
@@ -49,7 +51,7 @@ public class CatalogYamlTest extends AbstractYamlTest {
         String registeredTypeName = "my.catalog.app.id.launch";
         registerAndLaunchAndAssertSimpleEntity(registeredTypeName, SIMPLE_ENTITY_TYPE);
     }
-
+    
     @Test
     public void testLaunchApplicationWithCatalogReferencingOtherCatalog() throws Exception {
         String referencedRegisteredTypeName = "my.catalog.app.id.referenced";
@@ -68,6 +70,35 @@ public class CatalogYamlTest extends AbstractYamlTest {
     }
 
     @Test
+    public void testLaunchApplicationChildWithCatalogReferencingOtherCatalog() throws Exception {
+        String referencedRegisteredTypeName = "my.catalog.app.id.child.referenced";
+        String referrerRegisteredTypeName = "my.catalog.app.id.child.referring";
+        addCatalogOSGiEntity(referencedRegisteredTypeName, SIMPLE_ENTITY_TYPE);
+        addCatalogChildOSGiEntity(referrerRegisteredTypeName, referencedRegisteredTypeName);
+
+        Entity app = createAndStartApplication(
+            "name: simple-app-yaml",
+            "location: localhost",
+            "services:",
+            "- serviceType: "+BasicEntity.class.getName(),
+            "  brooklyn.children:",
+            "  - type: " + referrerRegisteredTypeName);
+        
+        Collection<Entity> children = app.getChildren();
+        assertEquals(children.size(), 1);
+        Entity child = Iterables.getOnlyElement(children);
+        assertEquals(child.getEntityType().getName(), BasicEntity.class.getName());
+        Collection<Entity> grandChildren = child.getChildren();
+        assertEquals(grandChildren.size(), 1);
+        Entity grandChild = Iterables.getOnlyElement(grandChildren);
+        assertEquals(grandChild.getEntityType().getName(), BasicEntity.class.getName());
+        Collection<Entity> grandGrandChildren = grandChild.getChildren();
+        assertEquals(grandGrandChildren.size(), 1);
+        Entity grandGrandChild = Iterables.getOnlyElement(grandGrandChildren);
+        assertEquals(grandGrandChild.getEntityType().getName(), SIMPLE_ENTITY_TYPE);
+    }
+
+    @Test
     public void testLaunchApplicationWithTypeUsingJavaColonPrefix() throws Exception {
         String registeredTypeName = SIMPLE_ENTITY_TYPE;
         String serviceName = "java:"+SIMPLE_ENTITY_TYPE;
@@ -86,6 +117,28 @@ public class CatalogYamlTest extends AbstractYamlTest {
         String registeredTypeName = "self.referencing.type";
         registerAndLaunchFailsWithRecursionError(registeredTypeName, registeredTypeName);
     }
+    
+    @Test
+    public void testLaunchApplicationChildLoopCatalogIdFails() throws Exception {
+        String referrerRegisteredTypeName = "my.catalog.app.id.child.referring";
+        addCatalogChildOSGiEntity(referrerRegisteredTypeName, referrerRegisteredTypeName);
+
+        try {
+            createAndStartApplication(
+                "name: simple-app-yaml",
+                "location: localhost",
+                "services:",
+                "- serviceType: "+BasicEntity.class.getName(),
+                "  brooklyn.children:",
+                "  - type: " + referrerRegisteredTypeName);
+            
+                fail("Expected to throw IllegalStateException");
+        } catch (IllegalStateException e) {
+            assertTrue(e.getMessage().contains("Recursive reference to "+referrerRegisteredTypeName));
+        } finally {
+            deleteCatalogEntity(referrerRegisteredTypeName);
+        }
+    }
 
     private void registerAndLaunchAndAssertSimpleEntity(String registeredTypeName, String serviceType) throws Exception {
         addCatalogOSGiEntity(registeredTypeName, serviceType);
@@ -126,23 +179,41 @@ public class CatalogYamlTest extends AbstractYamlTest {
     }
     
     private void addCatalogOSGiEntity(String registeredTypeName, String serviceType) {
-        String catalogYaml =
-            "name: "+registeredTypeName+"\n"+
+        addCatalogItem(
+            "name: "+registeredTypeName,
+            // FIXME name above should be unnecessary -- slight problem somewhere currently
+            // as testListApplicationYaml fails without the line above
+            "brooklyn.catalog:",
+            "  id: " + registeredTypeName,
+            "  name: My Catalog App",
+            "  description: My description",
+            "  icon_url: classpath://path/to/myicon.jpg",
+            "  version: 0.1.2",
+            "  libraries:",
+            "  - url: " + OsgiStandaloneTest.BROOKLYN_TEST_OSGI_ENTITIES_URL,
+            "",
+            "services:",
+            "- type: " + serviceType);
+    }
+
+    private void addCatalogChildOSGiEntity(String registeredTypeName, String serviceType) {
+        addCatalogItem(
+            "name: "+registeredTypeName,
             // FIXME name above should be unnecessary -- slight problem somewhere currently
             // as testListApplicationYaml fails without the line above
-            "brooklyn.catalog:\n"+
-            "  id: " + registeredTypeName + "\n"+
-            "  name: My Catalog App\n"+
-            "  description: My description\n"+
-            "  icon_url: classpath://path/to/myicon.jpg\n"+
-            "  version: 0.1.2\n"+
-            "  libraries:\n"+
-            "  - url: " + OsgiStandaloneTest.BROOKLYN_TEST_OSGI_ENTITIES_URL + "\n"+
-            "\n"+
-            "services:\n"+
-            "- type: " + serviceType;
-
-        addCatalogItem(catalogYaml);
+            "brooklyn.catalog:",
+            "  id: " + registeredTypeName,
+            "  name: My Catalog App",
+            "  description: My description",
+            "  icon_url: classpath://path/to/myicon.jpg",
+            "  version: 0.1.2",
+            "  libraries:",
+            "  - url: " + OsgiStandaloneTest.BROOKLYN_TEST_OSGI_ENTITIES_URL,
+            "",
+            "services:",
+            "- type: " + BasicEntity.class.getName(),
+            "  brooklyn.children:",
+            "  - type: " + serviceType);
     }
 
 }

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/6bc8d49f/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/ReferencedYamlTest.java
----------------------------------------------------------------------
diff --git a/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/ReferencedYamlTest.java b/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/ReferencedYamlTest.java
index d70497d..b2ad68b 100644
--- a/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/ReferencedYamlTest.java
+++ b/usage/camp/src/test/java/io/brooklyn/camp/brooklyn/ReferencedYamlTest.java
@@ -26,7 +26,6 @@ import org.testng.annotations.Test;
 import brooklyn.entity.Entity;
 import brooklyn.entity.basic.BasicApplication;
 import brooklyn.entity.basic.BasicEntity;
-import brooklyn.test.entity.TestEntity;
 
 import com.google.common.collect.Iterables;
 
@@ -44,6 +43,15 @@ public class ReferencedYamlTest extends AbstractYamlTest {
     }
 
     @Test
+    public void testAnonymousReferenceEntityYamlAsPlatformComponent() throws Exception {
+        Entity app = createAndStartApplication(
+            "services:",
+            "- type: classpath://yaml-ref-entity.yaml");
+        
+        checkChildEntitySpec(app, "service");
+    }
+
+    @Test
     public void testReferenceAppYamlAsPlatformComponent() throws Exception {
         Entity app = createAndStartApplication(
             "services:",
@@ -57,8 +65,7 @@ public class ReferencedYamlTest extends AbstractYamlTest {
         Assert.assertEquals(app.getEntityType().getName(), BasicApplication.class.getName());
     }
 
-    //the test fails, since the current code doesn't allow for nested yaml references
-    @Test(enabled = false)
+    @Test
     public void testReferenceYamlAsChild() throws Exception {
         String entityName = "Reference child name";
         Entity createAndStartApplication = createAndStartApplication(
@@ -72,6 +79,17 @@ public class ReferencedYamlTest extends AbstractYamlTest {
     }
 
     @Test
+    public void testAnonymousReferenceYamlAsChild() throws Exception {
+        Entity createAndStartApplication = createAndStartApplication(
+            "services:",
+            "- type: brooklyn.entity.basic.BasicEntity",
+            "  brooklyn.children:",
+            "  - type: classpath://yaml-ref-entity.yaml");
+        
+        checkGrandchildEntitySpec(createAndStartApplication, "service");
+    }
+
+    @Test
     public void testCatalogReferencingYamlUrl() throws Exception {
         addCatalogItem(
             "brooklyn.catalog:",