/* Copyright 2014 MITRE Corporation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.mitre.provenance.dag;
import javax.ws.rs.core.MultivaluedHashMap;
import javax.ws.rs.core.MultivaluedMap;
/**
* Controls the settings that the graph traverser uses to determine
* what to return in response to a given query.
*
* <p>This object provides relatively fine-grained control over what kind of
* provenance graph to discover from the database.
*
* <p>Creating default instances of this object will traverse the graph in both directions.
*
* <P>Specific objects can be created idiomatically by using the chaining methods specified below, such as:
*
* <pre>new TraversalSettings().onlyForward().setMaxDepth(1).excludeEdges().includeNodes();</pre>
*
* <p>For example, that will create a TraversalSettings object that instructs the code to fetch all nodes forward of
* a starting point, only one hop away, returning a set of nodes but not edges.
* @author moxious
*/
public class TraversalSettings {
public static final TraversalSettings UNLIMITED = new TraversalSettings(-1, -1, true, true, true, true, true, true, true);
public static final TraversalSettings UNLIMITED_PROVENANCE_ONLY = new TraversalSettings(-1, -1, true, true, true, false, false, true, true);
/** The maximum number of nodes to return */
public int n = 200;
/** The maximum depth away from the starting point to visit.
* A value of less than or equal to zero means no limit.
*/
public int maxDepth = 10;
/** If true, breadth first will be used. If false, depth first */
public boolean breadthFirst = true;
/** Whether the result should include nodes */
public boolean includeNodes = true;
/** Whether the result should include edges */
public boolean includeEdges = true;
/** Whether the result should include non-provenance edges */
public boolean includeNPEs = true;
/** Whether or not NPIDs should be followed when
* discovering new nodes in the graph.
*/
public boolean followNPIDs = true;
/** Whether or not to traverse forward in the DAG */
public boolean forward = true;
/** Whether or not to traverse backwards in the DAG */
public boolean backward = true;
/** Whether or not to expand workflows. */
public boolean expandWorkflows = true;
private TraversalSettings(int n, int maxDepth, boolean breadthFirst, boolean includeNodes, boolean includeEdges,
boolean includeNPEs, boolean followNPIDs, boolean forward, boolean backward) {
this.n = n;
this.maxDepth = maxDepth;
this.breadthFirst = breadthFirst;
this.includeNodes = includeNodes;
this.includeEdges = includeEdges;
this.includeNPEs = includeNPEs;
this.followNPIDs = followNPIDs;
this.forward = forward;
this.backward = backward;
}
public TraversalSettings() {
this(200, 10, true, true, true, true, true, true, true);
}
/** Traversal will not expand workflows (that is, will keep them individual nodes) */
public TraversalSettings dontExpandWorkflows() { expandWorkflows = false; return this; }
/** Traversal will expand workflows (that is, expand their members and traverse them) */
public TraversalSettings expandWorkflows() { expandWorkflows = true; return this; }
/** Traversal will not follow non-provenance edges/IDs */
public TraversalSettings ignoreNPIDs() { followNPIDs = false; return this; }
/** Traversal will follow non-provenance edges/IDs. */
public TraversalSettings followNPIDs() { followNPIDs = true; return this; }
/** Traversal will go both forwards and backwards (upstream/downstream) */
public TraversalSettings bothWays() { forward = true; backward = true; return this; }
/** Set the maximum number of nodes to return */
public TraversalSettings setN(int n) { this.n = n; return this; }
/** Traversal will go forward only */
public TraversalSettings onlyForward() { forward = true; backward = false; return this; }
/* Traversal will go backward only */
public TraversalSettings onlyBackward() { forward = false; backward = true; return this; }
/** Results will not include NonProvenanceEdge objects */
public TraversalSettings excludeNPEs() { includeNPEs = false; return this; }
/** Results will include NonProvenanceEdge objects as appropriate */
public TraversalSettings includeNPEs() { includeNPEs = true; return this; }
/** Results will not include edge objects */
public TraversalSettings excludeEdges() { includeEdges = false; return this; }
/** Results will include edge objects */
public TraversalSettings includeEdges() { includeEdges = true; return this; }
/** Results will exclude nodes */
public TraversalSettings excludeNodes() { includeNodes = false; return this; }
/** Results will include nodes */
public TraversalSettings includeNodes() { includeNodes = true; return this; }
/** Traversal will occur depth first */
public TraversalSettings depthFirst() { breadthFirst = false; return this; }
/** Traversal will occur breadth first */
public TraversalSettings breadthFirst() { breadthFirst = true; return this; }
/** Traversal will go to a maximum depth of the parameter specified */
public TraversalSettings setMaxDepth(int maxDepth) { this.maxDepth = maxDepth; return this; }
/**
* Utility method to return the properties of this object as a map.
* @return
*/
public MultivaluedMap<String,String> asMultivaluedMap() {
MultivaluedMap<String,String> m = new MultivaluedHashMap<String,String>();
m.add("n", ""+n);
m.add("maxDepth", ""+maxDepth);
m.add("breadthFirst", ""+breadthFirst);
m.add("includeNodes", ""+includeNodes);
m.add("includeEdges", ""+includeEdges);
m.add("includeNPEs", ""+includeNPEs);
m.add("followNPIDs", ""+followNPIDs);
m.add("forward", ""+forward);
m.add("backward", ""+backward);
return m;
}
public String toString() {
return (breadthFirst ? "Breadth first" : "Depth first") + ": " +
n + " nodes to depth " + maxDepth + " including (" +
(includeNodes ? "nodes, " : "") +
(includeEdges ? "edges, " : "") +
(includeNPEs ? "NPEs" : "") +
") forward=" + forward + " backward=" + backward +
(followNPIDs ? "following NPIDs" : "");
}
} // End TraversalSettings