⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 xpathevaluator.java

📁 ejb3 java session bean
💻 JAVA
字号:
/* * JBoss, Home of Professional Open Source * Copyright 2005, JBoss Inc., and individual contributors as indicated * by the @authors tag. * * This is free software; you can redistribute it and/or modify it * under the terms of the JBPM BPEL PUBLIC LICENSE AGREEMENT as * published by JBoss Inc.; either version 1.0 of the License, or * (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. */package org.jbpm.bpel.sublang.xpath;import java.io.IOException;import java.util.ArrayList;import java.util.Collections;import java.util.Iterator;import java.util.List;import javax.xml.namespace.QName;import org.apache.commons.logging.Log;import org.apache.commons.logging.LogFactory;import org.jaxen.BaseXPath;import org.jaxen.Context;import org.jaxen.ContextSupport;import org.jaxen.Function;import org.jaxen.FunctionContext;import org.jaxen.JaxenException;import org.jaxen.SimpleFunctionContext;import org.jaxen.dom.DocumentNavigator;import org.jaxen.expr.CommentNodeStep;import org.jaxen.expr.LocationPath;import org.jaxen.expr.NameStep;import org.jaxen.expr.Predicate;import org.jaxen.expr.ProcessingInstructionNodeStep;import org.jaxen.expr.Step;import org.jaxen.expr.TextNodeStep;import org.jaxen.saxpath.Axis;import org.w3c.dom.Attr;import org.w3c.dom.Document;import org.w3c.dom.Element;import org.w3c.dom.Node;import org.xml.sax.SAXException;import org.jbpm.JbpmConfiguration;import org.jbpm.bpel.graph.exe.BpelFaultException;import org.jbpm.bpel.xml.BpelConstants;import org.jbpm.bpel.xml.util.XmlUtil;import org.jbpm.util.ClassLoaderUtil;/** * @author Alejandro Guizar * @version $Revision: 1.9 $ $Date: 2007/09/04 06:42:26 $ */abstract class XPathEvaluator extends BaseXPath {  private static final FunctionContext EMPTY_FUNCTION_CONTEXT = new SimpleFunctionContext();  private static final Log log = LogFactory.getLog(XPathEvaluator.class);  private static final long serialVersionUID = 1L;  XPathEvaluator(String text) throws JaxenException {    super(text, DocumentNavigator.getInstance());  }  protected static List selectOrCreateNodes(LocationPath location, Context context)      throws JaxenException {    List contextNodes = context.getNodeSet();    // empty context nodeset -> empty selection    if (contextNodes.isEmpty())      return Collections.EMPTY_LIST;    ContextSupport support = context.getContextSupport();    // absolute path?    if (location.isAbsolute()) {      // start from the root node      Object rootNode = support.getNavigator().getDocumentNode(contextNodes.get(0));      contextNodes = Collections.singletonList(rootNode);    }    Iterator stepIter = location.getSteps().iterator();    while (stepIter.hasNext()) {      // prepare the context for the current step      Context stepContext = new Context(support);      stepContext.setNodeSet(contextNodes);      // evaluate the step, capture the selected nodes      Step step = (Step) stepIter.next();      contextNodes = step.evaluate(stepContext);      // no node was selected?      if (contextNodes.isEmpty()) {        // try to create the missing node        Node newNode = createNode(step, stepContext);        // create a new list, since the existing empty list is immutable        contextNodes = Collections.singletonList(newNode);      }    }    return contextNodes;  }  private static Node createNode(Step step, Context context) {    List nodeset = context.getNodeSet();    if (nodeset.size() != 1) {      log.error("cannot create node for context node set of size other than one: " + nodeset);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    Object contextNode = nodeset.get(0);    if (!(contextNode instanceof Element)) {      log.error("cannot create node for non-element context node: " + contextNode);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    Element contextElem = (Element) contextNode;    Node newNode;    switch (step.getAxis()) {    case Axis.ATTRIBUTE:      newNode = createAttribute(step, context, contextElem);      break;    case Axis.CHILD:      if (step instanceof NameStep)        newNode = createElement((NameStep) step, context, contextElem);      else        newNode = createNonElementChild(step, contextElem);      contextElem.appendChild(newNode);      break;    default:      log.error("cannot create node on the specified axis: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    return newNode;  }  private static Attr createAttribute(Step step, Context context, Element contextElem) {    if (!step.getPredicates().isEmpty()) {      log.error("cannot create attribute for step with predicates: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    if (!(step instanceof NameStep)) {      log.error("cannot create attribute for non-name node test: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    NameStep nameStep = (NameStep) step;    String localName = nameStep.getLocalName();    if ("*".equals(localName)) {      log.error("cannot create attribute for any-name node test: " + nameStep);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    // BPEL-191: preserve source prefix    String prefix = nameStep.getPrefix();    String namespaceURI = context.translateNamespacePrefixToUri(prefix);    Attr attribute = contextElem.getOwnerDocument().createAttributeNS(namespaceURI,        namespaceURI != null ? prefix + ':' + localName : localName);    contextElem.setAttributeNodeNS(attribute);    return attribute;  }  private static Element createElement(NameStep step, Context context, Element contextElem) {    String localName = step.getLocalName();    if ("*".equals(localName)) {      log.error("cannot create node for any-name node tests: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    // BPEL-191: preserve source prefix    String prefix = step.getPrefix();    String namespaceURI = context.translateNamespacePrefixToUri(prefix);    List predicates = step.getPredicates();    switch (predicates.size()) {    case 0:      break;    case 1: {      // prepare the context for the predicate      List contextNodes = getElements(contextElem, namespaceURI, localName);      Context predicateContext = new Context(context.getContextSupport());      predicateContext.setNodeSet(contextNodes);      try {        // evaluate the predicate, capture the result        Predicate predicate = (Predicate) predicates.get(0);        Object result = predicate.evaluate(predicateContext);        if (!(result instanceof Number)) {          log.error("cannot create element for step with non-numeric predicate: " + step);          throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);        }        if (((Number) result).intValue() != contextNodes.size() + 1) {          log.error("cannot create element for step with numeric predicate "              + "beyond the next position: "              + step);          throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);        }      }      catch (JaxenException e) {        log.error("predicate evaluation failed", e);        throw new BpelFaultException(BpelConstants.FAULT_SUB_LANGUAGE_EXECUTION);      }      break;    }    default:      log.error("cannot create element for step with multiple predicates: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    String qualifiedName = namespaceURI != null ? prefix + ':' + localName : localName;    return contextElem.getOwnerDocument().createElementNS(namespaceURI, qualifiedName);  }  private static Node createNonElementChild(Step step, Element contextElem) {    if (!step.getPredicates().isEmpty()) {      log.error("cannot create node for step with predicates: " + step);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    Document contextDoc = contextElem.getOwnerDocument();    if (step instanceof TextNodeStep)      return contextDoc.createTextNode("");    if (step instanceof ProcessingInstructionNodeStep) {      ProcessingInstructionNodeStep processingStep = (ProcessingInstructionNodeStep) step;      return contextDoc.createProcessingInstruction(processingStep.getName(), "");    }    if (step instanceof CommentNodeStep)      return contextDoc.createComment("");    log.error("cannot create node for any-node tests on the child axis: " + step);    throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);  }  private static List getElements(Element parent, String namespaceURI, String localName) {    ArrayList elements = new ArrayList();    for (Node child = parent.getFirstChild(); child != null; child = child.getNextSibling()) {      if (XmlUtil.nodeNameEquals(child, namespaceURI, localName))        elements.add(child);    }    return elements;  }  protected static Node narrowToSingleNode(List nodeset) {    log.debug("narrowing to single node: " + nodeset);    if (nodeset == null || nodeset.size() != 1) {      log.error("selection of size other than one: " + nodeset);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    Object singleResult = nodeset.get(0);    if (!(singleResult instanceof Node)) {      log.error("selection is not a node: " + singleResult);      throw new BpelFaultException(BpelConstants.FAULT_SELECTION_FAILURE);    }    return (Node) singleResult;  }  protected static FunctionContext readFunctionLibrary(String configName) {    // get functions resource name    String resource = JbpmConfiguration.Configs.getString(configName);    // parse functions document    Element functionsElem;    try {      functionsElem = XmlUtil.parseResource(resource);    }    catch (SAXException e) {      log.error("functions document contains invalid xml: " + resource, e);      return EMPTY_FUNCTION_CONTEXT;    }    catch (IOException e) {      log.error("could not read functions document: " + resource, e);      return EMPTY_FUNCTION_CONTEXT;    }    // load function context class    String functionContextClassName = functionsElem.getAttribute("class");    Class functionContextClass = ClassLoaderUtil.loadClass(functionContextClassName);    // instantiate function context    FunctionContext functionContext;    try {      functionContext = (FunctionContext) functionContextClass.newInstance();    }    catch (InstantiationException e) {      log.warn("function context class not instantiable: " + functionContextClassName, e);      return EMPTY_FUNCTION_CONTEXT;    }    catch (IllegalAccessException e) {      log.warn("function context class or constructor not public: " + functionContextClassName, e);      return EMPTY_FUNCTION_CONTEXT;    }    // walk through function elements    Iterator functionElemIt = XmlUtil.getElements(functionsElem, null, "function");    if (functionElemIt.hasNext()) {      /*       * since the FunctionContext interface does not mandate methods to register new functions, we       * cannot add functions to an arbitrary implementation, unless it is a subclass of the       * SimpleFunctionContext included with Jaxen       */      if (!SimpleFunctionContext.class.isAssignableFrom(functionContextClass)) {        log.warn("unknown function context implementation, cannot add functions to it: "            + functionContextClassName);        return functionContext;      }      SimpleFunctionContext simpleContext = (SimpleFunctionContext) functionContext;      while (functionElemIt.hasNext()) {        Element functionElem = (Element) functionElemIt.next();        // name - XPath function names are QNames        QName functionName = XmlUtil.getQNameValue(functionElem.getAttributeNode("name"));        // load function class        String functionClassName = functionElem.getAttribute("class");        Class functionClass = ClassLoaderUtil.loadClass(functionClassName);        // validate function class        if (!Function.class.isAssignableFrom(functionClass)) {          log.warn("not a function: " + functionClassName);          continue;        }        try {          // instantiate function          Function function = (Function) functionClass.newInstance();          // register function          simpleContext.registerFunction(functionName.getNamespaceURI(),              functionName.getLocalPart(), function);          log.debug("registered function: name=" + functionName + ", class=" + functionClassName);        }        catch (InstantiationException e) {          log.warn("function class not instantiable: " + functionClassName, e);        }        catch (IllegalAccessException e) {          log.warn("function class or constructor not public: " + functionClassName, e);        }      }    }    return functionContext;  }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -