ingo@107: /*
ingo@107: * Copyright (c) 2011 by Intevation GmbH
ingo@107: *
ingo@107: * This program is free software under the LGPL (>=v2.1)
ingo@107: * Read the file LGPL.txt coming with the software for details
ingo@107: * or visit http://www.gnu.org/licenses/ if it does not exist.
ingo@107: */
ingo@107: package de.intevation.artifactdatabase;
ingo@107:
ingo@109: import java.util.List;
ingo@107:
ingo@295: import org.w3c.dom.Document;
ingo@107: import org.w3c.dom.Element;
ingo@295: import org.w3c.dom.Node;
ingo@295:
ingo@295: import de.intevation.artifacts.ArtifactNamespaceContext;
ingo@107:
ingo@107: import de.intevation.artifacts.common.utils.XMLUtils;
ingo@295: import de.intevation.artifacts.common.utils.XMLUtils.ElementCreator;
ingo@107:
ingo@227: import de.intevation.artifactdatabase.state.Facet;
ingo@211: import de.intevation.artifactdatabase.state.Output;
ingo@109: import de.intevation.artifactdatabase.state.State;
ingo@109:
ingo@107:
ingo@107: /**
ingo@107: * This class provides methods that help creating the artifact protocol
ingo@107: * documents describe, feed, advance and out.
ingo@107: *
ingo@107: * @author Ingo Weinzierl
ingo@107: */
ingo@107: public class ProtocolUtils {
ingo@107:
ingo@107: /**
ingo@107: * It should not be necessary to create instances of this class.
ingo@107: */
ingo@107: private ProtocolUtils() {}
ingo@107:
ingo@107:
ingo@107: /**
ingo@107: * This method creates a node that might be used for the artifact protocol.
ingo@107: *
ingo@107: * @param creator The ElementCreator that is used to create the node.
ingo@107: * @param nodeName The node name.
ingo@107: * @param attrName The names of optional attributes.
ingo@107: * @param value The values for the optional attributes.
ingo@107: *
ingo@107: * @return the created node.
ingo@107: */
ingo@107: public static Element createArtNode(
ingo@107: XMLUtils.ElementCreator creator,
ingo@107: String nodeName, String[] attrName, String[] value)
ingo@107: {
ingo@107: Element typeNode = creator.create(nodeName);
ingo@107:
ingo@107: if (attrName != null && value != null) {
ingo@107: for (int i = 0; i < attrName.length; i++) {
ingo@107: if (i < value.length) {
ingo@107: creator.addAttr(typeNode, attrName[i], value[i], true);
ingo@107: }
ingo@107: else {
ingo@107: break;
ingo@107: }
ingo@107: }
ingo@107: }
ingo@107:
ingo@107: return typeNode;
ingo@107: }
ingo@107:
ingo@107:
ingo@107: /**
ingo@107: * This method creates the root node for all artifact protocol documents.
ingo@107: *
ingo@107: * @param creator The ElementCreator used to create new elements.
ingo@107: *
ingo@107: * @return the root node for the artifact protocol document.
ingo@107: */
ingo@107: public static Element createRootNode(XMLUtils.ElementCreator creator) {
ingo@107: return createArtNode(creator, "result", null, null);
ingo@107: }
ingo@107:
ingo@107:
ingo@107: /**
ingo@107: * This method appends the three necessary nodes type, uuid
ingo@107: * and hash of the describe document to root node.
ingo@107: *
ingo@107: * @param creator The ElementCreator that is used to create new nodes.
ingo@107: * @param root The root node of the describe document.
ingo@107: * @param uuid The UUID of the artifact.
ingo@107: * @param hash The hash if the artifact.
ingo@107: */
ingo@107: public static void appendDescribeHeader(
ingo@107: XMLUtils.ElementCreator creator, Element root, String uuid, String hash)
ingo@107: {
ingo@107: root.appendChild(createArtNode(
ingo@107: creator,
ingo@107: "type",
ingo@107: new String[] {"name"},
ingo@107: new String[] {"describe"}));
ingo@107:
ingo@107: root.appendChild(createArtNode(
ingo@107: creator,
ingo@107: "uuid",
ingo@107: new String[] {"value"},
ingo@107: new String[] {uuid}));
ingo@107:
ingo@107: root.appendChild(createArtNode(
ingo@107: creator,
ingo@107: "hash",
ingo@107: new String[] {"value"},
ingo@107: new String[] {hash}));
ingo@107: }
ingo@109:
ingo@109:
ingo@109: /**
ingo@109: * This method appends a node that describes the current state to
ingo@109: * root.
ingo@109: *
ingo@109: * @param creator The ElementCreator used to create new elements.
ingo@109: * @param root The parent node for new elements.
ingo@109: * @param state The state to be appended.
ingo@109: */
ingo@109: public static void appendState(
ingo@109: XMLUtils.ElementCreator creator, Element root, State state)
ingo@109: {
ingo@109: root.appendChild(createArtNode(
ingo@109: creator, "state",
ingo@109: new String[] { "description", "name" },
ingo@109: new String[] { state.getDescription(), state.getID() }));
ingo@109: }
ingo@109:
ingo@109:
ingo@109: /**
ingo@109: * This method appends a node with reachable states to root.
ingo@109: *
ingo@109: * @param creator The ElementCreator used to create new elements.
ingo@109: * @param root The parent node for new elements.
ingo@109: * @param states The reachable states to be appended.
ingo@109: */
ingo@109: public static void appendReachableStates(
ingo@109: XMLUtils.ElementCreator creator,
ingo@109: Element root,
ingo@109: List states)
ingo@109: {
ingo@109: Element reachable = createArtNode(
ingo@109: creator, "reachable-states", null, null);
ingo@109:
ingo@109: for (State s: states) {
ingo@109: appendState(creator, reachable, s);
ingo@109: }
ingo@109:
ingo@109: root.appendChild(reachable);
ingo@109: }
ingo@211:
ingo@211:
ingo@227: /**
ingo@227: * This method appends a node for each Output in the outputs list to
ingo@227: * out. Note: an output node includes its provided facets!
ingo@227: *
felix@400: * @param doc The document to which to add new elements.
ingo@227: * @param out The parent node for new elements.
ingo@227: * @param outputs The list of reachable outputs.
ingo@227: */
ingo@211: public static void appendOutputModes(
ingo@295: Document doc,
ingo@295: Element out,
ingo@295: List