You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@brooklyn.apache.org by he...@apache.org on 2016/11/29 13:40:20 UTC
[06/13] brooklyn-server git commit: BROOKLYN-345: add (failing) tests
for rebind
BROOKLYN-345: add (failing) tests for rebind
Project: http://git-wip-us.apache.org/repos/asf/brooklyn-server/repo
Commit: http://git-wip-us.apache.org/repos/asf/brooklyn-server/commit/b97cd178
Tree: http://git-wip-us.apache.org/repos/asf/brooklyn-server/tree/b97cd178
Diff: http://git-wip-us.apache.org/repos/asf/brooklyn-server/diff/b97cd178
Branch: refs/heads/master
Commit: b97cd17839d8414fb70339de37417abc0d3ff574
Parents: c856cd1
Author: Aled Sage <al...@gmail.com>
Authored: Wed Nov 16 09:58:08 2016 +0000
Committer: Aled Sage <al...@gmail.com>
Committed: Mon Nov 28 21:11:48 2016 +0000
----------------------------------------------------------------------
.../camp/brooklyn/AbstractYamlRebindTest.java | 1 +
.../camp/brooklyn/ConfigParametersYamlTest.java | 87 ++++++++---
.../camp/brooklyn/DslAndRebindYamlTest.java | 18 +++
.../ServiceFailureDetectorYamlRebindTest.java | 147 +++++++++++++++++++
.../rebind/RecordingRebindExceptionHandler.java | 33 ++++-
5 files changed, 258 insertions(+), 28 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/b97cd178/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/AbstractYamlRebindTest.java
----------------------------------------------------------------------
diff --git a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/AbstractYamlRebindTest.java b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/AbstractYamlRebindTest.java
index 5eae76c..2ba96e2 100644
--- a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/AbstractYamlRebindTest.java
+++ b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/AbstractYamlRebindTest.java
@@ -82,6 +82,7 @@ public class AbstractYamlRebindTest extends RebindTestFixture<StartableApplicati
}
}
+ @Override
protected StartableApplication rebind(RebindOptions options) throws Exception {
StartableApplication result = super.rebind(options);
if (launcher != null) {
http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/b97cd178/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ConfigParametersYamlTest.java
----------------------------------------------------------------------
diff --git a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ConfigParametersYamlTest.java b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ConfigParametersYamlTest.java
index 7d6828a..2f655c6 100644
--- a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ConfigParametersYamlTest.java
+++ b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ConfigParametersYamlTest.java
@@ -55,7 +55,7 @@ import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Iterables;
-public class ConfigParametersYamlTest extends AbstractYamlTest {
+public class ConfigParametersYamlTest extends AbstractYamlRebindTest {
@SuppressWarnings("unused")
private static final Logger LOG = LoggerFactory.getLogger(ConfigParametersYamlTest.class);
@@ -77,6 +77,40 @@ public class ConfigParametersYamlTest extends AbstractYamlTest {
}
@Test
+ public void testConfigParameterWithOverriddenValueListedInType() throws Exception {
+ addCatalogItems(
+ "brooklyn.catalog:",
+ " itemType: entity",
+ " items:",
+ " - id: entity-with-keys",
+ " item:",
+ " type: "+TestEntity.class.getName(),
+ " brooklyn.parameters:",
+ " - name: testConfigParametersListedInType.mykey",
+ " description: myDescription",
+ " type: String",
+ " default: myDefaultVal",
+ " brooklyn.config:",
+ " testConfigParametersListedInType.mykey: myOverridingVal");
+
+ String yaml = Joiner.on("\n").join(
+ "services:",
+ "- type: entity-with-keys");
+
+ Entity app = createStartWaitAndLogApplication(yaml);
+ TestEntity entity = (TestEntity) Iterables.getOnlyElement(app.getChildren());
+
+ // Check config key is listed
+ assertKeyEquals(entity, "testConfigParametersListedInType.mykey", "myDescription", String.class, "myDefaultVal", "myOverridingVal");
+
+ // Rebind, and then check again that the config key is listed
+ Entity newApp = rebind();
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(newApp.getChildren());
+ assertKeyEquals(newEntity, "testConfigParametersListedInType.mykey", "myDescription", String.class, "myDefaultVal", "myOverridingVal");
+ }
+
+
+ @Test
public void testConfigParametersListedInType() throws Exception {
addCatalogItems(
"brooklyn.catalog:",
@@ -100,19 +134,17 @@ public class ConfigParametersYamlTest extends AbstractYamlTest {
TestEntity entity = (TestEntity) Iterables.getOnlyElement(app.getChildren());
// Check config key is listed
- ConfigKey<?> key = entity.getEntityType().getConfigKey("testConfigParametersListedInType.mykey");
- assertNotNull(key);
- assertEquals(key.getName(), "testConfigParametersListedInType.mykey");
- assertEquals(key.getDescription(), "myDescription");
- assertEquals(key.getType(), Map.class);
- assertEquals(key.getDefaultValue(), ImmutableMap.of("myDefaultKey", "myDefaultVal"));
-
- // Check get default value
- assertEquals(entity.config().get(key), ImmutableMap.of("myDefaultKey", "myDefaultVal"));
+ Map<?,?> expectedVal = ImmutableMap.of("myDefaultKey", "myDefaultVal");
+ assertKeyEquals(entity, "testConfigParametersListedInType.mykey", "myDescription", Map.class, expectedVal, expectedVal);
+
+ // Rebind, and then check again that the config key is listed
+ Entity newApp = rebind();
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(newApp.getChildren());
+ assertKeyEquals(newEntity, "testConfigParametersListedInType.mykey", "myDescription", Map.class, expectedVal, expectedVal);
}
/**
- * See comment in testConfigParametersAtRootListedInTemplateSingleEntity for why we have two
+ * See comment in testConfigParametersAtRootListedInTemplateSingleEntity for why we have two.
* Note that (surprisingly!) it's very important that there are two entities listed under
* "services". If there is just one, then the BasicApplication created to wrap it will not
* have the key. Instead, the single child will have the key. This is because the top-level
@@ -144,11 +176,11 @@ public class ConfigParametersYamlTest extends AbstractYamlTest {
Entity app = createStartWaitAndLogApplication(yaml);
- ConfigKey<?> key = app.getEntityType().getConfigKey("test.parameter");
- assertNotNull(key, "No key 'test.parameter'; keys="+app.getEntityType().getConfigKeys());
- assertEquals(key.getDescription(), "myDescription");
- assertEquals(key.getType(), String.class);
- assertEquals(key.getDefaultValue(), "myDefaultParamVal");
+ assertKeyEquals(app, "test.parameter", "myDescription", String.class, "myDefaultParamVal", "myDefaultParamVal");
+
+ // After rebind, check config key is listed
+ newApp = rebind();
+ assertKeyEquals(newApp, "test.parameter", "myDescription", String.class, "myDefaultParamVal", "myDefaultParamVal");
}
/**
@@ -178,11 +210,12 @@ public class ConfigParametersYamlTest extends AbstractYamlTest {
Entity app = createStartWaitAndLogApplication(yaml);
TestEntity entity = (TestEntity) Iterables.getOnlyElement(app.getChildren());
- ConfigKey<?> key = entity.getEntityType().getConfigKey("test.parameter");
- assertNotNull(key, "No key 'test.parameter'; keys="+entity.getEntityType().getConfigKeys());
- assertEquals(key.getDescription(), "myDescription");
- assertEquals(key.getType(), String.class);
- assertEquals(key.getDefaultValue(), "myDefaultParamVal");
+ assertKeyEquals(entity, "test.parameter", "myDescription", String.class, "myDefaultParamVal", "myDefaultParamVal");
+
+ // After rebind, check config key is listed
+ newApp = rebind();
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(newApp.getChildren());
+ assertKeyEquals(newEntity, "test.parameter", "myDescription", String.class, "myDefaultParamVal", "myDefaultParamVal");
}
@Test
@@ -614,4 +647,16 @@ public class ConfigParametersYamlTest extends AbstractYamlTest {
assertEquals(entity.config().get(ConfigKeys.newConfigKey(Object.class, "my.param.key")), PortRanges.fromInteger(1234));
assertEquals(entity.sensors().get(Sensors.newSensor(Object.class, "my.param.key")), 1234);
}
+
+ protected <T> void assertKeyEquals(Entity entity, String keyName, String expectedDescription, Class<T> expectedType, T expectedDefaultVal, T expectedEntityVal) {
+ ConfigKey<?> key = entity.getEntityType().getConfigKey(keyName);
+ assertNotNull(key, "No key '"+keyName+"'; keys="+entity.getEntityType().getConfigKeys());
+
+ assertEquals(key.getName(), keyName);
+ assertEquals(key.getDescription(), expectedDescription);
+ assertEquals(key.getType(), expectedType);
+ assertEquals(key.getDefaultValue(), expectedDefaultVal);
+
+ assertEquals(entity.config().get(key), expectedEntityVal);
+ }
}
http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/b97cd178/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/DslAndRebindYamlTest.java
----------------------------------------------------------------------
diff --git a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/DslAndRebindYamlTest.java b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/DslAndRebindYamlTest.java
index 91da883..9770338 100644
--- a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/DslAndRebindYamlTest.java
+++ b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/DslAndRebindYamlTest.java
@@ -386,6 +386,7 @@ public class DslAndRebindYamlTest extends AbstractYamlRebindTest {
Entity e2 = rebind(testEntity);
Assert.assertEquals(getConfigInTask(e2, TestEntity.CONF_NAME), "bar");
+ Assert.assertEquals(e2.getConfig(TestEntity.CONF_NAME), "bar");
}
private Entity entityWithConfigFromRoot() throws Exception {
@@ -397,6 +398,23 @@ public class DslAndRebindYamlTest extends AbstractYamlRebindTest {
" foo: bar");
}
+ @Test
+ public void testDslConfigWithBrooklynParameterDefault() throws Exception {
+ Entity testEntity = setupAndCheckTestEntityInBasicYamlWith(
+ " id: x",
+ " brooklyn.parameters:",
+ " - name: test.param",
+ " type: String",
+ " default: myDefaultVal",
+ " brooklyn.config:",
+ " test.confName: $brooklyn:config(\"test.param\")");
+ Assert.assertEquals(getConfigInTask(testEntity, TestEntity.CONF_NAME), "myDefaultVal");
+ Assert.assertEquals(testEntity.config().get(TestEntity.CONF_NAME), "myDefaultVal");
+
+ Entity e2 = rebind(testEntity);
+ Assert.assertEquals(getConfigInTask(e2, TestEntity.CONF_NAME), "myDefaultVal");
+ Assert.assertEquals(e2.config().get(TestEntity.CONF_NAME), "myDefaultVal");
+ }
@Test
public void testDslFormatString() throws Exception {
http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/b97cd178/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ServiceFailureDetectorYamlRebindTest.java
----------------------------------------------------------------------
diff --git a/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ServiceFailureDetectorYamlRebindTest.java b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ServiceFailureDetectorYamlRebindTest.java
new file mode 100644
index 0000000..377a2a5
--- /dev/null
+++ b/camp/camp-brooklyn/src/test/java/org/apache/brooklyn/camp/brooklyn/ServiceFailureDetectorYamlRebindTest.java
@@ -0,0 +1,147 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.apache.brooklyn.camp.brooklyn;
+
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.appVersionedId;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.assertEnricherConfigMatchesDsl;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.assertHasEnricher;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.catalogYamlSimple;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.catalogYamlWithDsl;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.catalogYamlWithDslReferenceParentDefault;
+import static org.apache.brooklyn.camp.brooklyn.ServiceFailureDetectorYamlTest.subscribeToHaSensors;
+
+import org.apache.brooklyn.api.entity.Entity;
+import org.apache.brooklyn.api.mgmt.rebind.RebindManager.RebindFailureMode;
+import org.apache.brooklyn.core.entity.RecordingSensorEventListener;
+import org.apache.brooklyn.core.entity.StartableApplication;
+import org.apache.brooklyn.core.entity.lifecycle.ServiceStateLogic.ServiceNotUpLogic;
+import org.apache.brooklyn.core.mgmt.rebind.RebindExceptionHandlerImpl;
+import org.apache.brooklyn.core.mgmt.rebind.RebindOptions;
+import org.apache.brooklyn.core.mgmt.rebind.RecordingRebindExceptionHandler;
+import org.apache.brooklyn.core.sensor.SensorEventPredicates;
+import org.apache.brooklyn.core.test.entity.TestEntity;
+import org.apache.brooklyn.policy.ha.HASensors;
+import org.apache.brooklyn.policy.ha.ServiceFailureDetector;
+import org.testng.annotations.Test;
+
+import com.google.common.base.Joiner;
+import com.google.common.collect.Iterables;
+
+@Test
+public class ServiceFailureDetectorYamlRebindTest extends AbstractYamlRebindTest {
+
+ final static String INDICATOR_KEY_1 = "test-indicator-1";
+
+ @Test
+ public void testRebindWhenHealthy() throws Exception {
+ runRebindWhenHealthy(catalogYamlSimple, appVersionedId);
+ }
+
+ @Test
+ public void testRebindWhenHealthyWithDslConfig() throws Exception {
+ runRebindWhenHealthy(catalogYamlWithDsl, appVersionedId);
+
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(app().getChildren());
+ ServiceFailureDetector newEnricher = assertHasEnricher(newEntity, ServiceFailureDetector.class);
+ assertEnricherConfigMatchesDsl(newEnricher);
+ }
+
+ @Test
+ public void testRebindWhenHealthyWithDslConfigReferenceParentDefault() throws Exception {
+ runRebindWhenHealthy(catalogYamlWithDslReferenceParentDefault, appVersionedId);
+
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(app().getChildren());
+ ServiceFailureDetector newEnricher = assertHasEnricher(newEntity, ServiceFailureDetector.class);
+ assertEnricherConfigMatchesDsl(newEnricher);
+ }
+
+ @Test
+ public void testRebindWhenHasNotUpIndicator() throws Exception {
+ runRebindWhenNotUp(catalogYamlSimple, appVersionedId);
+ }
+
+ // See https://issues.apache.org/jira/browse/BROOKLYN-345
+ @Test
+ public void testRebinWhenHasNotUpIndicatorWithDslConfig() throws Exception {
+ runRebindWhenNotUp(catalogYamlWithDsl, appVersionedId);
+ }
+
+ // See https://issues.apache.org/jira/browse/BROOKLYN-345
+ @Test
+ public void testRebindWhenHasNotUpIndicatorWithDslConfigReferenceParentDefault() throws Exception {
+ runRebindWhenNotUp(catalogYamlWithDslReferenceParentDefault, appVersionedId);
+ }
+
+ protected void runRebindWhenHealthy(String catalogYaml, String appId) throws Exception {
+ addCatalogItems(catalogYaml);
+
+ String appYaml = Joiner.on("\n").join(
+ "services:",
+ "- type: " + appId);
+ createStartWaitAndLogApplication(appYaml);
+
+ // Rebind
+ StartableApplication newApp = rebind();
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(newApp.getChildren());
+ assertHasEnricher(newEntity, ServiceFailureDetector.class);
+
+ // Confirm ServiceFailureDetector still functions
+ RecordingSensorEventListener<Object> listener = subscribeToHaSensors(newEntity);
+
+ ServiceNotUpLogic.updateNotUpIndicator(newEntity, INDICATOR_KEY_1, "Simulate a problem");
+ listener.assertHasEventEventually(SensorEventPredicates.sensorEqualTo(HASensors.ENTITY_FAILED));
+ listener.assertEventCount(1);
+ }
+
+ protected void runRebindWhenNotUp(String catalogYaml, String appId) throws Exception {
+ addCatalogItems(catalogYaml);
+
+ String appYaml = Joiner.on("\n").join(
+ "services:",
+ "- type: " + appId);
+ Entity app = createStartWaitAndLogApplication(appYaml);
+
+ // Make entity go on-fire
+ TestEntity entity = (TestEntity) Iterables.getOnlyElement(app.getChildren());
+ RecordingSensorEventListener<Object> listener = subscribeToHaSensors(entity);
+ ServiceNotUpLogic.updateNotUpIndicator(entity, INDICATOR_KEY_1, "Simulating a problem");
+ listener.assertHasEventEventually(SensorEventPredicates.sensorEqualTo(HASensors.ENTITY_FAILED));
+
+ // Rebind
+ StartableApplication newApp = rebind();
+ TestEntity newEntity = (TestEntity) Iterables.getOnlyElement(newApp.getChildren());
+ assertHasEnricher(newEntity, ServiceFailureDetector.class);
+
+ // Confirm ServiceFailureDetector still functions
+ RecordingSensorEventListener<Object> newListener = subscribeToHaSensors(newEntity);
+
+ ServiceNotUpLogic.clearNotUpIndicator(newEntity, INDICATOR_KEY_1);
+ newListener.assertHasEventEventually(SensorEventPredicates.sensorEqualTo(HASensors.ENTITY_RECOVERED));
+ newListener.assertEventCount(1);
+ }
+
+ @Override
+ protected StartableApplication rebind() throws Exception {
+ RecordingRebindExceptionHandler exceptionHandler = new RecordingRebindExceptionHandler(RebindExceptionHandlerImpl.builder()
+ .addPolicyFailureMode(RebindFailureMode.FAIL_AT_END)
+ .loadPolicyFailureMode(RebindFailureMode.FAIL_AT_END)
+ .danglingRefFailureMode(RebindFailureMode.FAIL_AT_END));
+ return rebind(RebindOptions.create().exceptionHandler(exceptionHandler));
+ }
+}
http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/b97cd178/core/src/test/java/org/apache/brooklyn/core/mgmt/rebind/RecordingRebindExceptionHandler.java
----------------------------------------------------------------------
diff --git a/core/src/test/java/org/apache/brooklyn/core/mgmt/rebind/RecordingRebindExceptionHandler.java b/core/src/test/java/org/apache/brooklyn/core/mgmt/rebind/RecordingRebindExceptionHandler.java
index 6d27fc7..b94970d 100644
--- a/core/src/test/java/org/apache/brooklyn/core/mgmt/rebind/RecordingRebindExceptionHandler.java
+++ b/core/src/test/java/org/apache/brooklyn/core/mgmt/rebind/RecordingRebindExceptionHandler.java
@@ -22,28 +22,35 @@ import java.util.List;
import java.util.Map;
import org.apache.brooklyn.api.entity.Entity;
+import org.apache.brooklyn.api.entity.EntityLocal;
import org.apache.brooklyn.api.location.Location;
import org.apache.brooklyn.api.mgmt.rebind.RebindManager;
import org.apache.brooklyn.api.objs.BrooklynObject;
import org.apache.brooklyn.api.objs.BrooklynObjectType;
-import org.apache.brooklyn.core.mgmt.rebind.RebindExceptionHandlerImpl;
+import org.apache.brooklyn.api.policy.Policy;
+import org.apache.brooklyn.api.sensor.Enricher;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
public class RecordingRebindExceptionHandler extends RebindExceptionHandlerImpl {
- protected final List<Exception> loadMementoFailures = Lists.newArrayList();
- protected final Map<String, Exception> createFailures = Maps.newLinkedHashMap();
- protected final Map<BrooklynObject, Exception> rebindFailures = Maps.newLinkedHashMap();
- protected final Map<BrooklynObject, Exception> manageFailures = Maps.newLinkedHashMap();
- protected final Map<String, Exception> notFoundFailures = Maps.newLinkedHashMap();
- protected Exception failed;
+ public final List<Exception> loadMementoFailures = Lists.newArrayList();
+ public final Map<String, Exception> createFailures = Maps.newLinkedHashMap();
+ public final Map<BrooklynObject, Exception> rebindFailures = Maps.newLinkedHashMap();
+ public final Map<BrooklynObject, Exception> manageFailures = Maps.newLinkedHashMap();
+ public final Map<BrooklynObject, Exception> addFailures = Maps.newLinkedHashMap();
+ public final Map<String, Exception> notFoundFailures = Maps.newLinkedHashMap();
+ public Exception failed;
public RecordingRebindExceptionHandler(RebindManager.RebindFailureMode danglingRefFailureMode, RebindManager.RebindFailureMode rebindFailureMode) {
super(builder().danglingRefFailureMode(danglingRefFailureMode).rebindFailureMode(rebindFailureMode));
}
+ public RecordingRebindExceptionHandler(Builder builder) {
+ super(builder);
+ }
+
@Override
public void onLoadMementoFailed(BrooklynObjectType type, String msg, Exception e) {
loadMementoFailures.add(new IllegalStateException("problem loading "+type.toCamelCase()+" memento: "+msg, e));
@@ -89,4 +96,16 @@ public class RecordingRebindExceptionHandler extends RebindExceptionHandlerImpl
failed = e;
return super.onFailed(e);
}
+
+ @Override
+ public void onAddEnricherFailed(EntityLocal entity, Enricher enricher, Exception e) {
+ addFailures.put(enricher, e);
+ super.onAddEnricherFailed(entity, enricher, e);
+ }
+
+ @Override
+ public void onAddPolicyFailed(EntityLocal entity, Policy policy, Exception e) {
+ addFailures.put(policy, e);
+ super.onAddPolicyFailed(entity, policy, e);
+ }
}