RANGER-2653: Refactor product code to move out APIs used only by test code
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/contextenricher/RangerTagEnricher.java b/agents-common/src/main/java/org/apache/ranger/plugin/contextenricher/RangerTagEnricher.java
index 75b0bf4..95a0bed 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/contextenricher/RangerTagEnricher.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/contextenricher/RangerTagEnricher.java
@@ -34,6 +34,7 @@
 import org.apache.ranger.plugin.policyengine.RangerAccessRequest;
 import org.apache.ranger.plugin.policyengine.RangerAccessResource;
 import org.apache.ranger.plugin.policyengine.RangerAccessResourceImpl;
+import org.apache.ranger.plugin.policyengine.RangerResourceTrie;
 import org.apache.ranger.plugin.policyresourcematcher.RangerDefaultPolicyResourceMatcher;
 import org.apache.ranger.plugin.policyresourcematcher.RangerPolicyResourceMatcher;
 import org.apache.ranger.plugin.util.DownloadTrigger;
@@ -42,7 +43,6 @@
 import org.apache.ranger.plugin.service.RangerBasePlugin;
 import org.apache.ranger.plugin.util.RangerAccessRequestUtil;
 import org.apache.ranger.plugin.util.RangerPerfTracer;
-import org.apache.ranger.plugin.util.RangerResourceTrie;
 import org.apache.ranger.plugin.util.RangerServiceNotFoundException;
 import org.apache.ranger.plugin.util.RangerServiceTagsDeltaUtil;
 import org.apache.ranger.plugin.util.ServiceTags;
@@ -344,55 +344,8 @@
 		token.waitForCompletion();
 	}
 
-	public boolean compare(RangerTagEnricher other) {
-		boolean ret;
-
-		if (enrichedServiceTags == null || other == null || other.enrichedServiceTags == null) {
-			return false;
-		}
-
-		if (enrichedServiceTags.getServiceResourceTrie() != null && other.enrichedServiceTags.getServiceResourceTrie() != null) {
-			ret = enrichedServiceTags.getServiceResourceTrie().size() == other.enrichedServiceTags.getServiceResourceTrie().size();
-
-			if (ret && enrichedServiceTags.getServiceResourceTrie().size() > 0) {
-				for (Map.Entry<String, RangerResourceTrie<RangerServiceResourceMatcher>> entry : enrichedServiceTags.getServiceResourceTrie().entrySet()) {
-					ret = entry.getValue().compareSubtree(other.enrichedServiceTags.getServiceResourceTrie().get(entry.getKey()));
-					if (!ret) {
-						break;
-					}
-				}
-			}
-		} else {
-			ret = enrichedServiceTags.getServiceResourceTrie() == other.enrichedServiceTags.getServiceResourceTrie();
-		}
-
-		if (ret) {
-			// Compare mappings
-			ServiceTags myServiceTags = enrichedServiceTags.getServiceTags();
-			ServiceTags otherServiceTags = other.enrichedServiceTags.getServiceTags();
-
-			ret = StringUtils.equals(myServiceTags.getServiceName(), otherServiceTags.getServiceName()) &&
-					//myServiceTags.getTagVersion().equals(otherServiceTags.getTagVersion()) &&
-					myServiceTags.getTags().size() == otherServiceTags.getTags().size() &&
-					myServiceTags.getServiceResources().size() == otherServiceTags.getServiceResources().size() &&
-					myServiceTags.getResourceToTagIds().size() == otherServiceTags.getResourceToTagIds().size();
-			if (ret) {
-				for (RangerServiceResource serviceResource : myServiceTags.getServiceResources()) {
-					Long serviceResourceId = serviceResource.getId();
-
-					List<Long> myTagsForResource = myServiceTags.getResourceToTagIds().get(serviceResourceId);
-					List<Long> otherTagsForResource = otherServiceTags.getResourceToTagIds().get(serviceResourceId);
-
-					ret = CollectionUtils.size(myTagsForResource) == CollectionUtils.size(otherTagsForResource);
-
-					if (ret && CollectionUtils.size(myTagsForResource) > 0) {
-						ret = myTagsForResource.size() == CollectionUtils.intersection(myTagsForResource, otherTagsForResource).size();
-					}
-				}
-			}
-		}
-
-		return ret;
+	public EnrichedServiceTags getEnrichedServiceTags() {
+		return enrichedServiceTags;
 	}
 
 	private void processServiceTags(ServiceTags serviceTags) {
@@ -830,7 +783,7 @@
 		return ret;
 	}
 
-	static private final class EnrichedServiceTags {
+	static public final class EnrichedServiceTags {
 		final private ServiceTags                                                      serviceTags;
 		final private List<RangerServiceResourceMatcher>                               serviceResourceMatchers;
 		final private Map<String, RangerResourceTrie<RangerServiceResourceMatcher>>    serviceResourceTrie;
@@ -844,11 +797,11 @@
 			this.tagsForEmptyResourceAndAnyAccess = createTagsForEmptyResourceAndAnyAccess();
 			this.resourceTrieVersion              = serviceTags.getTagVersion();
 		}
-		ServiceTags                                                   getServiceTags() {return serviceTags;}
-		List<RangerServiceResourceMatcher>                            getServiceResourceMatchers() { return serviceResourceMatchers;}
-		Map<String, RangerResourceTrie<RangerServiceResourceMatcher>> getServiceResourceTrie() { return serviceResourceTrie;}
-		Long                                                          getResourceTrieVersion() { return resourceTrieVersion;}
-		Set<RangerTagForEval>                                         getTagsForEmptyResourceAndAnyAccess() { return tagsForEmptyResourceAndAnyAccess;}
+		public ServiceTags                                                   getServiceTags() {return serviceTags;}
+		public List<RangerServiceResourceMatcher>                            getServiceResourceMatchers() { return serviceResourceMatchers;}
+		public Map<String, RangerResourceTrie<RangerServiceResourceMatcher>> getServiceResourceTrie() { return serviceResourceTrie;}
+		public Long                                                          getResourceTrieVersion() { return resourceTrieVersion;}
+		public Set<RangerTagForEval>                                         getTagsForEmptyResourceAndAnyAccess() { return tagsForEmptyResourceAndAnyAccess;}
 
 		private Set<RangerTagForEval> createTagsForEmptyResourceAndAnyAccess() {
 			Set<RangerTagForEval> tagsForEmptyResourceAndAnyAccess = new HashSet<>();
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/model/validation/RangerSecurityZoneValidator.java b/agents-common/src/main/java/org/apache/ranger/plugin/model/validation/RangerSecurityZoneValidator.java
index d892676..ba25f13 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/model/validation/RangerSecurityZoneValidator.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/model/validation/RangerSecurityZoneValidator.java
@@ -31,12 +31,12 @@
 import org.apache.ranger.plugin.model.RangerServiceDef;
 import org.apache.ranger.plugin.model.RangerSecurityZone.RangerSecurityZoneService;
 import org.apache.ranger.plugin.policyengine.RangerAccessResourceImpl;
+import org.apache.ranger.plugin.policyengine.RangerResourceTrie;
 import org.apache.ranger.plugin.policyresourcematcher.RangerDefaultPolicyResourceMatcher;
 import org.apache.ranger.plugin.policyresourcematcher.RangerPolicyResourceMatcher;
 import org.apache.ranger.plugin.store.EmbeddedServiceDefsUtil;
 import org.apache.ranger.plugin.store.SecurityZoneStore;
 import org.apache.ranger.plugin.store.ServiceStore;
-import org.apache.ranger.plugin.util.RangerResourceTrie;
 import org.apache.ranger.plugin.util.SearchFilter;
 
 import java.util.ArrayList;
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/PolicyEngine.java b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/PolicyEngine.java
index 38b1c93..a41d2c8 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/PolicyEngine.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/PolicyEngine.java
@@ -25,7 +25,6 @@
 import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
-import java.util.Objects;
 import java.util.Set;
 
 import org.apache.commons.collections.CollectionUtils;
@@ -45,7 +44,6 @@
 import org.apache.ranger.plugin.store.EmbeddedServiceDefsUtil;
 import org.apache.ranger.plugin.util.RangerPerfTracer;
 import org.apache.ranger.plugin.util.RangerPolicyDeltaUtil;
-import org.apache.ranger.plugin.util.RangerResourceTrie;
 import org.apache.ranger.plugin.util.RangerRoles;
 import org.apache.ranger.plugin.util.ServicePolicies;
 
@@ -153,60 +151,16 @@
         return sb;
     }
 
-    public boolean compare(PolicyEngine other) {
-        boolean ret;
-
-        if (policyRepository != null && other.policyRepository != null) {
-            ret = policyRepository .compare(other.policyRepository);
-        } else {
-            ret = policyRepository == other.policyRepository;
-        }
-
-        if (ret) {
-            if (tagPolicyRepository != null && other.tagPolicyRepository != null) {
-                ret = tagPolicyRepository.compare(other.tagPolicyRepository);
-            } else {
-                ret = tagPolicyRepository == other.tagPolicyRepository;
-            }
-        }
-
-        if (ret) {
-            ret = Objects.equals(resourceZoneTrie.keySet(), other.resourceZoneTrie.keySet());
-
-            if (ret) {
-                for (Map.Entry<String, RangerResourceTrie> entry : resourceZoneTrie.entrySet()) {
-                    ret = entry.getValue().compareSubtree(other.resourceZoneTrie.get(entry.getKey()));
-
-                    if (!ret) {
-                        break;
-                    }
-                }
-            }
-        }
-
-        if (ret) {
-            ret = Objects.equals(zonePolicyRepositories.keySet(), other.zonePolicyRepositories.keySet());
-
-            if (ret) {
-                for (Map.Entry<String, RangerPolicyRepository> entry : zonePolicyRepositories.entrySet()) {
-                    ret = entry.getValue().compare(other.zonePolicyRepositories.get(entry.getKey()));
-
-                    if (!ret) {
-                        break;
-                    }
-                }
-            }
-        }
-
-        return ret;
-    }
-
     public List<RangerPolicy> getResourcePolicies(String zoneName) {
         RangerPolicyRepository zoneResourceRepository = zonePolicyRepositories.get(zoneName);
 
         return zoneResourceRepository == null ? ListUtils.EMPTY_LIST : zoneResourceRepository.getPolicies();
     }
 
+    Map<String, RangerResourceTrie> getResourceZoneTrie() {
+        return resourceZoneTrie;
+    }
+
     public RangerAccessResult createAccessResult(RangerAccessRequest request, int policyType) {
         RangerAccessResult ret = new RangerAccessResult(policyType, getServiceName(), getPolicyRepository().getServiceDef(), request);
 
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyEngineImpl.java b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyEngineImpl.java
index 5709fd8..dff54ac 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyEngineImpl.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyEngineImpl.java
@@ -357,6 +357,10 @@
 		return ret;
 	}
 
+	PolicyEngine getPolicyEngine() {
+		return policyEngine;
+	}
+
 	// This API is used only used by test code
 	@Override
 	public RangerResourceAccessInfo getResourceAccessInfo(RangerAccessRequest request) {
@@ -529,10 +533,6 @@
 		}
 	}
 
-	public boolean compare(RangerPolicyEngineImpl other) {
-		return policyEngine.compare(other.policyEngine);
-	}
-
 	private RangerPolicyEngineImpl(final PolicyEngine policyEngine) {
 		this.policyEngine     = policyEngine;
 		this.requestProcessor = new RangerDefaultRequestProcessor(policyEngine);
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyRepository.java b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyRepository.java
index 3a78eab..d2d1722 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyRepository.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerPolicyRepository.java
@@ -38,7 +38,6 @@
 import org.apache.ranger.plugin.policyevaluator.RangerPolicyEvaluator;
 import org.apache.ranger.plugin.store.AbstractServiceStore;
 import org.apache.ranger.plugin.util.RangerPerfTracer;
-import org.apache.ranger.plugin.util.RangerResourceTrie;
 import org.apache.ranger.plugin.util.ServiceDefUtil;
 import org.apache.ranger.plugin.util.ServicePolicies;
 
@@ -1404,7 +1403,7 @@
         return ret;
     }
 
-    private Map<String, RangerResourceTrie> getTrie(final int policyType) {
+    Map<String, RangerResourceTrie> getTrie(final int policyType) {
         final Map<String, RangerResourceTrie> ret;
         switch (policyType) {
             case RangerPolicy.POLICY_TYPE_ACCESS:
@@ -1422,33 +1421,4 @@
         return ret;
     }
 
-    public boolean compare(RangerPolicyRepository other) {
-        return compareTrie(RangerPolicy.POLICY_TYPE_ACCESS, other) &&
-                compareTrie(RangerPolicy.POLICY_TYPE_DATAMASK, other) &&
-                compareTrie(RangerPolicy.POLICY_TYPE_ROWFILTER, other);
-    }
-
-    private boolean compareTrie(final int policyType, RangerPolicyRepository other) {
-        boolean ret;
-
-        Map<String, RangerResourceTrie> myTrie    = getTrie(policyType);
-        Map<String, RangerResourceTrie> otherTrie = other.getTrie(policyType);
-
-        ret = myTrie.size() == otherTrie.size();
-
-        if (ret) {
-            for (Map.Entry<String, RangerResourceTrie> entry : myTrie.entrySet()) {
-                RangerResourceTrie myResourceTrie    = entry.getValue();
-                RangerResourceTrie otherResourceTrie = otherTrie.get(entry.getKey());
-
-                ret = otherResourceTrie != null && myResourceTrie.compareSubtree(otherResourceTrie);
-
-                if (!ret) {
-                    break;
-                }
-            }
-        }
-
-        return ret;
-    }
 }
diff --git a/agents-common/src/main/java/org/apache/ranger/plugin/util/RangerResourceTrie.java b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerResourceTrie.java
similarity index 91%
rename from agents-common/src/main/java/org/apache/ranger/plugin/util/RangerResourceTrie.java
rename to agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerResourceTrie.java
index ea92e3c..88d3b97 100644
--- a/agents-common/src/main/java/org/apache/ranger/plugin/util/RangerResourceTrie.java
+++ b/agents-common/src/main/java/org/apache/ranger/plugin/policyengine/RangerResourceTrie.java
@@ -17,7 +17,7 @@
  * under the License.
  */
 
-package org.apache.ranger.plugin.util;
+package org.apache.ranger.plugin.policyengine;
 
 
 import org.apache.commons.collections.CollectionUtils;
@@ -27,10 +27,10 @@
 import org.apache.hadoop.conf.Configuration;
 import org.apache.ranger.plugin.model.RangerPolicy.RangerPolicyResource;
 import org.apache.ranger.plugin.model.RangerServiceDef;
-import org.apache.ranger.plugin.policyengine.RangerPluginContext;
 import org.apache.ranger.plugin.policyresourcematcher.RangerPolicyResourceEvaluator;
 import org.apache.ranger.plugin.resourcematcher.RangerAbstractResourceMatcher;
 import org.apache.ranger.plugin.resourcematcher.RangerResourceMatcher;
+import org.apache.ranger.plugin.util.RangerPerfTracer;
 
 import java.util.ArrayList;
 import java.util.Collection;
@@ -62,7 +62,33 @@
         this(resourceDef, evaluators, true, null);
     }
 
-    public RangerResourceTrie(RangerServiceDef.RangerResourceDef resourceDef, List<T> evaluators, boolean isOptimizedForRetrieval, RangerPluginContext pluginContext) {
+    public RangerResourceTrie(RangerResourceTrie<T> other) {
+        RangerPerfTracer perf = null;
+
+        if(RangerPerfTracer.isPerfTraceEnabled(PERF_TRIE_INIT_LOG)) {
+            perf = RangerPerfTracer.getPerfTracer(PERF_TRIE_INIT_LOG, "RangerResourceTrie.copyTrie(name=" + other.resourceDef.getName() + ")");
+        }
+
+        this.resourceDef = other.resourceDef;
+        this.optIgnoreCase = other.optIgnoreCase;
+        this.optWildcard = other.optWildcard;
+        this.wildcardChars = other.wildcardChars;
+        this.isOptimizedForRetrieval = false;
+        this.root = copyTrieSubtree(other.root, null);
+
+        RangerPerfTracer.logAlways(perf);
+
+        if (PERF_TRIE_INIT_LOG.isDebugEnabled()) {
+            PERF_TRIE_INIT_LOG.debug(toString());
+        }
+        if (TRACE_LOG.isTraceEnabled()) {
+            StringBuilder sb = new StringBuilder();
+            root.toString("", sb);
+            TRACE_LOG.trace("Trie Dump from RangerResourceTrie.copyTrie(name=" + other.resourceDef.getName() + "):\n{" + sb.toString() + "}");
+        }
+    }
+
+    RangerResourceTrie(RangerServiceDef.RangerResourceDef resourceDef, List<T> evaluators, boolean isOptimizedForRetrieval, RangerPluginContext pluginContext) {
         if(LOG.isDebugEnabled()) {
             LOG.debug("==> RangerResourceTrie(" + resourceDef.getName() + ", evaluatorCount=" + evaluators.size() + ", isOptimizedForRetrieval=" + isOptimizedForRetrieval + ")");
         }
@@ -133,10 +159,6 @@
         }
     }
 
-    public String getResourceName() {
-        return resourceDef.getName();
-    }
-
     public Set<T> getEvaluatorsForResource(Object resource) {
         if (resource instanceof String) {
             return getEvaluatorsForResource((String) resource);
@@ -221,83 +243,8 @@
         }
     }
 
-    public boolean compareSubtree(RangerResourceTrie<T> other) {
-
-        final boolean ret;
-        List<TrieNode<T>> mismatchedNodes = new ArrayList<>();
-
-        if (this.root == null || other.root == null) {
-            ret = this.root == other.root;
-            if (!ret) {
-                mismatchedNodes.add(this.root);
-            }
-        } else {
-            ret = compareSubtree(this.root, other.root, mismatchedNodes);
-        }
-        return ret;
-    }
-
-    private boolean compareSubtree(TrieNode<T> me, TrieNode<T> other, List<TrieNode<T>> misMatched) {
-        boolean ret = StringUtils.equals(me.getStr(), other.getStr());
-
-        if (ret) {
-            Map<Character, TrieNode<T>> myChildren = me.getChildren();
-            Map<Character, TrieNode<T>> otherChildren = other.getChildren();
-
-            ret = myChildren.size() == otherChildren.size() &&
-                    compareLists(me.getEvaluators(), other.getEvaluators()) &&
-                    compareLists(me.getWildcardEvaluators(), other.getWildcardEvaluators()) &&
-                    myChildren.keySet().size() == otherChildren.keySet().size();
-            if (ret) {
-                // Check if subtrees match
-                for (Map.Entry<Character, TrieNode<T>> entry : myChildren.entrySet()) {
-                    Character c = entry.getKey();
-                    TrieNode<T> myNode = entry.getValue();
-                    TrieNode<T> otherNode = otherChildren.get(c);
-                    ret = otherNode != null && compareSubtree(myNode, otherNode, misMatched);
-                    if (!ret) {
-                        break;
-                    }
-                }
-            }
-        }
-
-        if (!ret) {
-            misMatched.add(me);
-        }
-
-        return ret;
-    }
-
-    private boolean compareLists(Set<? extends RangerPolicyResourceEvaluator> me, Set<? extends RangerPolicyResourceEvaluator> other) {
-        boolean ret;
-
-        if (me == null || other == null) {
-            ret = me == other;
-        } else {
-            ret = me.size() == other.size();
-
-            if (ret) {
-		        List<? extends RangerPolicyResourceEvaluator> meAsList = new ArrayList<>(me);
-		        List<? extends RangerPolicyResourceEvaluator> otherAsList = new ArrayList<>(other);
-
-                List<Long> myIds = new ArrayList<>();
-                List<Long> otherIds = new ArrayList<>();
-                for (RangerPolicyResourceEvaluator evaluator : meAsList) {
-                    myIds.add(evaluator.getId());
-                }
-                for (RangerPolicyResourceEvaluator evaluator : otherAsList) {
-                    otherIds.add(evaluator.getId());
-                }
-
-                ret = compareLongLists(myIds, otherIds);
-            }
-        }
-        return ret;
-    }
-
-    private boolean compareLongLists(List<Long> me, List<Long> other) {
-        return me.size() == CollectionUtils.intersection(me, other).size();
+    TrieNode<T> getRoot() {
+        return root;
     }
 
     private TrieNode<T> copyTrieSubtree(final TrieNode<T> source, final TrieNode<T> parent) {
@@ -352,32 +299,6 @@
         return dest;
     }
 
-    public RangerResourceTrie(RangerResourceTrie<T> other) {
-        RangerPerfTracer perf = null;
-
-        if(RangerPerfTracer.isPerfTraceEnabled(PERF_TRIE_INIT_LOG)) {
-            perf = RangerPerfTracer.getPerfTracer(PERF_TRIE_INIT_LOG, "RangerResourceTrie.copyTrie(name=" + other.resourceDef.getName() + ")");
-        }
-
-        this.resourceDef = other.resourceDef;
-        this.optIgnoreCase = other.optIgnoreCase;
-        this.optWildcard = other.optWildcard;
-        this.wildcardChars = other.wildcardChars;
-        this.isOptimizedForRetrieval = false;
-        this.root = copyTrieSubtree(other.root, null);
-
-        RangerPerfTracer.logAlways(perf);
-
-        if (PERF_TRIE_INIT_LOG.isDebugEnabled()) {
-            PERF_TRIE_INIT_LOG.debug(toString());
-        }
-        if (TRACE_LOG.isTraceEnabled()) {
-            StringBuilder sb = new StringBuilder();
-            root.toString("", sb);
-            TRACE_LOG.trace("Trie Dump from RangerResourceTrie.copyTrie(name=" + other.resourceDef.getName() + "):\n{" + sb.toString() + "}");
-        }
-    }
-
     private TrieNode<T> buildTrie(RangerServiceDef.RangerResourceDef resourceDef, List<T> evaluators, int builderThreadCount) {
         if(LOG.isDebugEnabled()) {
             LOG.debug("==> buildTrie(" + resourceDef.getName() + ", evaluatorCount=" + evaluators.size() + ", isMultiThreaded=" + (builderThreadCount > 1) + ")");
@@ -817,7 +738,7 @@
         int wildcardEvaluatorListRefCount;
     }
 
-    private class TrieNode<U extends T> {
+    class TrieNode<U extends T> {
         private          String                      str;
         private          TrieNode<U>                 parent;
         private final    Map<Character, TrieNode<U>> children = new HashMap<>();
@@ -1132,7 +1053,7 @@
 
         }
 
-        public void toString(StringBuilder sb) {
+        void toString(StringBuilder sb) {
             String nodeValue = this.str;
 
             sb.append("nodeValue=").append(nodeValue);
@@ -1155,7 +1076,7 @@
             }
         }
 
-        public void toString(String prefix, StringBuilder sb) {
+        void toString(String prefix, StringBuilder sb) {
             String nodeValue = prefix + (str != null ? str : "");
 
             sb.append(prefix);
@@ -1169,12 +1090,5 @@
             }
 
         }
-
-        public void clear() {
-            children.clear();
-
-            evaluators         = null;
-            wildcardEvaluators = null;
-        }
     }
 }
diff --git a/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngine.java b/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngine.java
index b4c3060..28f7314 100644
--- a/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngine.java
+++ b/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngine.java
@@ -32,20 +32,25 @@
 import org.apache.ranger.audit.provider.AuditHandler;
 import org.apache.ranger.audit.provider.AuditProviderFactory;
 import org.apache.ranger.plugin.audit.RangerDefaultAuditHandler;
+import org.apache.ranger.plugin.contextenricher.RangerServiceResourceMatcher;
+import org.apache.ranger.plugin.contextenricher.RangerTagEnricher;
 import org.apache.ranger.plugin.contextenricher.RangerTagForEval;
 import org.apache.ranger.plugin.model.RangerPolicy;
 import org.apache.ranger.plugin.model.RangerPolicyDelta;
 import org.apache.ranger.plugin.model.RangerRole;
 import org.apache.ranger.plugin.model.RangerServiceDef;
+import org.apache.ranger.plugin.model.RangerServiceResource;
 import org.apache.ranger.plugin.model.RangerValiditySchedule;
 import org.apache.ranger.plugin.model.validation.RangerValidityScheduleValidator;
 import org.apache.ranger.plugin.model.validation.ValidationFailureDetails;
 import org.apache.ranger.plugin.policyengine.TestPolicyEngine.PolicyEngineTestCase.TestData;
 import org.apache.ranger.plugin.policyevaluator.RangerValidityScheduleEvaluator;
+import org.apache.ranger.plugin.policyresourcematcher.RangerPolicyResourceEvaluator;
 import org.apache.ranger.plugin.util.RangerAccessRequestUtil;
 import org.apache.ranger.plugin.util.RangerRequestedResources;
 import org.apache.ranger.plugin.util.RangerRoles;
 import org.apache.ranger.plugin.util.ServicePolicies;
+import org.apache.ranger.plugin.util.ServiceTags;
 import org.junit.AfterClass;
 import org.junit.BeforeClass;
 import org.junit.Test;
@@ -63,6 +68,7 @@
 import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
+import java.util.Objects;
 import java.util.Properties;
 import java.util.Set;
 import java.util.TimeZone;
@@ -766,5 +772,216 @@
 			return gsonBuilder.fromJson(jsonObj, RangerAccessResourceImpl.class);
 		}
 	}
+
+	// Test utility functions
+	public static boolean compare(PolicyEngine me, PolicyEngine other) {
+		boolean ret;
+
+		if (me.getPolicyRepository() != null && other.getPolicyRepository() != null) {
+			ret = compare(me.getPolicyRepository(), other.getPolicyRepository());
+		} else {
+			ret = me.getPolicyRepository() == other.getPolicyRepository();
+		}
+
+		if (ret) {
+			if (me.getTagPolicyRepository() != null && other.getTagPolicyRepository() != null) {
+				ret = compare(me.getTagPolicyRepository(), other.getTagPolicyRepository());
+			} else {
+				ret = me.getTagPolicyRepository() == other.getTagPolicyRepository();
+			}
+		}
+
+		if (ret) {
+			ret = Objects.equals(me.getResourceZoneTrie().keySet(), other.getResourceZoneTrie().keySet());
+
+			if (ret) {
+				for (Map.Entry<String, RangerResourceTrie> entry : me.getResourceZoneTrie().entrySet()) {
+					ret = compareSubtree(entry.getValue(), other.getResourceZoneTrie().get(entry.getKey()));
+
+					if (!ret) {
+						break;
+					}
+				}
+			}
+		}
+
+		if (ret) {
+			ret = Objects.equals(me.getZonePolicyRepositories().keySet(), other.getZonePolicyRepositories().keySet());
+
+			if (ret) {
+				for (Map.Entry<String, RangerPolicyRepository> entry : me.getZonePolicyRepositories().entrySet()) {
+					ret = compare(entry.getValue(), other.getZonePolicyRepositories().get(entry.getKey()));
+
+					if (!ret) {
+						break;
+					}
+				}
+			}
+		}
+
+		return ret;
+	}
+
+	public static boolean compare(RangerPolicyRepository me, RangerPolicyRepository other) {
+		return compareTrie(RangerPolicy.POLICY_TYPE_ACCESS, me, other) &&
+				compareTrie(RangerPolicy.POLICY_TYPE_DATAMASK, me, other) &&
+				compareTrie(RangerPolicy.POLICY_TYPE_ROWFILTER, me, other);
+	}
+
+	public static boolean compareTrie(final int policyType, RangerPolicyRepository me, RangerPolicyRepository other) {
+		boolean ret;
+
+		Map<String, RangerResourceTrie> myTrie    = me.getTrie(policyType);
+		Map<String, RangerResourceTrie> otherTrie = other.getTrie(policyType);
+
+		ret = myTrie.size() == otherTrie.size();
+
+		if (ret) {
+			for (Map.Entry<String, RangerResourceTrie> entry : myTrie.entrySet()) {
+				RangerResourceTrie myResourceTrie    = entry.getValue();
+				RangerResourceTrie otherResourceTrie = otherTrie.get(entry.getKey());
+
+				ret = otherResourceTrie != null && compareSubtree(myResourceTrie, otherResourceTrie);
+
+				if (!ret) {
+					break;
+				}
+			}
+		}
+
+		return ret;
+	}
+
+	public static boolean compare(RangerTagEnricher me, RangerTagEnricher other) {
+		boolean ret;
+
+		if (me.getEnrichedServiceTags() == null || other == null || other.getEnrichedServiceTags() == null) {
+			return false;
+		}
+
+		if (me.getEnrichedServiceTags().getServiceResourceTrie() != null && other.getEnrichedServiceTags().getServiceResourceTrie() != null) {
+			ret = me.getEnrichedServiceTags().getServiceResourceTrie().size() == other.getEnrichedServiceTags().getServiceResourceTrie().size();
+
+			if (ret && me.getEnrichedServiceTags().getServiceResourceTrie().size() > 0) {
+				for (Map.Entry<String, RangerResourceTrie<RangerServiceResourceMatcher>> entry : me.getEnrichedServiceTags().getServiceResourceTrie().entrySet()) {
+					ret = compareSubtree(entry.getValue(), other.getEnrichedServiceTags().getServiceResourceTrie().get(entry.getKey()));
+					if (!ret) {
+						break;
+					}
+				}
+			}
+		} else {
+			ret = me.getEnrichedServiceTags().getServiceResourceTrie() == other.getEnrichedServiceTags().getServiceResourceTrie();
+		}
+
+		if (ret) {
+			// Compare mappings
+			ServiceTags myServiceTags = me.getEnrichedServiceTags().getServiceTags();
+			ServiceTags otherServiceTags = other.getEnrichedServiceTags().getServiceTags();
+
+			ret = StringUtils.equals(myServiceTags.getServiceName(), otherServiceTags.getServiceName()) &&
+					//myServiceTags.getTagVersion().equals(otherServiceTags.getTagVersion()) &&
+					myServiceTags.getTags().size() == otherServiceTags.getTags().size() &&
+					myServiceTags.getServiceResources().size() == otherServiceTags.getServiceResources().size() &&
+					myServiceTags.getResourceToTagIds().size() == otherServiceTags.getResourceToTagIds().size();
+			if (ret) {
+				for (RangerServiceResource serviceResource : myServiceTags.getServiceResources()) {
+					Long serviceResourceId = serviceResource.getId();
+
+					List<Long> myTagsForResource = myServiceTags.getResourceToTagIds().get(serviceResourceId);
+					List<Long> otherTagsForResource = otherServiceTags.getResourceToTagIds().get(serviceResourceId);
+
+					ret = CollectionUtils.size(myTagsForResource) == CollectionUtils.size(otherTagsForResource);
+
+					if (ret && CollectionUtils.size(myTagsForResource) > 0) {
+						ret = myTagsForResource.size() == CollectionUtils.intersection(myTagsForResource, otherTagsForResource).size();
+					}
+				}
+			}
+		}
+
+		return ret;
+	}
+
+	public static boolean compareSubtree(RangerResourceTrie me, RangerResourceTrie other) {
+
+		final boolean ret;
+		List<RangerResourceTrie.TrieNode> mismatchedNodes = new ArrayList<>();
+
+		if (me.getRoot() == null || other.getRoot() == null) {
+			ret = me.getRoot() == other.getRoot();
+			if (!ret) {
+				mismatchedNodes.add(me.getRoot());
+			}
+		} else {
+			ret = compareSubtree(me.getRoot(), other.getRoot(), mismatchedNodes);
+		}
+		return ret;
+	}
+
+	private static boolean compareSubtree(RangerResourceTrie.TrieNode me, RangerResourceTrie.TrieNode other, List<RangerResourceTrie.TrieNode> misMatched) {
+		boolean ret = StringUtils.equals(me.getStr(), other.getStr());
+
+		if (ret) {
+			Map<Character, RangerResourceTrie.TrieNode> myChildren = me.getChildren();
+			Map<Character, RangerResourceTrie.TrieNode> otherChildren = other.getChildren();
+
+			ret = myChildren.size() == otherChildren.size() &&
+					compareLists(me.getEvaluators(), other.getEvaluators()) &&
+					compareLists(me.getWildcardEvaluators(), other.getWildcardEvaluators()) &&
+					myChildren.keySet().size() == otherChildren.keySet().size();
+			if (ret) {
+				// Check if subtrees match
+				for (Map.Entry<Character, RangerResourceTrie.TrieNode> entry : myChildren.entrySet()) {
+					Character c = entry.getKey();
+					RangerResourceTrie.TrieNode myNode = entry.getValue();
+					RangerResourceTrie.TrieNode otherNode = otherChildren.get(c);
+					ret = otherNode != null && compareSubtree(myNode, otherNode, misMatched);
+					if (!ret) {
+						break;
+					}
+				}
+			}
+		}
+
+		if (!ret) {
+			misMatched.add(me);
+		}
+
+		return ret;
+	}
+
+	private static boolean compareLists(Set me, Set other) {
+		boolean ret;
+
+		if (me == null || other == null) {
+			ret = me == other;
+		} else {
+			ret = me.size() == other.size();
+
+			if (ret) {
+				List<? extends RangerPolicyResourceEvaluator> meAsList = new ArrayList<>(me);
+				List<? extends RangerPolicyResourceEvaluator> otherAsList = new ArrayList<>(other);
+
+				List<Long> myIds = new ArrayList<>();
+				List<Long> otherIds = new ArrayList<>();
+				for (RangerPolicyResourceEvaluator evaluator : meAsList) {
+					myIds.add(evaluator.getId());
+				}
+				for (RangerPolicyResourceEvaluator evaluator : otherAsList) {
+					otherIds.add(evaluator.getId());
+				}
+
+				ret = compareLongLists(myIds, otherIds);
+			}
+		}
+		return ret;
+	}
+
+	private static boolean compareLongLists(List<Long> me, List<Long> other) {
+		return me.size() == CollectionUtils.intersection(me, other).size();
+	}
+
+
 }
 
diff --git a/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngineComparison.java b/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngineComparison.java
index 94ba8b9..4ba0fa1 100644
--- a/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngineComparison.java
+++ b/agents-common/src/test/java/org/apache/ranger/plugin/policyengine/TestPolicyEngineComparison.java
@@ -126,7 +126,7 @@
                 RangerPolicyEngineImpl myPolicyEngine = new RangerPolicyEngineImpl("test-compare-my-engine", myServicePolicies, options, rangerPluginContext, null);
                 RangerPolicyEngineImpl otherPolicyEngine = new RangerPolicyEngineImpl("test-compare-other-engine", otherServicePolicies, options, rangerPluginContext, null);
 
-                isPolicyEnginesEqual = myPolicyEngine.compare(otherPolicyEngine) && otherPolicyEngine.compare(myPolicyEngine);
+                isPolicyEnginesEqual = TestPolicyEngine.compare(myPolicyEngine.getPolicyEngine(), otherPolicyEngine.getPolicyEngine()) && TestPolicyEngine.compare(otherPolicyEngine.getPolicyEngine(), myPolicyEngine.getPolicyEngine());
 
 
                 if (myServiceTags != null) {
@@ -143,7 +143,7 @@
                     otherTagEnricher.setServiceName(otherServiceTags.getServiceName());
                     otherTagEnricher.setServiceTags(otherServiceTags);
 
-                    isTagsEqual = myTagEnricher.compare(otherTagEnricher) && otherTagEnricher.compare(myTagEnricher);
+                    isTagsEqual = TestPolicyEngine.compare(myTagEnricher, otherTagEnricher) && TestPolicyEngine.compare(otherTagEnricher, myTagEnricher);
 
                 }
             }