summaryrefslogtreecommitdiffstats
path: root/controlloop/common/guard/src/test
diff options
context:
space:
mode:
Diffstat (limited to 'controlloop/common/guard/src/test')
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardResultTest.java40
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardUtilTest.java109
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PIPEngineGetHistoryTest.java233
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardRequestTest.java53
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardResponseTest.java50
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardTest.java173
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlHelperTest.java154
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlRequestAttributesTest.java64
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardYamlToXacmlTest.java208
-rw-r--r--controlloop/common/guard/src/test/java/org/onap/policy/guard/TextFileUtils.java63
-rw-r--r--controlloop/common/guard/src/test/resources/blacklist_template.xml55
-rw-r--r--controlloop/common/guard/src/test/resources/frequency_limiter_template.xml58
12 files changed, 1199 insertions, 61 deletions
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardResultTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardResultTest.java
new file mode 100644
index 000000000..b4d417e35
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardResultTest.java
@@ -0,0 +1,40 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import static org.junit.Assert.*;
+
+import org.junit.Test;
+
+public class GuardResultTest {
+
+ @Test
+ public void guardResultTest() {
+ assertEquals(3, GuardResult.values().length);
+ assertNotNull(GuardResult.LOCK_ACQUIRED);
+ assertNotNull(GuardResult.LOCK_DENIED);
+ assertNotNull(GuardResult.LOCK_EXCEPTION);
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, GuardResult.valueOf("LOCK_ACQUIRED"));
+ assertEquals(GuardResult.LOCK_DENIED, GuardResult.valueOf("LOCK_DENIED"));
+ assertEquals(GuardResult.LOCK_EXCEPTION, GuardResult.valueOf("LOCK_EXCEPTION"));
+ }
+}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardUtilTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardUtilTest.java
new file mode 100644
index 000000000..9e1d1b29e
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/GuardUtilTest.java
@@ -0,0 +1,109 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import static org.junit.Assert.*;
+
+import java.io.File;
+import java.io.IOException;
+
+import org.junit.Test;
+import org.onap.policy.controlloop.policy.ControlLoopPolicy;
+import org.onap.policy.controlloop.policy.guard.ControlLoopGuard;
+import org.onap.policy.guard.Util.Pair;
+import org.yaml.snakeyaml.Yaml;
+import org.yaml.snakeyaml.constructor.Constructor;
+
+import com.att.aft.dme2.internal.google.common.io.Files;
+
+public class GuardUtilTest {
+ @Test
+ public void testLoadYamlOK() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+
+ ControlLoopPolicy clPolicy = new ControlLoopPolicy();
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopPolicy.class));
+ String clYamlString = clYaml.dump(clPolicy);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+
+ Pair<ControlLoopPolicy, String> result = Util.loadYaml(tempYAMLFile.getCanonicalPath());
+
+ assertEquals(clPolicy, result.a);
+ assertEquals(clYamlString, result.b);
+
+ tempYAMLFile.delete();
+ }
+
+ @Test
+ public void testLoadYamlError() throws IOException {
+ File tempDir = Files.createTempDir();
+
+ // Read from a directory forces an IO exception
+ assertNull(Util.loadYaml(tempDir.getCanonicalPath()));
+
+ tempDir.delete();
+ }
+
+ @Test
+ public void testLoadGuardYamlOK() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+
+ ControlLoopGuard clGuardPolicy = new ControlLoopGuard();
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopPolicy.class));
+ String clYamlString = clYaml.dump(clGuardPolicy);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+
+ ControlLoopGuard result = Util.loadYamlGuard(tempYAMLFile.getCanonicalPath());
+
+ assertEquals(clGuardPolicy, result);
+
+ tempYAMLFile.delete();
+ }
+
+ @Test
+ public void testLoadGuardYamlError() throws IOException {
+ File tempDir = Files.createTempDir();
+
+ // Read from a directory forces an IO exception
+ assertNull(Util.loadYamlGuard(tempDir.getCanonicalPath()));
+
+ tempDir.delete();
+ }
+
+ @Test
+ public void testMisc() {
+ Util.setGuardEnvProp("Actor", "Judy Garland");
+ assertEquals("Judy Garland", Util.getGuardProp("Actor"));
+
+ Util.setGuardEnvProps("http://somewhere.over.the.rainbow", "Dorothy", "Toto", "Wizard", "Emerald", "Oz");
+
+ assertEquals("http://somewhere.over.the.rainbow", Util.getGuardProp(Util.PROP_GUARD_URL));
+ assertEquals("Dorothy", Util.getGuardProp(Util.PROP_GUARD_USER));
+ assertEquals("Toto", Util.getGuardProp(Util.PROP_GUARD_PASS));
+ assertEquals("Wizard", Util.getGuardProp(Util.PROP_GUARD_CLIENT_USER));
+ assertEquals("Emerald", Util.getGuardProp(Util.PROP_GUARD_CLIENT_PASS));
+ assertEquals("Oz", Util.getGuardProp(Util.PROP_GUARD_ENV));
+ }
+}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PIPEngineGetHistoryTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PIPEngineGetHistoryTest.java
index 566cc7a93..0c34d62b1 100644
--- a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PIPEngineGetHistoryTest.java
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PIPEngineGetHistoryTest.java
@@ -28,6 +28,13 @@ import static org.mockito.Mockito.when;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
+import java.net.URI;
+import java.net.URISyntaxException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+import java.util.Properties;
+import java.util.UUID;
import javax.persistence.EntityManager;
import javax.persistence.Persistence;
@@ -37,9 +44,24 @@ import org.junit.BeforeClass;
import org.junit.Test;
import org.onap.policy.drools.system.PolicyEngine;
+import com.att.research.xacml.api.Attribute;
+import com.att.research.xacml.api.AttributeValue;
+import com.att.research.xacml.api.Identifier;
+import com.att.research.xacml.api.Status;
+import com.att.research.xacml.api.pip.PIPEngine;
+import com.att.research.xacml.api.pip.PIPException;
+import com.att.research.xacml.api.pip.PIPFinder;
+import com.att.research.xacml.api.pip.PIPRequest;
+import com.att.research.xacml.api.pip.PIPResponse;
+import com.att.research.xacml.std.IdentifierImpl;
+import com.att.research.xacml.std.StdAttribute;
+import com.att.research.xacml.std.StdAttributeValue;
+import com.att.research.xacml.std.StdStatus;
+import com.att.research.xacml.std.StdStatusCode;
import com.att.research.xacml.std.pip.StdPIPRequest;
import com.att.research.xacml.std.pip.StdPIPResponse;
import com.att.research.xacml.std.pip.finders.EngineFinder;
+import com.att.research.xacml.util.FactoryException;
public class PIPEngineGetHistoryTest {
static PIPEngineGetHistory pegh;
@@ -73,8 +95,7 @@ public class PIPEngineGetHistoryTest {
// Test issuer null
when(mockPIPRequest.getIssuer()).thenReturn(null);
try {
- assertEquals(pegh.getAttributes(mockPIPRequest, mockPIPFinder),
- StdPIPResponse.PIP_RESPONSE_EMPTY);
+ assertEquals(StdPIPResponse.PIP_RESPONSE_EMPTY, pegh.getAttributes(mockPIPRequest, mockPIPFinder));
} catch (Exception e) {
fail("getAttributes failed");
}
@@ -83,8 +104,7 @@ public class PIPEngineGetHistoryTest {
pegh.setIssuer(ISSUER);
when(mockPIPRequest.getIssuer()).thenReturn("something else");
try {
- assertEquals(pegh.getAttributes(mockPIPRequest, mockPIPFinder),
- StdPIPResponse.PIP_RESPONSE_EMPTY);
+ assertEquals(StdPIPResponse.PIP_RESPONSE_EMPTY, pegh.getAttributes(mockPIPRequest, mockPIPFinder));
} catch (Exception e) {
fail("getAttributes failed");
}
@@ -165,4 +185,209 @@ public class PIPEngineGetHistoryTest {
assertEquals(1, count);
}
+ @Test
+ public void testConfigure() throws PIPException {
+ PIPEngineGetHistory pegh = new PIPEngineGetHistory();
+ pegh.configure("Dorothy", new Properties());
+
+ pegh.setDescription(null);
+ pegh.setIssuer(null);
+ pegh.configure("Dorothy", new Properties());
+ }
+
+ @Test
+ public void getAttributesTest() throws URISyntaxException, PIPException, FactoryException {
+ PIPEngineGetHistory pegh = new PIPEngineGetHistory();
+ pegh.setIssuer("Dorothy");
+
+ Identifier identifierCategory = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/category"));;
+ Identifier identifierAttribute = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/atrtribute"));;
+ Identifier identifierDataType = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/datatype"));;
+ PIPRequest pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:1000:SECOND");
+
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderPipException()));
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderResponseStatusNOK()));
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderResponseEmptyAttrs()));
+ }
+
+ @Test
+ public void timeWindowTest() throws URISyntaxException, PIPException, FactoryException {
+ PIPEngineGetHistory pegh = new PIPEngineGetHistory();
+ pegh.setIssuer("Dorothy");
+
+ Identifier identifierCategory = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/category"));;
+ Identifier identifierAttribute = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/atrtribute"));;
+ Identifier identifierDataType = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/datatype"));;
+
+ PIPRequest pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:SECOND");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:MINUTE");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:HOUR");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:DAY");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:WEEK");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:MONTH");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:QUARTER");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:YEAR");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:FORTNIGHT");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ pipRequest = new StdPIPRequest(identifierCategory , identifierAttribute, identifierDataType, "Dorothy,tw:100:FORT NIGHT");
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinder()));
+
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderPipException()));
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderResponseStatusNOK()));
+ assertNotNull(pegh.getAttributes(pipRequest, new DummyPipFinderResponseEmptyAttrs()));
+ }
+
+ private class DummyPipFinder implements PIPFinder {
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ try {
+ List<Attribute> attributeList = new ArrayList<>();
+ Identifier categoryIdIn = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/category"));
+ Identifier dataTypeIdIn = new IdentifierImpl(new URI("http://www.w3.org/2001/XMLSchema#string"));
+
+ Identifier attributeIdIn0 = new IdentifierImpl(new URI(UUID.randomUUID().toString()));
+ AttributeValue<String> valueIn0 = new StdAttributeValue<String>(dataTypeIdIn, "ActorDorothy");
+ Attribute attribute0 = new StdAttribute(categoryIdIn, attributeIdIn0, valueIn0);
+ attributeList.add(attribute0);
+
+ Identifier attributeIdIn1 = new IdentifierImpl(new URI(UUID.randomUUID().toString()));
+ AttributeValue<String> valueIn1 = new StdAttributeValue<String>(dataTypeIdIn, "OperationHomeFromOZ");
+ Attribute attribute1 = new StdAttribute(categoryIdIn, attributeIdIn1, valueIn1);
+ attributeList.add(attribute1);
+
+ Identifier attributeIdIn2 = new IdentifierImpl(new URI(UUID.randomUUID().toString()));
+ AttributeValue<String> valueIn2 = new StdAttributeValue<String>(dataTypeIdIn, "TargetWickedWitch");
+ Attribute attribute2 = new StdAttribute(categoryIdIn, attributeIdIn2, valueIn2);
+ attributeList.add(attribute2);
+
+ return new StdPIPResponse(attributeList);
+ }
+ catch (Exception e) {
+ return null;
+ }
+ }
+
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public Collection<PIPEngine> getPIPEngines() {
+ return null;
+ }
+ }
+
+ private class DummyPipFinderPipException implements PIPFinder {
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ throw new PIPException();
+ }
+
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public Collection<PIPEngine> getPIPEngines() {
+ return null;
+ }
+ }
+
+ private class DummyPipFinderResponseStatusNOK implements PIPFinder {
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ Status status = new StdStatus(StdStatusCode.STATUS_CODE_PROCESSING_ERROR, "Processing Error");
+ return new StdPIPResponse(status);
+ }
+
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public Collection<PIPEngine> getPIPEngines() {
+ return null;
+ }
+ }
+
+ private class DummyPipFinderResponseEmptyAttrs implements PIPFinder {
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude) throws PIPException {
+ List<Attribute> attributeList = new ArrayList<>();
+ return new StdPIPResponse(attributeList);
+ }
+
+ @Override
+ public PIPResponse getAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public PIPResponse getMatchingAttributes(PIPRequest pipRequest, PIPEngine exclude, PIPFinder pipFinderParent) throws PIPException {
+ return null;
+ }
+
+ @Override
+ public Collection<PIPEngine> getPIPEngines() {
+ return null;
+ }
+ }
}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardRequestTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardRequestTest.java
new file mode 100644
index 000000000..fa4acf7ec
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardRequestTest.java
@@ -0,0 +1,53 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import static org.junit.Assert.*;
+
+import java.util.UUID;
+
+import org.junit.Test;
+
+public class PolicyGuardRequestTest {
+
+ @Test
+ public void policyGuardRequestTest() {
+ UUID requestId = UUID.randomUUID();
+
+ assertNotNull(new PolicyGuardRequest(null, null, null, null));
+
+ PolicyGuardRequest request = new PolicyGuardRequest("Dorothy", "Kansas", requestId, "GetBackHome");
+
+ request.setRequestID(requestId);
+ assertEquals(requestId, request.getRequestID());
+
+ request.setActor("Dorothy");
+ assertEquals("Dorothy", request.getActor());
+
+ request.setTarget("Kansas");
+ assertEquals("Kansas", request.getTarget());
+
+ request.setOperation("GetBackHome");
+ assertEquals("GetBackHome", request.getOperation());
+
+ assertEquals("PolicyGuardRequest [actor=Dorothy", request.toString().substring(0, 33));
+ }
+}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardResponseTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardResponseTest.java
new file mode 100644
index 000000000..fe0155541
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardResponseTest.java
@@ -0,0 +1,50 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import static org.junit.Assert.*;
+
+import java.util.UUID;
+
+import org.junit.Test;
+
+public class PolicyGuardResponseTest {
+
+ @Test
+ public void policyGuardResponseTest() {
+ UUID requestId = UUID.randomUUID();
+
+ assertNotNull(new PolicyGuardResponse(null, null, null));
+
+ PolicyGuardResponse response = new PolicyGuardResponse("BackHome", requestId, "GetBackHome");
+
+ response.setRequestID(requestId);
+ assertEquals(requestId, response.getRequestID());
+
+ response.setResult("BackHome");
+ assertEquals("BackHome", response.getResult());
+
+ response.setOperation("GetBackHome");
+ assertEquals("GetBackHome", response.getOperation());
+
+ assertEquals("PolicyGuardResponse [requestID=", response.toString().substring(0, 31));
+ }
+}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardTest.java
index 17e115707..82656fa09 100644
--- a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardTest.java
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardTest.java
@@ -19,36 +19,42 @@
*/
package org.onap.policy.guard;
+import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import java.util.UUID;
import org.junit.Test;
import org.onap.policy.controlloop.policy.TargetType;
+import org.onap.policy.guard.PolicyGuard.LockResult;
+import org.onap.policy.guard.impl.PNFTargetLock;
+import org.onap.policy.guard.impl.VMTargetLock;
+import org.onap.policy.guard.impl.VNFTargetLock;
public class PolicyGuardTest {
- private class DummyLockCallback implements LockCallback{
+ private static final String INSTANCENAME = "targetInstance";
+
+ private class DummyLockCallback implements LockCallback {
@Override
public boolean isActive() {
- // TODO Auto-generated method stub
return false;
}
@Override
public boolean releaseLock() {
- // TODO Auto-generated method stub
return false;
}
}
- private class DummyTargetLock implements TargetLock{
+
+ private class DummyTargetLock implements TargetLock {
@Override
public UUID getLockID() {
- // TODO Auto-generated method stub
return null;
}
@Override
public TargetType getTargetType() {
- // TODO Auto-generated method stub
return null;
}
@Override
@@ -57,26 +63,173 @@ public class PolicyGuardTest {
}
@Override
public UUID getRequestID() {
- // TODO Auto-generated method stub
return null;
}
}
- private static final String INSTANCENAME = "targetInstance";
+ @Test
+ public void testLockVM() {
+ UUID uuid = UUID.randomUUID();
+ TargetType type = TargetType.VM;
+
+ // Test isLocked before and after lock added
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, result.getA());
+ assertEquals(VMTargetLock.class, result.getB().getClass());
+
+ VMTargetLock vtl = (VMTargetLock) result.getB();
+ assertNotNull(vtl.getLockID());
+ assertEquals(INSTANCENAME, vtl.getTargetInstance());
+ assertEquals(TargetType.VM, vtl.getTargetType());
+ assertNotNull(vtl.getRequestID());
+ assertEquals(dlcb, vtl.getCallback());
+
+ // Test isLocked after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ }
+
+ @Test
+ public void testLockPNF() {
+ UUID uuid = UUID.randomUUID();
+ TargetType type = TargetType.PNF;
+
+ // Test isLocked before and after lock added
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, result.getA());
+ assertEquals(PNFTargetLock.class, result.getB().getClass());
+
+ PNFTargetLock ptl = (PNFTargetLock) result.getB();
+ assertNotNull(ptl.getLockID());
+ assertEquals(INSTANCENAME, ptl.getTargetInstance());
+ assertEquals(TargetType.PNF, ptl.getTargetType());
+ assertNotNull(ptl.getRequestID());
+ assertEquals(dlcb, ptl.getCallback());
+
+ // Test isLocked after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ }
+
+
+ @Test
+ public void testLockVNF() {
+ UUID uuid = UUID.randomUUID();
+ TargetType type = TargetType.VNF;
+
+ // Test isLocked before and after lock added
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, result.getA());
+ assertEquals(VNFTargetLock.class, result.getB().getClass());
+
+ VNFTargetLock vtl = (VNFTargetLock) result.getB();
+ assertNotNull(vtl.getLockID());
+ assertEquals(INSTANCENAME, vtl.getTargetInstance());
+ assertEquals(TargetType.VNF, vtl.getTargetType());
+ assertNotNull(vtl.getRequestID());
+ assertEquals(dlcb, vtl.getCallback());
+
+ // Test isLocked after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ }
@Test
- public void testAll() {
+ public void testLockVFC() {
+ UUID uuid = UUID.randomUUID();
+ TargetType type = TargetType.VFC;
+
+ // Test isLocked before and after lock added
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_EXCEPTION, result.getA());
+ assertNull(result.getB());
+
+ // Test isLocked after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ }
+
+ @Test
+ public void testUnLockNotLocked() {
UUID uuid = UUID.randomUUID();
TargetType type = TargetType.VM;
+ // Test isLocked before and after lock added
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, result.getA());
+ assertEquals(VMTargetLock.class, result.getB().getClass());
+
+ result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_DENIED, result.getA());
+ assertNull(result.getB());
+
+ // Test isLocked after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ // Test unlock after lock removed
+ PolicyGuard.unlockTarget(new DummyTargetLock());
+ assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+ }
+
+ @Test
+ public void testLockAlreadyLocked() {
+ UUID uuid = UUID.randomUUID();
+ TargetType type = TargetType.VM;
// Test isLocked before and after lock added
assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
- PolicyGuard.lockTarget(type, INSTANCENAME, uuid , new DummyLockCallback());
+ DummyLockCallback dlcb = new DummyLockCallback();
+ LockResult<GuardResult, TargetLock> result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_ACQUIRED, result.getA());
+ assertEquals(VMTargetLock.class, result.getB().getClass());
+
+ result = PolicyGuard.lockTarget(type, INSTANCENAME, uuid , dlcb);
+ assertTrue(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
+
+ assertEquals(GuardResult.LOCK_DENIED, result.getA());
+ assertNull(result.getB());
// Test isLocked after lock removed
PolicyGuard.unlockTarget(new DummyTargetLock());
assertFalse(PolicyGuard.isLocked(type, INSTANCENAME, uuid));
}
+
+ @Test
+ public void testInnards() {
+
+ DummyLockCallback dlcb = new DummyLockCallback();
+ assertFalse(dlcb.isActive());
+ assertFalse(dlcb.releaseLock());
+
+ DummyTargetLock dtl = new DummyTargetLock();
+ assertNull(dtl.getLockID());
+ assertNull(dtl.getRequestID());
+ assertEquals(INSTANCENAME, dtl.getTargetInstance());
+ assertNull(dtl.getTargetType());
+ }
}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlHelperTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlHelperTest.java
index 1d3ab02e4..10c6d7239 100644
--- a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlHelperTest.java
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlHelperTest.java
@@ -19,17 +19,43 @@
*/
package org.onap.policy.guard;
+import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
+import java.net.URI;
+import java.net.URISyntaxException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Properties;
+import java.util.UUID;
+
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.onap.policy.drools.http.server.HttpServletServer;
+import org.onap.policy.drools.system.PolicyEngine;
import org.onap.policy.drools.utils.LoggerUtil;
-
+import com.att.research.xacml.api.Advice;
+import com.att.research.xacml.api.Attribute;
+import com.att.research.xacml.api.AttributeCategory;
+import com.att.research.xacml.api.AttributeValue;
+import com.att.research.xacml.api.Decision;
+import com.att.research.xacml.api.IdReference;
+import com.att.research.xacml.api.Identifier;
+import com.att.research.xacml.api.Obligation;
+import com.att.research.xacml.api.Response;
+import com.att.research.xacml.api.Result;
+import com.att.research.xacml.api.Status;
+import com.att.research.xacml.std.IdentifierImpl;
+import com.att.research.xacml.std.StdAttribute;
+import com.att.research.xacml.std.StdAttributeCategory;
+import com.att.research.xacml.std.StdAttributeValue;
+import com.att.research.xacml.std.StdResponse;
+import com.att.research.xacml.std.StdResult;
+import com.att.research.xacml.std.StdStatus;
public class PolicyGuardXacmlHelperTest {
@@ -65,7 +91,7 @@ public class PolicyGuardXacmlHelperTest {
org.onap.policy.simulators.GuardSimulatorJaxRs.DENY_CLNAME, "actor", "recipe", "target", "requestId");
String rawDecision = new PolicyGuardXacmlHelper().callPDP(xacmlReq);
assertNotNull(rawDecision);
- assertTrue(0 == Util.INDETERMINATE.compareToIgnoreCase(rawDecision));
+ assertEquals(0, Util.INDETERMINATE.compareToIgnoreCase(rawDecision));
}
@Test
@@ -93,9 +119,131 @@ public class PolicyGuardXacmlHelperTest {
"clname", "actor", "recipe", "target", "requestId");
rawDecision = new PolicyGuardXacmlHelper().callPDP(xacmlReq);
assertNotNull(rawDecision);
- assertTrue(0 == Util.PERMIT.compareToIgnoreCase(rawDecision));
+ assertEquals(0, Util.PERMIT.compareToIgnoreCase(rawDecision));
// Indeterminate case is in tearDown for efficiency
}
+
+ @Test
+ /**
+ * Tests PolicyGuardXacmlHelper.callPDP method to exercise all branches
+ */
+ public void testCallPDPExtra() {
+ PolicyGuardXacmlRequestAttributes xacmlReq = new PolicyGuardXacmlRequestAttributes(
+ org.onap.policy.simulators.GuardSimulatorJaxRs.DENY_CLNAME, "actor", "recipe", "target", "requestId");
+
+ xacmlReq.setClnameID(null);
+ String rawDecision = new PolicyGuardXacmlHelper().callPDP(xacmlReq);
+ assertNotNull(rawDecision);
+ assertEquals(-5, Util.DENY.compareToIgnoreCase(rawDecision));
+
+ org.onap.policy.guard.Util.setGuardEnvProps("http://localhost:6669/pdp/api/getDecision",
+ "",
+ "",
+ "",
+ "",
+ "");
+
+ rawDecision = new PolicyGuardXacmlHelper().callPDP(xacmlReq);
+ assertNotNull(rawDecision);
+
+ org.onap.policy.guard.Util.setGuardEnvProps("http://localhost:6669/pdp/api/getDecision",
+ "python",
+ "test",
+ "python",
+ "test",
+ "DEVL");
+
+ }
+
+ @Test
+ public void testParseXACMLPDPResponse() throws URISyntaxException {
+ PolicyGuardResponse pgResponse = PolicyGuardXacmlHelper.parseXACMLPDPResponse(null);
+ assertEquals("Indeterminate", pgResponse.getResult());
+ Decision decision = Decision.PERMIT;
+ Status status = new StdStatus(StdStatus.STATUS_OK);
+ Result result = new StdResult(decision, status);
+ Response xacmlResponse = new StdResponse(result);
+ pgResponse = PolicyGuardXacmlHelper.parseXACMLPDPResponse(xacmlResponse);
+ assertEquals("Permit", pgResponse.getResult());
+
+
+ Collection<Obligation> obligationsIn = null;
+ Collection<Advice> adviceIn = null;
+ Collection<IdReference> policyIdentifiersIn = null;
+ Collection<IdReference> policySetIdentifiersIn = null;
+
+ Collection<AttributeCategory> attributesIn = new ArrayList<>();
+ Identifier identifierCategory = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow"));
+ Collection<Attribute> listAttributes = new ArrayList<>();
+ Identifier categoryIdIn = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow/category"));
+ Identifier attributeIdIn0 = new IdentifierImpl(new URI("urn:oasis:names:tc:xacml:1.0:request:request-id"));
+ Identifier dataTypeIdIn = new IdentifierImpl(new URI("http://somewhere.over.the.rainbow.dataType"));
+ AttributeValue<String> valueIn = new StdAttributeValue<String>(dataTypeIdIn, UUID.randomUUID().toString());
+ Attribute attribute0 = new StdAttribute(categoryIdIn, attributeIdIn0, valueIn);
+ listAttributes.add(attribute0);
+
+ Identifier attributeIdIn1 = new IdentifierImpl(new URI("urn:oasis:names:tc:xacml:1.0:operation:operation-id"));
+ Attribute attribute1 = new StdAttribute(categoryIdIn, attributeIdIn1, valueIn);
+ listAttributes.add(attribute1);
+ attributesIn.add(new StdAttributeCategory(identifierCategory , listAttributes));
+
+ Identifier attributeIdIn2 = new IdentifierImpl(new URI("Http://somewhere.over.the.rainbow/attributeId"));
+ Attribute attribute2 = new StdAttribute(categoryIdIn, attributeIdIn2, valueIn);
+ listAttributes.add(attribute2);
+ attributesIn.add(new StdAttributeCategory(identifierCategory , listAttributes));
+
+ Result fullResult = new StdResult(Decision.DENY, obligationsIn, adviceIn, attributesIn, policyIdentifiersIn, policySetIdentifiersIn);
+ Response fullXacmlResponse = new StdResponse(fullResult);
+ PolicyGuardResponse fullPGResponse = PolicyGuardXacmlHelper.parseXACMLPDPResponse(fullXacmlResponse);
+ assertEquals("Deny", fullPGResponse.getResult());
+ }
+
+ @Test
+ public void testInit() {
+ Properties savedEnvironment = (Properties) PolicyEngine.manager.getEnvironment().clone();
+
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.url", "http://localhost:6669/pdp/api/getDecision,Dorothy");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.url", "http://localhost:6669/pdp/api/getDecision,Dorothy,Toto");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.url", "http://localhost:6669/pdp/api/getDecision");
+
+ PolicyEngine.manager.getEnvironment().setProperty("pdpx.timeout", "thisIsNotANumber");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("pdpx.timeout", "1000");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().remove("pdpx.password");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("pdpx.username", "python");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().remove("pdpx.client.password");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().remove("pdpx.client.username");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.url", "///");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.disabled", "");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().setProperty("guard.disabled", "true");
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.getEnvironment().clear();
+ assertNotNull(new PolicyGuardXacmlHelper());
+
+ PolicyEngine.manager.setEnvironment(savedEnvironment);
+ }
}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlRequestAttributesTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlRequestAttributesTest.java
new file mode 100644
index 000000000..d07a97a67
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardXacmlRequestAttributesTest.java
@@ -0,0 +1,64 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import static org.junit.Assert.*;
+
+import java.util.UUID;
+
+import org.junit.Test;
+
+public class PolicyGuardXacmlRequestAttributesTest {
+
+ @Test
+ public void policyGuardXacmlRequestAttributesTest() {
+ assertNotNull(new PolicyGuardXacmlRequestAttributes(null, null, null, null, null));
+
+ UUID controlLoopID = UUID.randomUUID();
+ UUID operationID = UUID.randomUUID();
+ UUID requestID = UUID.randomUUID();
+ UUID actorID = UUID.randomUUID();
+ UUID targetID = UUID.randomUUID();
+
+ PolicyGuardXacmlRequestAttributes attributes = new PolicyGuardXacmlRequestAttributes(
+ controlLoopID.toString(), actorID.toString(), operationID.toString(), targetID.toString(), requestID.toString());
+
+ attributes.setRequestID(requestID.toString());
+ assertEquals(requestID.toString(), attributes.getRequestID());
+
+ attributes.setOperationID(operationID.toString());
+ assertEquals(operationID.toString(), attributes.getOperationID());
+
+ attributes.setActorID(actorID.toString());
+ assertEquals(actorID.toString(), attributes.getActorID());
+
+ attributes.setTargetID(targetID.toString());
+ assertEquals(targetID.toString(), attributes.getTargetID());
+
+ attributes.setTargetID(targetID.toString());
+ assertEquals(targetID.toString(), attributes.getTargetID());
+
+ attributes.setClnameID(controlLoopID.toString());
+ assertEquals(controlLoopID.toString(), attributes.getClnameID());
+
+ assertEquals("PolicyGuardXacmlRequestAttributes [actorID=", attributes.toString().substring(0, 43));
+ }
+}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardYamlToXacmlTest.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardYamlToXacmlTest.java
index 1e972c30f..b35356438 100644
--- a/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardYamlToXacmlTest.java
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/PolicyGuardYamlToXacmlTest.java
@@ -22,48 +22,126 @@ package org.onap.policy.guard;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
+import java.io.File;
+import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
+import java.util.LinkedList;
import java.util.List;
import java.util.Map;
+import org.junit.Before;
import org.junit.Test;
+import org.onap.policy.controlloop.policy.guard.Constraint;
+import org.onap.policy.controlloop.policy.guard.ControlLoopGuard;
+import org.onap.policy.controlloop.policy.guard.GuardPolicy;
+import org.onap.policy.controlloop.policy.guard.MatchParameters;
+import org.yaml.snakeyaml.Yaml;
+import org.yaml.snakeyaml.constructor.Constructor;
public class PolicyGuardYamlToXacmlTest {
-
- @Test
- public void testFromYamlToXacml() {
- //PolicyGuardYamlToXacml.fromYamlToXacml(yamlFile, xacmlTemplate, xacmlPolicyOutput);
- //fail("Not yet implemented");
+ private ControlLoopGuard clGuard;
+
+ @Before
+ public void createControlLoopGuard() {
+ clGuard = new ControlLoopGuard();
+ GuardPolicy guardPolicy = new GuardPolicy();
+ MatchParameters matchParameters = new MatchParameters();
+ matchParameters.setControlLoopName("WizardOfOz");
+ matchParameters.setActor("Dorothy");
+ matchParameters.setRecipe("GoToOz");
+ List<String> targets = new ArrayList<>();
+ targets.add("Wizard");
+ targets.add("WickedWitchOfTheWest");
+ matchParameters.setTargets(targets );
+ guardPolicy.setMatch_parameters(matchParameters );
+ Constraint limitConstraint = new Constraint();
+ limitConstraint.setFreq_limit_per_target(5);
+ Map<String, String> timeWindow = new HashMap<>();
+ timeWindow.put("value", "10");
+ timeWindow.put("units", "hours");
+ limitConstraint.setTime_window(timeWindow);
+ Map<String, String> activeTimeRange = new HashMap<>();
+ activeTimeRange.put("start", "someStartTime");
+ activeTimeRange.put("end", "someEndTime");
+ limitConstraint.setActive_time_range(activeTimeRange );
+ LinkedList<Constraint> limitConstraints = new LinkedList<>();
+ limitConstraints.add(limitConstraint);
+ guardPolicy.setLimit_constraints(limitConstraints);
+ LinkedList<GuardPolicy> guardList = new LinkedList<>();
+ guardList.add(guardPolicy);
+ clGuard.setGuards(guardList);
}
-
+
@Test
- public void testGenerateXacmlGuard() {
- String dummyFileContent = "${clname}, ${actor}, ${recipe}, ${targets}, ${limit}, ${twValue}, ${twUnits}, ${guardActiveStart}, ${guardActiveEnd}";
- List<String> targets = new ArrayList();
- targets.add("target1");
- targets.add("target2");
- Map<String, String> tw = new HashMap();
- tw.put("value", "10");
- tw.put("units", "hours");
- String res = PolicyGuardYamlToXacml.generateXacmlGuard(dummyFileContent,
- "cl", "actor", "recipe", targets, 5, tw, "start", "end");
+ public void testGenerateXacmlGuardFull() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+ File tempXACMLTemplateFile = new File("src/test/resources/frequency_limiter_template.xml");
+ File tempXACMLOutputFile = File.createTempFile("ONAPPF", ".out.xacml");
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopGuard.class));
+ String clYamlString = clYaml.dump(clGuard);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+ PolicyGuardYamlToXacml.fromYamlToXacml(tempYAMLFile.getCanonicalPath(), tempXACMLTemplateFile.getCanonicalPath(), tempXACMLOutputFile.getCanonicalPath());
+
+ String result = TextFileUtils.getTextFileAsString(tempXACMLOutputFile.getCanonicalPath());
// Assert no mote "${}" are left
- assertFalse(res.contains("${"));
- assertFalse(res.contains("}"));
+ assertFalse(result.contains("${"));
+ assertFalse(result.contains("}"));
// Assert all substitutions are made
- assertTrue(res.contains("cl"));
- assertTrue(res.contains("actor"));
- assertTrue(res.contains("recipe"));
- assertTrue(res.contains("target1"));
- assertTrue(res.contains("target2"));
- assertTrue(res.contains("10"));
- assertTrue(res.contains("hours"));
- assertTrue(res.contains("start"));
- assertTrue(res.contains("end"));
+ assertTrue(result.contains("cl"));
+ assertTrue(result.contains("actor"));
+ assertTrue(result.contains("GoToOz"));
+ assertTrue(result.contains("Wizard"));
+ assertTrue(result.contains("WickedWitchOfTheWest"));
+ assertTrue(result.contains("10"));
+ assertTrue(result.contains("hours"));
+ assertTrue(result.contains("someStartTime"));
+ assertTrue(result.contains("someEndTime"));
+
+ tempYAMLFile.delete();
+ tempXACMLOutputFile.delete();
}
+
+ @Test
+ public void testGenerateXacmlGuardPartial() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+ File tempXACMLTemplateFile = new File("src/test/resources/frequency_limiter_template.xml");
+ File tempXACMLOutputFile = File.createTempFile("ONAPPF", ".out.xacml");
+
+ clGuard.getGuards().getFirst().getMatch_parameters().setControlLoopName(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setActor(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setRecipe(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setTargets(null);
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopGuard.class));
+ String clYamlString = clYaml.dump(clGuard);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+ PolicyGuardYamlToXacml.fromYamlToXacml(tempYAMLFile.getCanonicalPath(), tempXACMLTemplateFile.getCanonicalPath(), tempXACMLOutputFile.getCanonicalPath());
+
+ String result = TextFileUtils.getTextFileAsString(tempXACMLOutputFile.getCanonicalPath());
+ // Assert no mote "${}" are left
+ assertFalse(result.contains("${"));
+ assertFalse(result.contains("}"));
+ // Assert all substitutions are made
+ assertTrue(result.contains("cl"));
+ assertTrue(result.contains("actor"));
+ assertFalse(result.contains("GoToOz"));
+ assertFalse(result.contains("Wizard"));
+ assertFalse(result.contains("WickedWitchOfTheWest"));
+ assertTrue(result.contains("10"));
+ assertTrue(result.contains("hours"));
+ assertTrue(result.contains("someStartTime"));
+ assertTrue(result.contains("someEndTime"));
+
+ tempYAMLFile.delete();
+ tempXACMLOutputFile.delete();
+ }
+
@Test
public void testIsNullOrEmpty() {
assertTrue(PolicyGuardYamlToXacml.isNullOrEmpty(""));
@@ -73,7 +151,7 @@ public class PolicyGuardYamlToXacmlTest {
@Test
public void testIsNullOrEmptyList() {
- List<String> l = new ArrayList();
+ List<String> l = new ArrayList<>();
assertTrue(PolicyGuardYamlToXacml.isNullOrEmptyList(null));
assertTrue(PolicyGuardYamlToXacml.isNullOrEmptyList(l));
@@ -87,25 +165,67 @@ public class PolicyGuardYamlToXacmlTest {
}
@Test
- public void testGenerateXacmlGuardBlacklist() {
- String dummyFileContent = "${clname}, ${actor}, ${recipe}, ${blackListElement}, ${guardActiveStart}, ${guardActiveEnd}";
- List<String> blacklist = new ArrayList();
- blacklist.add("target1");
- blacklist.add("target2");
- String res = PolicyGuardYamlToXacml.generateXacmlGuardBlacklist(dummyFileContent,
- "cl", "actor", "recipe", blacklist, "start", "end");
+ public void testGenerateXacmlGuardBlacklist() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+ File tempXACMLTemplateFile = new File("src/test/resources/blacklist_template.xml");
+ File tempXACMLOutputFile = File.createTempFile("ONAPPF", ".out.xacml");
+
+ List<String> blacklist = new ArrayList<>();
+ blacklist.add("WestWitches");
+ blacklist.add("EastWitches");
+ clGuard.getGuards().getFirst().getLimit_constraints().getFirst().setBlacklist(blacklist );
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopGuard.class));
+ String clYamlString = clYaml.dump(clGuard);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+ PolicyGuardYamlToXacml.fromYamlToXacmlBlacklist(tempYAMLFile.getCanonicalPath(), tempXACMLTemplateFile.getCanonicalPath(), tempXACMLOutputFile.getCanonicalPath());
+ String result = TextFileUtils.getTextFileAsString(tempXACMLOutputFile.getCanonicalPath());
+ System.err.println(result);
// Assert no mote "${}" are left
- assertFalse(res.contains("${"));
- assertFalse(res.contains("}"));
+ assertFalse(result.contains("${"));
+ assertFalse(result.contains("}"));
// Assert all substitutions are made
- assertTrue(res.contains("cl"));
- assertTrue(res.contains("actor"));
- assertTrue(res.contains("recipe"));
- assertTrue(res.contains("target1"));
- assertTrue(res.contains("target2"));
- assertTrue(res.contains("start"));
- assertTrue(res.contains("end"));
+ assertTrue(result.contains("WestWitches"));
+ assertTrue(result.contains("EastWitches"));
+
+ tempYAMLFile.delete();
+ tempXACMLOutputFile.delete();
}
+ @Test
+ public void testGenerateXacmlGuardBlacklistPartial() throws IOException {
+ File tempYAMLFile = File.createTempFile("ONAPPF", "yaml");
+ File tempXACMLTemplateFile = new File("src/test/resources/blacklist_template.xml");
+ File tempXACMLOutputFile = File.createTempFile("ONAPPF", ".out.xacml");
+
+ List<String> blacklist = new ArrayList<>();
+ blacklist.add("WestWitches");
+ blacklist.add("EastWitches");
+ clGuard.getGuards().getFirst().getLimit_constraints().getFirst().setBlacklist(blacklist );
+
+ clGuard.getGuards().getFirst().getMatch_parameters().setControlLoopName(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setActor(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setRecipe(null);
+ clGuard.getGuards().getFirst().getMatch_parameters().setTargets(null);
+
+ Yaml clYaml = new Yaml(new Constructor(ControlLoopGuard.class));
+ String clYamlString = clYaml.dump(clGuard);
+
+ TextFileUtils.putStringAsFile(clYamlString, tempYAMLFile);
+ PolicyGuardYamlToXacml.fromYamlToXacmlBlacklist(tempYAMLFile.getCanonicalPath(), tempXACMLTemplateFile.getCanonicalPath(), tempXACMLOutputFile.getCanonicalPath());
+
+ String result = TextFileUtils.getTextFileAsString(tempXACMLOutputFile.getCanonicalPath());
+ System.err.println(result);
+ // Assert no mote "${}" are left
+ assertFalse(result.contains("${"));
+ assertFalse(result.contains("}"));
+ // Assert all substitutions are made
+ assertTrue(result.contains("WestWitches"));
+ assertTrue(result.contains("EastWitches"));
+
+ tempYAMLFile.delete();
+ tempXACMLOutputFile.delete();
+ }
}
diff --git a/controlloop/common/guard/src/test/java/org/onap/policy/guard/TextFileUtils.java b/controlloop/common/guard/src/test/java/org/onap/policy/guard/TextFileUtils.java
new file mode 100644
index 000000000..21b75ed20
--- /dev/null
+++ b/controlloop/common/guard/src/test/java/org/onap/policy/guard/TextFileUtils.java
@@ -0,0 +1,63 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * guard
+ * ================================================================================
+ * Copyright (C) 2018 Ericsson. 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.
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.guard;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
+/**
+ * The Class TextFileUtils is class that provides useful functions for handling text files. Functions to read and wrtie text files to strings and strings are
+ * provided.
+ *
+ * @author Liam Fallon (liam.fallon@ericsson.com)
+ */
+public abstract class TextFileUtils {
+ /**
+ * Method to return the contents of a text file as a string.
+ *
+ * @param textFilePath The path to the file as a string
+ * @return A string containing the contents of the file
+ * @throws IOException on errors reading text from the file
+ */
+ public static String getTextFileAsString(final String textFilePath) throws IOException {
+ final File textFile = new File(textFilePath);
+ final FileInputStream textFileInputStream = new FileInputStream(textFile);
+ final byte[] textData = new byte[(int) textFile.length()];
+ textFileInputStream.read(textData);
+ textFileInputStream.close();
+ return new String(textData);
+ }
+
+ /**
+ * Method to write contents of a string to a text file.
+ *
+ * @param outString The string to write
+ * @param textFile The file to write the string to
+ * @throws IOException on errors reading text from the file
+ */
+ public static void putStringAsFile(final String outString, final File textFile) throws IOException {
+ final FileOutputStream textFileOutputStream = new FileOutputStream(textFile);
+ textFileOutputStream.write(outString.getBytes());
+ textFileOutputStream.close();
+ }
+}
diff --git a/controlloop/common/guard/src/test/resources/blacklist_template.xml b/controlloop/common/guard/src/test/resources/blacklist_template.xml
new file mode 100644
index 000000000..5d31730db
--- /dev/null
+++ b/controlloop/common/guard/src/test/resources/blacklist_template.xml
@@ -0,0 +1,55 @@
+<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
+<Policy xmlns="urn:oasis:names:tc:xacml:3.0:core:schema:wd-17" PolicyId="urn:com:att:xacml:policy:id:25e12b06-11d5-4895-b2a2-6f6c594de069" Version="1" RuleCombiningAlgId="urn:oasis:names:tc:xacml:3.0:rule-combining-algorithm:permit-unless-deny">
+ <Description>Policy for frequency limiter.</Description>
+ <Target>
+ <AnyOf>
+ <AllOf>
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <!-- <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">.*</AttributeValue>-->
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${clname}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:1.0:subject-category:access-subject" AttributeId="urn:oasis:names:tc:xacml:1.0:clname:clname-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+
+ <!-- <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-equal">-->
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${actor}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:1.0:subject-category:access-subject" AttributeId="urn:oasis:names:tc:xacml:1.0:actor:actor-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${recipe}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:3.0:attribute-category:action" AttributeId="urn:oasis:names:tc:xacml:1.0:operation:operation-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+ </AllOf>
+ </AnyOf>
+ </Target>
+ <Rule RuleId="urn:com:att:xacml:rule:id:e1e8c5c0-e2ba-47d5-9289-6c015305ed21" Effect="Deny">
+ <Description>DENY - only if target is in black list and guard is active.</Description>
+ <Condition>
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:and">
+ <VariableReference VariableId="isGuardActive"/>
+ <VariableReference VariableId="isInBlackList"/>
+ </Apply>
+ </Condition>
+ </Rule>
+ <VariableDefinition VariableId="isInBlackList">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:3.0:function:any-of">
+ <Function FunctionId="urn:oasis:names:tc:xacml:1.0:function:string-equal"/>
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:string-one-and-only">
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:3.0:attribute-category:resource" AttributeId="urn:oasis:names:tc:xacml:1.0:target:target-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Apply>
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:string-bag">
+ ${blackListElement}
+ <!-- <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">vserver.vserver-name</AttributeValue>-->
+ </Apply>
+ </Apply>
+ </VariableDefinition>
+ <VariableDefinition VariableId="isGuardActive">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:2.0:function:time-in-range">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:time-one-and-only">
+ <AttributeDesignator AttributeId="urn:oasis:names:tc:xacml:1.0:environment:current-time" DataType="http://www.w3.org/2001/XMLSchema#time" Category="urn:oasis:names:tc:xacml:3.0:attribute-category:environment" MustBePresent="false"/>
+ </Apply>
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#time">${guardActiveStart}</AttributeValue>
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#time">${guardActiveEnd}</AttributeValue>
+ </Apply>
+ </VariableDefinition>
+</Policy>
diff --git a/controlloop/common/guard/src/test/resources/frequency_limiter_template.xml b/controlloop/common/guard/src/test/resources/frequency_limiter_template.xml
new file mode 100644
index 000000000..2d73a1e6d
--- /dev/null
+++ b/controlloop/common/guard/src/test/resources/frequency_limiter_template.xml
@@ -0,0 +1,58 @@
+<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
+<Policy xmlns="urn:oasis:names:tc:xacml:3.0:core:schema:wd-17" PolicyId="urn:com:att:xacml:policy:id:25e12b06-11d5-4895-b2a2-6f6c594de069" Version="1" RuleCombiningAlgId="urn:oasis:names:tc:xacml:3.0:rule-combining-algorithm:permit-unless-deny">
+ <Description>Policy for frequency limiter.</Description>
+ <Target>
+ <AnyOf>
+ <AllOf>
+
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <!-- <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">.*</AttributeValue>-->
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${clname}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:1.0:subject-category:access-subject" AttributeId="urn:oasis:names:tc:xacml:1.0:clname:clname-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+
+ <!-- <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-equal">-->
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${actor}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:1.0:subject-category:access-subject" AttributeId="urn:oasis:names:tc:xacml:1.0:actor:actor-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${recipe}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:3.0:attribute-category:action" AttributeId="urn:oasis:names:tc:xacml:1.0:operation:operation-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+
+ <Match MatchId="urn:oasis:names:tc:xacml:1.0:function:string-regexp-match">
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#string">${targets}</AttributeValue>
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:3.0:attribute-category:resource" AttributeId="urn:oasis:names:tc:xacml:1.0:target:target-id" DataType="http://www.w3.org/2001/XMLSchema#string" MustBePresent="false"/>
+ </Match>
+
+ </AllOf>
+ </AnyOf>
+ </Target>
+ <Rule RuleId="urn:com:att:xacml:rule:id:e1e8c5c0-e2ba-47d5-9289-6c015305ed21" Effect="Deny">
+ <Description>DENY - only if number of operations performed in the past is larger than the limit and the Guard is active.</Description>
+ <Condition>
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:and">
+ <VariableReference VariableId="isGuardActive"/>
+ <VariableReference VariableId="isHistoryGreaterThanLimit"/>
+ </Apply>
+ </Condition>
+ </Rule>
+ <VariableDefinition VariableId="isGuardActive">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:2.0:function:time-in-range">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:time-one-and-only">
+ <AttributeDesignator AttributeId="urn:oasis:names:tc:xacml:1.0:environment:current-time" DataType="http://www.w3.org/2001/XMLSchema#time" Category="urn:oasis:names:tc:xacml:3.0:attribute-category:environment" MustBePresent="false"/>
+ </Apply>
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#time">${guardActiveStart}</AttributeValue>
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#time">${guardActiveEnd}</AttributeValue>
+ </Apply>
+ </VariableDefinition>
+ <VariableDefinition VariableId="isHistoryGreaterThanLimit">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:integer-greater-than-or-equal">
+ <Apply FunctionId="urn:oasis:names:tc:xacml:1.0:function:integer-one-and-only">
+ <AttributeDesignator Category="urn:oasis:names:tc:xacml:3.0:attribute-category:resource" AttributeId="com:att:research:xacml:test:sql:resource:operations:count" DataType="http://www.w3.org/2001/XMLSchema#integer" Issuer="com:att:research:xacml:guard:historydb:tw:${twValue}:${twUnits}" MustBePresent="false"/>
+ </Apply>
+ <AttributeValue DataType="http://www.w3.org/2001/XMLSchema#integer">${limit}</AttributeValue>
+ </Apply>
+ </VariableDefinition>
+</Policy>