diff --git a/ext/java/nokogiri/NokogiriService.java b/ext/java/nokogiri/NokogiriService.java index a5d5b462ba..21c0c46a4c 100644 --- a/ext/java/nokogiri/NokogiriService.java +++ b/ext/java/nokogiri/NokogiriService.java @@ -92,6 +92,8 @@ public class NokogiriService implements BasicLibraryService createSaxModule(ruby, xmlSaxModule, htmlSaxModule); createXsltModule(ruby, xsltModule); nokogiri.setInternalVariable("cache", populateNokogiriClassCahce(ruby)); + + org.apache.xml.security.Init.init(); } private void diff --git a/ext/java/nokogiri/XmlDocument.java b/ext/java/nokogiri/XmlDocument.java index 3141ae28c4..8960e046be 100644 --- a/ext/java/nokogiri/XmlDocument.java +++ b/ext/java/nokogiri/XmlDocument.java @@ -8,6 +8,7 @@ import static nokogiri.internals.NokogiriHelpers.stringOrNil; import java.util.List; +import java.io.ByteArrayOutputStream; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; @@ -36,13 +37,13 @@ import org.w3c.dom.Node; import org.w3c.dom.NodeList; +import org.apache.xml.security.exceptions.XMLSecurityException; +import org.apache.xml.security.c14n.Canonicalizer; + import nokogiri.internals.NokogiriHelpers; import nokogiri.internals.NokogiriNamespaceCache; import nokogiri.internals.SaveContextVisitor; import nokogiri.internals.XmlDomParserContext; -import nokogiri.internals.c14n.CanonicalFilter; -import nokogiri.internals.c14n.CanonicalizationException; -import nokogiri.internals.c14n.Canonicalizer; /** * Class for Nokogiri::XML::Document @@ -673,15 +674,14 @@ private static class DocumentBuilderFactoryHolder try { Canonicalizer canonicalizer = Canonicalizer.getInstance(algorithmURI); XmlNode startingNode = getStartingNode(block); - byte[] result; - CanonicalFilter filter = new CanonicalFilter(context, block); + ByteArrayOutputStream writer = new ByteArrayOutputStream(); if (inclusive_namespace == null) { - result = canonicalizer.canonicalizeSubtree(startingNode.getNode(), filter); + canonicalizer.canonicalizeSubtree(startingNode.getNode(), writer); } else { - result = canonicalizer.canonicalizeSubtree(startingNode.getNode(), inclusive_namespace, filter); + canonicalizer.canonicalizeSubtree(startingNode.getNode(), inclusive_namespace, writer); } - return RubyString.newString(context.runtime, new ByteList(result, UTF8Encoding.INSTANCE)); - } catch (Exception e) { + return RubyString.newString(context.runtime, writer.toString()); + } catch (XMLSecurityException e) { throw context.getRuntime().newRuntimeError(e.getMessage()); } } diff --git a/ext/java/nokogiri/internals/c14n/AttrCompare.java b/ext/java/nokogiri/internals/c14n/AttrCompare.java deleted file mode 100644 index ed34b536dd..0000000000 --- a/ext/java/nokogiri/internals/c14n/AttrCompare.java +++ /dev/null @@ -1,122 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.Serializable; -import java.util.Comparator; - - -import org.w3c.dom.Attr; - -/** - * Compares two attributes based on the C14n specification. - * - * - * - * @author Christian Geuer-Pollmann - */ -public class AttrCompare implements Comparator, Serializable -{ - - private static final long serialVersionUID = -7113259629930576230L; - private static final int ATTR0_BEFORE_ATTR1 = -1; - private static final int ATTR1_BEFORE_ATTR0 = 1; - private static final String XMLNS = Constants.NamespaceSpecNS; - - /** - * Compares two attributes based on the C14n specification. - * - * - * - * @param attr0 - * @param attr1 - * @return returns a negative integer, zero, or a positive integer as - * obj0 is less than, equal to, or greater than obj1 - * - */ - public int - compare(Attr attr0, Attr attr1) - { - String namespaceURI0 = attr0.getNamespaceURI(); - String namespaceURI1 = attr1.getNamespaceURI(); - - boolean isNamespaceAttr0 = XMLNS.equals(namespaceURI0); - boolean isNamespaceAttr1 = XMLNS.equals(namespaceURI1); - - if (isNamespaceAttr0) { - if (isNamespaceAttr1) { - // both are namespaces - String localname0 = attr0.getLocalName(); - String localname1 = attr1.getLocalName(); - - if ("xmlns".equals(localname0)) { - localname0 = ""; - } - - if ("xmlns".equals(localname1)) { - localname1 = ""; - } - - return localname0.compareTo(localname1); - } - // attr0 is a namespace, attr1 is not - return ATTR0_BEFORE_ATTR1; - } else if (isNamespaceAttr1) { - // attr1 is a namespace, attr0 is not - return ATTR1_BEFORE_ATTR0; - } - - // none is a namespace - if (namespaceURI0 == null) { - if (namespaceURI1 == null) { - String name0 = attr0.getName(); - String name1 = attr1.getName(); - return name0.compareTo(name1); - } - return ATTR0_BEFORE_ATTR1; - } else if (namespaceURI1 == null) { - return ATTR1_BEFORE_ATTR0; - } - - int a = namespaceURI0.compareTo(namespaceURI1); - if (a != 0) { - return a; - } - - return (attr0.getLocalName()).compareTo(attr1.getLocalName()); - } -} diff --git a/ext/java/nokogiri/internals/c14n/C14nHelper.java b/ext/java/nokogiri/internals/c14n/C14nHelper.java deleted file mode 100644 index 4a3d842dd9..0000000000 --- a/ext/java/nokogiri/internals/c14n/C14nHelper.java +++ /dev/null @@ -1,178 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Document; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; - -/** - * Temporary swapped static functions from the normalizer Section - * - * @author Christian Geuer-Pollmann - */ -public class C14nHelper -{ - - /** - * Constructor C14nHelper - * - */ - private - C14nHelper() - { - // don't allow instantiation - } - - /** - * Method namespaceIsRelative - * - * @param namespace - * @return true if the given namespace is relative. - */ - public static boolean - namespaceIsRelative(Attr namespace) - { - return !namespaceIsAbsolute(namespace); - } - - /** - * Method namespaceIsRelative - * - * @param namespaceValue - * @return true if the given namespace is relative. - */ - public static boolean - namespaceIsRelative(String namespaceValue) - { - return !namespaceIsAbsolute(namespaceValue); - } - - /** - * Method namespaceIsAbsolute - * - * @param namespace - * @return true if the given namespace is absolute. - */ - public static boolean - namespaceIsAbsolute(Attr namespace) - { - return namespaceIsAbsolute(namespace.getValue()); - } - - /** - * Method namespaceIsAbsolute - * - * @param namespaceValue - * @return true if the given namespace is absolute. - */ - public static boolean - namespaceIsAbsolute(String namespaceValue) - { - // assume empty namespaces are absolute - if (namespaceValue.length() == 0) { - return true; - } - return namespaceValue.indexOf(':') > 0; - } - - /** - * This method throws an exception if the Attribute value contains - * a relative URI. - * - * @param attr - * @throws CanonicalizationException - */ - public static void - assertNotRelativeNS(Attr attr) throws CanonicalizationException - { - if (attr == null) { - return; - } - - String nodeAttrName = attr.getNodeName(); - boolean definesDefaultNS = nodeAttrName.equals("xmlns"); - boolean definesNonDefaultNS = nodeAttrName.startsWith("xmlns:"); - - if ((definesDefaultNS || definesNonDefaultNS) && namespaceIsRelative(attr)) { - String parentName = attr.getOwnerElement().getTagName(); - String attrValue = attr.getValue(); - Object exArgs[] = { parentName, nodeAttrName, attrValue }; - - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - - /** - * This method throws a CanonicalizationException if the supplied Document - * is not able to be traversed using a TreeWalker. - * - * @param document - * @throws CanonicalizationException - */ - public static void - checkTraversability(Document document) - throws CanonicalizationException - { - if (!document.isSupported("Traversal", "2.0")) { - Object exArgs[] = {document.getImplementation().getClass().getName() }; - - throw new CanonicalizationException( - "c14n.Canonicalizer.TraversalNotSupported", exArgs - ); - } - } - - /** - * This method throws a CanonicalizationException if the supplied Element - * contains any relative namespaces. - * - * @param ctxNode - * @throws CanonicalizationException - * @see C14nHelper#assertNotRelativeNS(Attr) - */ - public static void - checkForRelativeNamespace(Element ctxNode) - throws CanonicalizationException - { - if (ctxNode != null) { - NamedNodeMap attributes = ctxNode.getAttributes(); - - for (int i = 0; i < attributes.getLength(); i++) { - C14nHelper.assertNotRelativeNS((Attr) attributes.item(i)); - } - } else { - throw new CanonicalizationException("Called checkForRelativeNamespace() on null"); - } - } - - public static String - getErrorMessage(String message, Object... exArgs) - { - StringBuffer sb = new StringBuffer(message); - for (Object arg : exArgs) { - sb.append(", ").append(arg.toString()); - } - return new String(sb); - } -} diff --git a/ext/java/nokogiri/internals/c14n/CanonicalFilter.java b/ext/java/nokogiri/internals/c14n/CanonicalFilter.java deleted file mode 100644 index 5717f646f6..0000000000 --- a/ext/java/nokogiri/internals/c14n/CanonicalFilter.java +++ /dev/null @@ -1,43 +0,0 @@ -package nokogiri.internals.c14n; - -import nokogiri.XmlNode; -import nokogiri.internals.NokogiriHelpers; - -import org.jruby.runtime.Block; -import org.jruby.runtime.ThreadContext; -import org.jruby.runtime.builtin.IRubyObject; -import org.w3c.dom.Node; - -public class CanonicalFilter -{ - private final Block block; - private final ThreadContext context; - - public - CanonicalFilter(ThreadContext context, Block block) - { - this.context = context; - this.block = block; - } - - public boolean - includeNodes(Node currentNode, Node parentNode) - { - if (block == null || !block.isGiven()) { - return true; - } - - IRubyObject current = NokogiriHelpers.getCachedNodeOrCreate(context.getRuntime(), currentNode); - IRubyObject parent = NokogiriHelpers.getCachedNodeOrCreate(context.getRuntime(), parentNode); - - if (parent.isNil()) { - IRubyObject doc = ((XmlNode) current).document(context); - boolean returnValue = block.call(context, current, doc).isTrue(); - block.call(context, doc, context.nil); - return returnValue; - } - - return block.call(context, current, parent).isTrue(); - } - -} diff --git a/ext/java/nokogiri/internals/c14n/CanonicalizationException.java b/ext/java/nokogiri/internals/c14n/CanonicalizationException.java deleted file mode 100644 index bd0329cd95..0000000000 --- a/ext/java/nokogiri/internals/c14n/CanonicalizationException.java +++ /dev/null @@ -1,106 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * Class CanonicalizationException - * - * @author Christian Geuer-Pollmann - */ -public class CanonicalizationException extends Exception -{ - - /** - * - */ - private static final long serialVersionUID = 1L; - - /** - * Constructor CanonicalizationException - * - */ - public - CanonicalizationException() - { - super(); - } - - /** - * Constructor CanonicalizationException - * - * @param message - */ - public - CanonicalizationException(String message) - { - super(message); - } - - /** - * Constructor CanonicalizationException - * - * @param message - * @param rootCause - */ - public - CanonicalizationException(Exception rootCause) - { - super(rootCause); - } - - /** - * Constructor CanonicalizationException - * - * @param msgID - * @param exArgs - */ - public - CanonicalizationException(String message, Object... exArgs) - { - super(C14nHelper.getErrorMessage(message, exArgs)); - } - - /** - * Constructor CanonicalizationException - * - * @param message - * @param rootCause - */ - public - CanonicalizationException(String message, Exception rootCause) - { - super(message, rootCause); - } - - /** - * Constructor CanonicalizationException - * - * @param msgID - * @param exArgs - * @param originalException - */ - public - CanonicalizationException(String message, Exception rootCause, Object... exArgs) - { - super(C14nHelper.getErrorMessage(message, exArgs), rootCause); - } - - -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer.java b/ext/java/nokogiri/internals/c14n/Canonicalizer.java deleted file mode 100644 index b3e301cd8b..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer.java +++ /dev/null @@ -1,278 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.OutputStream; -import java.util.Map; -import java.util.concurrent.ConcurrentHashMap; - -import org.w3c.dom.Node; - -/** - * - * @author Christian Geuer-Pollmann - */ -public class Canonicalizer -{ - - /** The output encoding of canonicalized data */ - public static final String ENCODING = "UTF8"; - - /** - * XPath Expression for selecting every node and continuous comments joined - * in only one node - */ - public static final String XPATH_C14N_WITH_COMMENTS_SINGLE_NODE = - "(.//. | .//@* | .//namespace::*)"; - - /** - * The URL defined in XML-SEC Rec for inclusive c14n without comments. - */ - public static final String ALGO_ID_C14N_OMIT_COMMENTS = - "http://www.w3.org/TR/2001/REC-xml-c14n-20010315"; - /** - * The URL defined in XML-SEC Rec for inclusive c14n with comments. - */ - public static final String ALGO_ID_C14N_WITH_COMMENTS = - ALGO_ID_C14N_OMIT_COMMENTS + "#WithComments"; - /** - * The URL defined in XML-SEC Rec for exclusive c14n without comments. - */ - public static final String ALGO_ID_C14N_EXCL_OMIT_COMMENTS = - "http://www.w3.org/2001/10/xml-exc-c14n#"; - /** - * The URL defined in XML-SEC Rec for exclusive c14n with comments. - */ - public static final String ALGO_ID_C14N_EXCL_WITH_COMMENTS = - ALGO_ID_C14N_EXCL_OMIT_COMMENTS + "WithComments"; - /** - * The URI for inclusive c14n 1.1 without comments. - */ - public static final String ALGO_ID_C14N11_OMIT_COMMENTS = - "http://www.w3.org/2006/12/xml-c14n11"; - /** - * The URI for inclusive c14n 1.1 with comments. - */ - public static final String ALGO_ID_C14N11_WITH_COMMENTS = - ALGO_ID_C14N11_OMIT_COMMENTS + "#WithComments"; - /** - * Non-standard algorithm to serialize the physical representation for XML Encryption - */ - public static final String ALGO_ID_C14N_PHYSICAL = - "http://santuario.apache.org/c14n/physical"; - - private static Map> canonicalizerHash = null; - - private final CanonicalizerSpi canonicalizerSpi; - - /** - * Constructor Canonicalizer - * - * @param algorithmURI - * @throws InvalidCanonicalizerException - */ - @SuppressWarnings("deprecation") - private - Canonicalizer(String algorithmURI) throws CanonicalizationException - { - try { - Class implementingClass = - canonicalizerHash.get(algorithmURI); - - canonicalizerSpi = implementingClass.newInstance(); - canonicalizerSpi.reset = true; - } catch (Exception e) { - Object exArgs[] = { algorithmURI }; - throw new CanonicalizationException( - "signature.Canonicalizer.UnknownCanonicalizer", exArgs, e - ); - } - } - - /** - * Method getInstance - * - * @param algorithmURI - * @return a Canonicalizer instance ready for the job - * @throws InvalidCanonicalizerException - */ - public static final Canonicalizer - getInstance(String algorithmURI) - throws CanonicalizationException - { - if (canonicalizerHash == null) { - canonicalizerHash = new ConcurrentHashMap>(); - Canonicalizer.registerDefaultAlgorithms(); - } - return new Canonicalizer(algorithmURI); - } - - /** - * Method register - * - * @param algorithmURI - * @param implementingClass - * @throws CanonicalizationException - */ - @SuppressWarnings("unchecked") - public static void - register(String algorithmURI, String implementingClass) - throws CanonicalizationException, ClassNotFoundException - { - // check whether URI is already registered - Class registeredClass = - canonicalizerHash.get(algorithmURI); - - if (registeredClass != null) { - Object exArgs[] = { algorithmURI, registeredClass }; - throw new CanonicalizationException("algorithm.alreadyRegistered", exArgs); - } - - canonicalizerHash.put( - algorithmURI, (Class)Class.forName(implementingClass) - ); - } - - /** - * Method register - * - * @param algorithmURI - * @param implementingClass - * @throws CanonicalizationException - */ - public static void - register(String algorithmURI, Class implementingClass) - throws CanonicalizationException - { - // check whether URI is already registered - Class registeredClass = canonicalizerHash.get(algorithmURI); - - if (registeredClass != null) { - Object exArgs[] = { algorithmURI, registeredClass }; - throw new CanonicalizationException("algorithm.alreadyRegistered", exArgs); - } - - canonicalizerHash.put(algorithmURI, implementingClass); - } - - /** - * This method registers the default algorithms. - */ - private static void - registerDefaultAlgorithms() - { - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N_OMIT_COMMENTS, - Canonicalizer20010315OmitComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N_WITH_COMMENTS, - Canonicalizer20010315WithComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N_EXCL_OMIT_COMMENTS, - Canonicalizer20010315ExclOmitComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N_EXCL_WITH_COMMENTS, - Canonicalizer20010315ExclWithComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N11_OMIT_COMMENTS, - Canonicalizer11_OmitComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N11_WITH_COMMENTS, - Canonicalizer11_WithComments.class); - canonicalizerHash.put(Canonicalizer.ALGO_ID_C14N_PHYSICAL, - CanonicalizerPhysical.class); - } - - /** - * Method getURI - * - * @return the URI defined for this c14n instance. - */ - public final String - getURI() - { - return canonicalizerSpi.engineGetURI(); - } - - /** - * Method getIncludeComments - * - * @return true if the c14n respect the comments. - */ - public boolean - getIncludeComments() - { - return canonicalizerSpi.engineGetIncludeComments(); - } - - /** - * Canonicalizes the subtree rooted by node. - * - * @param node The node to canonicalize - * @return the result of the c14n. - * - * @throws CanonicalizationException - */ - public byte[] - canonicalizeSubtree(Node node, CanonicalFilter filter) throws CanonicalizationException - { - return canonicalizerSpi.engineCanonicalizeSubTree(node, filter); - } - - /** - * Canonicalizes the subtree rooted by node. - * - * @param node - * @param inclusiveNamespaces - * @return the result of the c14n. - * @throws CanonicalizationException - */ - public byte[] - canonicalizeSubtree(Node node, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException - { - return canonicalizerSpi.engineCanonicalizeSubTree(node, inclusiveNamespaces, filter); - } - - /** - * Sets the writer where the canonicalization ends. ByteArrayOutputStream - * if none is set. - * @param os - */ - public void - setWriter(OutputStream os) - { - canonicalizerSpi.setWriter(os); - } - - /** - * Returns the name of the implementing {@link CanonicalizerSpi} class - * - * @return the name of the implementing {@link CanonicalizerSpi} class - */ - public String - getImplementingCanonicalizerClass() - { - return canonicalizerSpi.getClass().getName(); - } - - /** - * Set the canonicalizer behaviour to not reset. - */ - public void - notReset() - { - canonicalizerSpi.reset = false; - } - -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer11.java b/ext/java/nokogiri/internals/c14n/Canonicalizer11.java deleted file mode 100644 index 324770c785..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer11.java +++ /dev/null @@ -1,664 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.net.URI; -import java.net.URISyntaxException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.SortedSet; -import java.util.TreeSet; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; - -/** - * Implements - * Canonical XML Version 1.1, a W3C Proposed Recommendation from 29 - * January 2008. - * - * @author Sean Mullan - * @author Raul Benito - */ -public abstract class Canonicalizer11 extends CanonicalizerBase -{ - - private static final String XMLNS_URI = Constants.NamespaceSpecNS; - private static final String XML_LANG_URI = Constants.XML_LANG_SPACE_SpecNS; - private final SortedSet result = new TreeSet(COMPARE); - - private boolean firstCall = true; - - private static class XmlAttrStack - { - static class XmlsStackElement - { - int level; - boolean rendered = false; - List nodes = new ArrayList(); - } - - int currentLevel = 0; - int lastlevel = 0; - XmlsStackElement cur; - List levels = new ArrayList(); - - void - push(int level) - { - currentLevel = level; - if (currentLevel == -1) { - return; - } - cur = null; - while (lastlevel >= currentLevel) { - levels.remove(levels.size() - 1); - int newSize = levels.size(); - if (newSize == 0) { - lastlevel = 0; - return; - } - lastlevel = (levels.get(newSize - 1)).level; - } - } - - void - addXmlnsAttr(Attr n) - { - if (cur == null) { - cur = new XmlsStackElement(); - cur.level = currentLevel; - levels.add(cur); - lastlevel = currentLevel; - } - cur.nodes.add(n); - } - - void - getXmlnsAttr(Collection col) throws CanonicalizationException - { - int size = levels.size() - 1; - if (cur == null) { - cur = new XmlsStackElement(); - cur.level = currentLevel; - lastlevel = currentLevel; - levels.add(cur); - } - boolean parentRendered = false; - if (size == -1) { - parentRendered = true; - } else { - XmlsStackElement e = levels.get(size); - if (e.rendered && e.level + 1 == currentLevel) { - parentRendered = true; - } - } - if (parentRendered) { - col.addAll(cur.nodes); - cur.rendered = true; - return; - } - - Map loa = new HashMap(); - List baseAttrs = new ArrayList(); - boolean successiveOmitted = true; - for (; size >= 0; size--) { - XmlsStackElement e = levels.get(size); - if (e.rendered) { - successiveOmitted = false; - } - Iterator it = e.nodes.iterator(); - while (it.hasNext() && successiveOmitted) { - Attr n = it.next(); - if (n.getLocalName().equals("base") && !e.rendered) { - baseAttrs.add(n); - } else if (!loa.containsKey(n.getName())) { - loa.put(n.getName(), n); - } - } - } - if (!baseAttrs.isEmpty()) { - Iterator it = col.iterator(); - String base = null; - Attr baseAttr = null; - while (it.hasNext()) { - Attr n = it.next(); - if (n.getLocalName().equals("base")) { - base = n.getValue(); - baseAttr = n; - break; - } - } - it = baseAttrs.iterator(); - while (it.hasNext()) { - Attr n = it.next(); - if (base == null) { - base = n.getValue(); - baseAttr = n; - } else { - try { - base = joinURI(n.getValue(), base); - } catch (URISyntaxException e1) { - throw new CanonicalizationException(e1); - } - } - } - if (base != null && base.length() != 0) { - baseAttr.setValue(base); - col.add(baseAttr); - } - } - - cur.rendered = true; - col.addAll(loa.values()); - } - } - - private final XmlAttrStack xmlattrStack = new XmlAttrStack(); - - /** - * Constructor Canonicalizer11 - * - * @param includeComments - */ - public - Canonicalizer11(boolean includeComments) - { - super(includeComments); - } - - /** - * Always throws a CanonicalizationException because this is inclusive c14n. - * - * @param rootNode - * @param inclusiveNamespaces - * @return none it always fails - * @throws CanonicalizationException - */ - public byte[] - engineCanonicalizeSubTree( - Node rootNode, String inclusiveNamespaces, CanonicalFilter filter - ) throws CanonicalizationException - { - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - /** - * Returns the Attr[]s to be output for the given element. - *
- * The code of this method is a copy of {@link #handleAttributes(Element, - * NameSpaceSymbTable)}, - * whereas it takes into account that subtree-c14n is -- well -- - * subtree-based. - * So if the element in question isRoot of c14n, it's parent is not in the - * node set, as well as all other ancestors. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - * @throws URISyntaxException - */ - @Override - protected Iterator - handleAttributesSubtree(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - if (!element.hasAttributes() && !firstCall) { - return null; - } - // result will contain the attrs which have to be output - final SortedSet result = this.result; - result.clear(); - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NUri = attribute.getNamespaceURI(); - String NName = attribute.getLocalName(); - String NValue = attribute.getValue(); - - if (!XMLNS_URI.equals(NUri)) { - // It's not a namespace attr node. Add to the result and continue. - result.add(attribute); - } else if (!(XML.equals(NName) && XML_LANG_URI.equals(NValue))) { - // The default mapping for xml must not be output. - Node n = ns.addMappingAndRender(NName, NValue, attribute); - - if (n != null) { - // Render the ns definition - result.add((Attr)n); - if (C14nHelper.namespaceIsRelative(attribute)) { - Object exArgs[] = {element.getTagName(), NName, attribute.getNodeValue()}; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - } - } - - if (firstCall) { - // It is the first node of the subtree - // Obtain all the namespaces defined in the parents, and added to the output. - ns.getUnrenderedNodes(result); - // output the attributes in the xml namespace. - xmlattrStack.getXmlnsAttr(result); - firstCall = false; - } - - return result.iterator(); - } - - /** - * Returns the Attr[]s to be output for the given element. - *
- * IMPORTANT: This method expects to work on a modified DOM tree, i.e. a - * DOM which has been prepared using - * {@link nokogiri.internals.c14n.security.utils.XMLUtils#circumventBug2650( - * org.w3c.dom.Document)}. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - */ - @Override - protected Iterator - handleAttributes(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - // result will contain the attrs which have to be output - xmlattrStack.push(ns.getLevel()); - boolean isRealVisible = isVisibleDO(element, ns.getLevel()) == 1; - final SortedSet result = this.result; - result.clear(); - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NUri = attribute.getNamespaceURI(); - String NName = attribute.getLocalName(); - String NValue = attribute.getValue(); - - if (!XMLNS_URI.equals(NUri)) { - //A non namespace definition node. - if (XML_LANG_URI.equals(NUri)) { - if (NName.equals("id")) { - if (isRealVisible) { - // treat xml:id like any other attribute - // (emit it, but don't inherit it) - result.add(attribute); - } - } else { - xmlattrStack.addXmlnsAttr(attribute); - } - } else if (isRealVisible) { - //The node is visible add the attribute to the list of output attributes. - result.add(attribute); - } - } else if (!XML.equals(NName) || !XML_LANG_URI.equals(NValue)) { - /* except omit namespace node with local name xml, which defines - * the xml prefix, if its string value is - * http://www.w3.org/XML/1998/namespace. - */ - // add the prefix binding to the ns symb table. - if (isVisible(attribute)) { - if (isRealVisible || !ns.removeMappingIfRender(NName)) { - // The xpath select this node output it if needed. - Node n = ns.addMappingAndRender(NName, NValue, attribute); - if (n != null) { - result.add((Attr)n); - if (C14nHelper.namespaceIsRelative(attribute)) { - Object exArgs[] = { element.getTagName(), NName, attribute.getNodeValue() }; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - } else { - if (isRealVisible && !XMLNS.equals(NName)) { - ns.removeMapping(NName); - } else { - ns.addMapping(NName, NValue, attribute); - } - } - } - } - } - - if (isRealVisible) { - //The element is visible, handle the xmlns definition - Attr xmlns = element.getAttributeNodeNS(XMLNS_URI, XMLNS); - Node n = null; - if (xmlns == null) { - //No xmlns def just get the already defined. - n = ns.getMapping(XMLNS); - } else if (!isVisible(xmlns)) { - //There is a definition but the xmlns is not selected by the xpath. - //then xmlns="" - n = ns.addMappingAndRender(XMLNS, "", nullNode); - } - //output the xmlns def if needed. - if (n != null) { - result.add((Attr)n); - } - //Float all xml:* attributes of the unselected parent elements to this one. - xmlattrStack.getXmlnsAttr(result); - ns.getUnrenderedNodes(result); - } - - return result.iterator(); - } - - @Override - protected void - handleParent(Element e, NameSpaceSymbTable ns) - { - if (!e.hasAttributes() && e.getNamespaceURI() == null) { - return; - } - xmlattrStack.push(-1); - NamedNodeMap attrs = e.getAttributes(); - int attrsLength = attrs.getLength(); - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NName = attribute.getLocalName(); - String NValue = attribute.getNodeValue(); - - if (Constants.NamespaceSpecNS.equals(attribute.getNamespaceURI())) { - if (!XML.equals(NName) || !Constants.XML_LANG_SPACE_SpecNS.equals(NValue)) { - ns.addMapping(NName, NValue, attribute); - } - } else if (!"id".equals(NName) && XML_LANG_URI.equals(attribute.getNamespaceURI())) { - xmlattrStack.addXmlnsAttr(attribute); - } - } - if (e.getNamespaceURI() != null) { - String NName = e.getPrefix(); - String NValue = e.getNamespaceURI(); - String Name; - if (NName == null || NName.equals("")) { - NName = "xmlns"; - Name = "xmlns"; - } else { - Name = "xmlns:" + NName; - } - Attr n = e.getOwnerDocument().createAttributeNS("http://www.w3.org/2000/xmlns/", Name); - n.setValue(NValue); - ns.addMapping(NName, NValue, n); - } - } - - private static String - joinURI(String baseURI, String relativeURI) throws URISyntaxException - { - String bscheme = null; - String bauthority = null; - String bpath = ""; - String bquery = null; - - // pre-parse the baseURI - if (baseURI != null) { - if (baseURI.endsWith("..")) { - baseURI = baseURI + "/"; - } - URI base = new URI(baseURI); - bscheme = base.getScheme(); - bauthority = base.getAuthority(); - bpath = base.getPath(); - bquery = base.getQuery(); - } - - URI r = new URI(relativeURI); - String rscheme = r.getScheme(); - String rauthority = r.getAuthority(); - String rpath = r.getPath(); - String rquery = r.getQuery(); - - String tscheme, tauthority, tpath, tquery; - if (rscheme != null && rscheme.equals(bscheme)) { - rscheme = null; - } - if (rscheme != null) { - tscheme = rscheme; - tauthority = rauthority; - tpath = removeDotSegments(rpath); - tquery = rquery; - } else { - if (rauthority != null) { - tauthority = rauthority; - tpath = removeDotSegments(rpath); - tquery = rquery; - } else { - if (rpath.length() == 0) { - tpath = bpath; - if (rquery != null) { - tquery = rquery; - } else { - tquery = bquery; - } - } else { - if (rpath.startsWith("/")) { - tpath = removeDotSegments(rpath); - } else { - if (bauthority != null && bpath.length() == 0) { - tpath = "/" + rpath; - } else { - int last = bpath.lastIndexOf('/'); - if (last == -1) { - tpath = rpath; - } else { - tpath = bpath.substring(0, last + 1) + rpath; - } - } - tpath = removeDotSegments(tpath); - } - tquery = rquery; - } - tauthority = bauthority; - } - tscheme = bscheme; - } - return new URI(tscheme, tauthority, tpath, tquery, null).toString(); - } - - private static String - removeDotSegments(String path) - { - - // 1. The input buffer is initialized with the now-appended path - // components then replace occurrences of "//" in the input buffer - // with "/" until no more occurrences of "//" are in the input buffer. - String input = path; - while (input.indexOf("//") > -1) { - input = input.replaceAll("//", "/"); - } - - // Initialize the output buffer with the empty string. - StringBuilder output = new StringBuilder(); - - // If the input buffer starts with a root slash "/" then move this - // character to the output buffer. - if (input.charAt(0) == '/') { - output.append('/'); - input = input.substring(1); - } - - printStep("1 ", output, input); - - // While the input buffer is not empty, loop as follows - while (input.length() != 0) { - // 2A. If the input buffer begins with a prefix of "./", - // then remove that prefix from the input buffer - // else if the input buffer begins with a prefix of "../", then - // if also the output does not contain the root slash "/" only, - // then move this prefix to the end of the output buffer else - // remove that prefix - if (input.startsWith("./")) { - input = input.substring(2); - printStep("2A", output, input); - } else if (input.startsWith("../")) { - input = input.substring(3); - if (!output.toString().equals("/")) { - output.append("../"); - } - printStep("2A", output, input); - // 2B. if the input buffer begins with a prefix of "/./" or "/.", - // where "." is a complete path segment, then replace that prefix - // with "/" in the input buffer; otherwise, - } else if (input.startsWith("/./")) { - input = input.substring(2); - printStep("2B", output, input); - } else if (input.equals("/.")) { - // FIXME: what is complete path segment? - input = input.replaceFirst("/.", "/"); - printStep("2B", output, input); - // 2C. if the input buffer begins with a prefix of "/../" or "/..", - // where ".." is a complete path segment, then replace that prefix - // with "/" in the input buffer and if also the output buffer is - // empty, last segment in the output buffer equals "../" or "..", - // where ".." is a complete path segment, then append ".." or "/.." - // for the latter case respectively to the output buffer else - // remove the last segment and its preceding "/" (if any) from the - // output buffer and if hereby the first character in the output - // buffer was removed and it was not the root slash then delete a - // leading slash from the input buffer; otherwise, - } else if (input.startsWith("/../")) { - input = input.substring(3); - if (output.length() == 0) { - output.append("/"); - } else if (output.toString().endsWith("../")) { - output.append(".."); - } else if (output.toString().endsWith("..")) { - output.append("/.."); - } else { - int index = output.lastIndexOf("/"); - if (index == -1) { - output = new StringBuilder(); - if (input.charAt(0) == '/') { - input = input.substring(1); - } - } else { - output = output.delete(index, output.length()); - } - } - printStep("2C", output, input); - } else if (input.equals("/..")) { - // FIXME: what is complete path segment? - input = input.replaceFirst("/..", "/"); - if (output.length() == 0) { - output.append("/"); - } else if (output.toString().endsWith("../")) { - output.append(".."); - } else if (output.toString().endsWith("..")) { - output.append("/.."); - } else { - int index = output.lastIndexOf("/"); - if (index == -1) { - output = new StringBuilder(); - if (input.charAt(0) == '/') { - input = input.substring(1); - } - } else { - output = output.delete(index, output.length()); - } - } - printStep("2C", output, input); - // 2D. if the input buffer consists only of ".", then remove - // that from the input buffer else if the input buffer consists - // only of ".." and if the output buffer does not contain only - // the root slash "/", then move the ".." to the output buffer - // else delte it.; otherwise, - } else if (input.equals(".")) { - input = ""; - printStep("2D", output, input); - } else if (input.equals("..")) { - if (!output.toString().equals("/")) { - output.append(".."); - } - input = ""; - printStep("2D", output, input); - // 2E. move the first path segment (if any) in the input buffer - // to the end of the output buffer, including the initial "/" - // character (if any) and any subsequent characters up to, but not - // including, the next "/" character or the end of the input buffer. - } else { - int end; - int begin = input.indexOf('/'); - if (begin == 0) { - end = input.indexOf('/', 1); - } else { - end = begin; - begin = 0; - } - String segment; - if (end == -1) { - segment = input.substring(begin); - input = ""; - } else { - segment = input.substring(begin, end); - input = input.substring(end); - } - output.append(segment); - printStep("2E", output, input); - } - } - - // 3. Finally, if the only or last segment of the output buffer is - // "..", where ".." is a complete path segment not followed by a slash - // then append a slash "/". The output buffer is returned as the result - // of remove_dot_segments - if (output.toString().endsWith("..")) { - output.append('/'); - printStep("3 ", output, input); - } - - return output.toString(); - } - - private static void - printStep(String step, StringBuilder output, String input) - { - //if (System.getProperty("nokogiri.c14.debug") == "on") { // - // System.out.println(" " + step + ": " + output); - // if (output.length() == 0) { - // System.out.println("\t\t\t\t" + input); - // } else { - // System.out.println("\t\t\t" + input); - // } - //} - } - -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer11_OmitComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer11_OmitComments.java deleted file mode 100644 index ce9f754775..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer11_OmitComments.java +++ /dev/null @@ -1,45 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * @author Sean Mullan - */ -public class Canonicalizer11_OmitComments extends Canonicalizer11 -{ - - public - Canonicalizer11_OmitComments() - { - super(false); - } - - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N11_OMIT_COMMENTS; - } - - public final boolean - engineGetIncludeComments() - { - return false; - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer11_WithComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer11_WithComments.java deleted file mode 100644 index ca80d6f554..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer11_WithComments.java +++ /dev/null @@ -1,45 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * @author Sean Mullan - */ -public class Canonicalizer11_WithComments extends Canonicalizer11 -{ - - public - Canonicalizer11_WithComments() - { - super(true); - } - - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N11_WITH_COMMENTS; - } - - public final boolean - engineGetIncludeComments() - { - return true; - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315.java deleted file mode 100644 index bf095e8747..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315.java +++ /dev/null @@ -1,388 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.ArrayList; -import java.util.Collection; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; - -/** - * Implements Canonical - * XML Version 1.0, a W3C Recommendation from 15 March 2001. - * - * @author Christian Geuer-Pollmann - */ -public abstract class Canonicalizer20010315 extends CanonicalizerBase -{ - private static final String XMLNS_URI = Constants.NamespaceSpecNS; - private static final String XML_LANG_URI = Constants.XML_LANG_SPACE_SpecNS; - - private boolean firstCall = true; - private final SortedSet result = new TreeSet(COMPARE); - - private static class XmlAttrStack - { - static class XmlsStackElement - { - int level; - boolean rendered = false; - List nodes = new ArrayList(); - } - - int currentLevel = 0; - int lastlevel = 0; - XmlsStackElement cur; - List levels = new ArrayList(); - - void - push(int level) - { - currentLevel = level; - if (currentLevel == -1) { - return; - } - cur = null; - while (lastlevel >= currentLevel) { - levels.remove(levels.size() - 1); - int newSize = levels.size(); - if (newSize == 0) { - lastlevel = 0; - return; - } - lastlevel = (levels.get(newSize - 1)).level; - } - } - - void - addXmlnsAttr(Attr n) - { - if (cur == null) { - cur = new XmlsStackElement(); - cur.level = currentLevel; - levels.add(cur); - lastlevel = currentLevel; - } - cur.nodes.add(n); - } - - void - getXmlnsAttr(Collection col) - { - int size = levels.size() - 1; - if (cur == null) { - cur = new XmlsStackElement(); - cur.level = currentLevel; - lastlevel = currentLevel; - levels.add(cur); - } - boolean parentRendered = false; - if (size == -1) { - parentRendered = true; - } else { - XmlsStackElement e = levels.get(size); - if (e.rendered && e.level + 1 == currentLevel) { - parentRendered = true; - } - } - if (parentRendered) { - col.addAll(cur.nodes); - cur.rendered = true; - return; - } - - Map loa = new HashMap(); - for (; size >= 0; size--) { - XmlsStackElement e = levels.get(size); - Iterator it = e.nodes.iterator(); - while (it.hasNext()) { - Attr n = it.next(); - if (!loa.containsKey(n.getName())) { - loa.put(n.getName(), n); - } - } - } - - cur.rendered = true; - col.addAll(loa.values()); - } - - } - - private final XmlAttrStack xmlattrStack = new XmlAttrStack(); - - /** - * Constructor Canonicalizer20010315 - * - * @param includeComments - */ - public - Canonicalizer20010315(boolean includeComments) - { - super(includeComments); - } - - /** - * Always throws a CanonicalizationException because this is inclusive c14n. - * - * @param xpathNodeSet - * @param inclusiveNamespaces - * @return none it always fails - * @throws CanonicalizationException always - */ - public byte[] - engineCanonicalizeXPathNodeSet(Set xpathNodeSet, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException - { - - /** $todo$ well, should we throw UnsupportedOperationException ? */ - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - /** - * Always throws a CanonicalizationException because this is inclusive c14n. - * - * @param rootNode - * @param inclusiveNamespaces - * @return none it always fails - * @throws CanonicalizationException - */ - @Override - public byte[] - engineCanonicalizeSubTree(Node rootNode, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException - { - - /** $todo$ well, should we throw UnsupportedOperationException ? */ - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - /** - * Returns the Attr[]s to be output for the given element. - *
- * The code of this method is a copy of {@link #handleAttributes(Element, - * NameSpaceSymbTable)}, - * whereas it takes into account that subtree-c14n is -- well -- subtree-based. - * So if the element in question isRoot of c14n, it's parent is not in the - * node set, as well as all other ancestors. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - */ - @Override - protected Iterator - handleAttributesSubtree(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - if (!element.hasAttributes() && !firstCall) { - return null; - } - // result will contain the attrs which have to be output - final SortedSet result = this.result; - result.clear(); - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NUri = attribute.getNamespaceURI(); - String NName = attribute.getLocalName(); - String NValue = attribute.getValue(); - - if (!XMLNS_URI.equals(NUri)) { - //It's not a namespace attr node. Add to the result and continue. - result.add(attribute); - } else if (!(XML.equals(NName) && XML_LANG_URI.equals(NValue))) { - //The default mapping for xml must not be output. - Node n = ns.addMappingAndRender(NName, NValue, attribute); - - if (n != null) { - //Render the ns definition - result.add((Attr)n); - if (C14nHelper.namespaceIsRelative(attribute)) { - Object exArgs[] = { element.getTagName(), NName, attribute.getNodeValue() }; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - } - } - - if (firstCall) { - //It is the first node of the subtree - //Obtain all the namespaces defined in the parents, and added to the output. - ns.getUnrenderedNodes(result); - //output the attributes in the xml namespace. - xmlattrStack.getXmlnsAttr(result); - firstCall = false; - } - - return result.iterator(); - } - - /** - * Returns the Attr[]s to be output for the given element. - *
- * IMPORTANT: This method expects to work on a modified DOM tree, i.e. a DOM which has - * been prepared using {@link nokogiri.internals.c14n.security.utils.XMLUtils#circumventBug2650( - * org.w3c.dom.Document)}. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - */ - @Override - protected Iterator - handleAttributes(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - // result will contain the attrs which have to be output - xmlattrStack.push(ns.getLevel()); - boolean isRealVisible = isVisibleDO(element, ns.getLevel()) == 1; - final SortedSet result = this.result; - result.clear(); - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NUri = attribute.getNamespaceURI(); - String NName = attribute.getLocalName(); - String NValue = attribute.getValue(); - - if (!XMLNS_URI.equals(NUri)) { - //A non namespace definition node. - if (XML_LANG_URI.equals(NUri)) { - xmlattrStack.addXmlnsAttr(attribute); - } else if (isRealVisible) { - //The node is visible add the attribute to the list of output attributes. - result.add(attribute); - } - } else if (!XML.equals(NName) || !XML_LANG_URI.equals(NValue)) { - /* except omit namespace node with local name xml, which defines - * the xml prefix, if its string value is http://www.w3.org/XML/1998/namespace. - */ - //add the prefix binding to the ns symb table. - if (isVisible(attribute)) { - if (isRealVisible || !ns.removeMappingIfRender(NName)) { - //The xpath select this node output it if needed. - Node n = ns.addMappingAndRender(NName, NValue, attribute); - if (n != null) { - result.add((Attr)n); - if (C14nHelper.namespaceIsRelative(attribute)) { - Object exArgs[] = { element.getTagName(), NName, attribute.getNodeValue() }; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - } else { - if (isRealVisible && !XMLNS.equals(NName)) { - ns.removeMapping(NName); - } else { - ns.addMapping(NName, NValue, attribute); - } - } - } - } - } - if (isRealVisible) { - //The element is visible, handle the xmlns definition - Attr xmlns = element.getAttributeNodeNS(XMLNS_URI, XMLNS); - Node n = null; - if (xmlns == null) { - //No xmlns def just get the already defined. - n = ns.getMapping(XMLNS); - } else if (!isVisible(xmlns)) { - //There is a definition but the xmlns is not selected by the xpath. - //then xmlns="" - n = ns.addMappingAndRender(XMLNS, "", nullNode); - } - //output the xmlns def if needed. - if (n != null) { - result.add((Attr)n); - } - //Float all xml:* attributes of the unselected parent elements to this one. - xmlattrStack.getXmlnsAttr(result); - ns.getUnrenderedNodes(result); - } - - return result.iterator(); - } - - @Override - protected void - handleParent(Element e, NameSpaceSymbTable ns) - { - if (!e.hasAttributes() && e.getNamespaceURI() == null) { - return; - } - xmlattrStack.push(-1); - NamedNodeMap attrs = e.getAttributes(); - int attrsLength = attrs.getLength(); - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NName = attribute.getLocalName(); - String NValue = attribute.getNodeValue(); - - if (Constants.NamespaceSpecNS.equals(attribute.getNamespaceURI())) { - if (!XML.equals(NName) || !Constants.XML_LANG_SPACE_SpecNS.equals(NValue)) { - ns.addMapping(NName, NValue, attribute); - } - } else if (XML_LANG_URI.equals(attribute.getNamespaceURI())) { - xmlattrStack.addXmlnsAttr(attribute); - } - } - if (e.getNamespaceURI() != null) { - String NName = e.getPrefix(); - String NValue = e.getNamespaceURI(); - String Name; - if (NName == null || NName.equals("")) { - NName = "xmlns"; - Name = "xmlns"; - } else { - Name = "xmlns:" + NName; - } - Attr n = e.getOwnerDocument().createAttributeNS("http://www.w3.org/2000/xmlns/", Name); - n.setValue(NValue); - ns.addMapping(NName, NValue, n); - } - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315Excl.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315Excl.java deleted file mode 100644 index f9e7cf7f5b..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315Excl.java +++ /dev/null @@ -1,308 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.Iterator; -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; - -/** - * Implements " Exclusive XML - * Canonicalization, Version 1.0 "
- * Credits: During restructuring of the Canonicalizer framework, Ren?? - * Kollmorgen from Software AG submitted an implementation of ExclC14n which - * fitted into the old architecture and which based heavily on my old (and slow) - * implementation of "Canonical XML". A big "thank you" to Ren?? for this. - *
- * THIS implementation is a complete rewrite of the algorithm. - * - * @author Christian Geuer-Pollmann - * @version $Revision: 1147448 $ - * @see - * XML Canonicalization, Version 1.0 - */ -public abstract class Canonicalizer20010315Excl extends CanonicalizerBase -{ - - private static final String XML_LANG_URI = Constants.XML_LANG_SPACE_SpecNS; - private static final String XMLNS_URI = Constants.NamespaceSpecNS; - - /** - * This Set contains the names (Strings like "xmlns" or "xmlns:foo") of - * the inclusive namespaces. - */ - private SortedSet inclusiveNSSet; - - private final SortedSet result = new TreeSet(COMPARE); - - /** - * Constructor Canonicalizer20010315Excl - * - * @param includeComments - */ - public - Canonicalizer20010315Excl(boolean includeComments) - { - super(includeComments); - } - - /** - * Method engineCanonicalizeSubTree - * @inheritDoc - * @param rootNode - * - * @throws CanonicalizationException - */ - @Override - public byte[] - engineCanonicalizeSubTree(Node rootNode, CanonicalFilter filter) - throws CanonicalizationException - { - return engineCanonicalizeSubTree(rootNode, "", null); - } - - /** - * Method engineCanonicalizeSubTree - * @inheritDoc - * @param rootNode - * @param inclusiveNamespaces - * - * @throws CanonicalizationException - */ - @Override - public byte[] - engineCanonicalizeSubTree( - Node rootNode, String inclusiveNamespaces, CanonicalFilter filter - ) throws CanonicalizationException - { - return engineCanonicalizeSubTree(rootNode, inclusiveNamespaces, null, filter); - } - - /** - * Method engineCanonicalizeSubTree - * @param rootNode - * @param inclusiveNamespaces - * @param excl A element to exclude from the c14n process. - * @return the rootNode c14n. - * @throws CanonicalizationException - */ - public byte[] - engineCanonicalizeSubTree( - Node rootNode, String inclusiveNamespaces, Node excl, CanonicalFilter filter - ) throws CanonicalizationException - { - inclusiveNSSet = InclusiveNamespaces.prefixStr2Set(inclusiveNamespaces); - return super.engineCanonicalizeSubTree(rootNode, excl, filter); - } - - @Override - protected Iterator - handleAttributesSubtree(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - // result will contain the attrs which have to be output - final SortedSet result = this.result; - result.clear(); - - // The prefix visibly utilized (in the attribute or in the name) in - // the element - SortedSet visiblyUtilized = new TreeSet(); - if (inclusiveNSSet != null && !inclusiveNSSet.isEmpty()) { - visiblyUtilized.addAll(inclusiveNSSet); - } - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NName = attribute.getLocalName(); - String NNodeValue = attribute.getNodeValue(); - - if (!XMLNS_URI.equals(attribute.getNamespaceURI())) { - // Not a namespace definition. - // The Element is output element, add the prefix (if used) to - // visiblyUtilized - String prefix = attribute.getPrefix(); - if (prefix != null && !(prefix.equals(XML) || prefix.equals(XMLNS))) { - visiblyUtilized.add(prefix); - } - // Add to the result. - result.add(attribute); - } else if (!(XML.equals(NName) && XML_LANG_URI.equals(NNodeValue)) - && ns.addMapping(NName, NNodeValue, attribute) - && C14nHelper.namespaceIsRelative(NNodeValue)) { - // The default mapping for xml must not be output. - // New definition check if it is relative. - Object exArgs[] = {element.getTagName(), NName, attribute.getNodeValue()}; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - String prefix; - if (element.getNamespaceURI() != null - && !(element.getPrefix() == null || element.getPrefix().length() == 0)) { - prefix = element.getPrefix(); - } else { - prefix = XMLNS; - } - visiblyUtilized.add(prefix); - - for (String s : visiblyUtilized) { - Attr key = ns.getMapping(s); - if (key != null) { - result.add(key); - } - } - - return result.iterator(); - } - - /** - * @inheritDoc - * @param element - * @throws CanonicalizationException - */ - @Override - protected final Iterator - handleAttributes(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - // result will contain the attrs which have to be output - final SortedSet result = this.result; - result.clear(); - - // The prefix visibly utilized (in the attribute or in the name) in - // the element - Set visiblyUtilized = null; - // It's the output selected. - boolean isOutputElement = isVisibleDO(element, ns.getLevel()) == 1; - if (isOutputElement) { - visiblyUtilized = new TreeSet(); - if (inclusiveNSSet != null && !inclusiveNSSet.isEmpty()) { - visiblyUtilized.addAll(inclusiveNSSet); - } - } - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - - String NName = attribute.getLocalName(); - String NNodeValue = attribute.getNodeValue(); - - if (!XMLNS_URI.equals(attribute.getNamespaceURI())) { - if (isVisible(attribute) && isOutputElement) { - // The Element is output element, add the prefix (if used) - // to visibyUtilized - String prefix = attribute.getPrefix(); - if (prefix != null && !(prefix.equals(XML) || prefix.equals(XMLNS))) { - visiblyUtilized.add(prefix); - } - // Add to the result. - result.add(attribute); - } - } else if (isOutputElement && !isVisible(attribute) && !XMLNS.equals(NName)) { - ns.removeMappingIfNotRender(NName); - } else { - if (!isOutputElement && isVisible(attribute) - && inclusiveNSSet.contains(NName) - && !ns.removeMappingIfRender(NName)) { - Node n = ns.addMappingAndRender(NName, NNodeValue, attribute); - if (n != null) { - result.add((Attr)n); - if (C14nHelper.namespaceIsRelative(attribute)) { - Object exArgs[] = { element.getTagName(), NName, attribute.getNodeValue() }; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - - if (ns.addMapping(NName, NNodeValue, attribute) - && C14nHelper.namespaceIsRelative(NNodeValue)) { - // New definition check if it is relative - Object exArgs[] = { element.getTagName(), NName, attribute.getNodeValue() }; - throw new CanonicalizationException( - "c14n.Canonicalizer.RelativeNamespace", exArgs - ); - } - } - } - } - - if (isOutputElement) { - // The element is visible, handle the xmlns definition - Attr xmlns = element.getAttributeNodeNS(XMLNS_URI, XMLNS); - if (xmlns != null && !isVisible(xmlns)) { - // There is a definition but the xmlns is not selected by the - // xpath. then xmlns="" - ns.addMapping(XMLNS, "", nullNode); - } - - String prefix; - if (element.getNamespaceURI() != null - && !(element.getPrefix() == null || element.getPrefix().length() == 0)) { - prefix = element.getPrefix(); - } else { - prefix = XMLNS; - } - visiblyUtilized.add(prefix); - - for (String s : visiblyUtilized) { - Attr key = ns.getMapping(s); - if (key != null) { - result.add(key); - } - } - } - - return result.iterator(); - } - - /* - protected void circumventBugIfNeeded(XMLSignatureInput input) - throws CanonicalizationException, ParserConfigurationException, - IOException, SAXException { - if (!input.isNeedsToBeExpanded() || inclusiveNSSet.isEmpty() || inclusiveNSSet.isEmpty()) { - return; - } - Document doc = null; - if (input.getSubNode() != null) { - doc = XMLUtils.getOwnerDocument(input.getSubNode()); - } else { - doc = XMLUtils.getOwnerDocument(input.getNodeSet()); - } - XMLUtils.circumventBug2650(doc); - } - */ -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclOmitComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclOmitComments.java deleted file mode 100644 index f53be05d35..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclOmitComments.java +++ /dev/null @@ -1,47 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -public class Canonicalizer20010315ExclOmitComments extends Canonicalizer20010315Excl -{ - - /** - * - */ - public - Canonicalizer20010315ExclOmitComments() - { - super(false); - } - - /** @inheritDoc */ - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N_EXCL_OMIT_COMMENTS; - } - - /** @inheritDoc */ - public final boolean - engineGetIncludeComments() - { - return false; - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclWithComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclWithComments.java deleted file mode 100644 index 22e175b717..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclWithComments.java +++ /dev/null @@ -1,51 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * Class Canonicalizer20010315ExclWithComments - */ -public class Canonicalizer20010315ExclWithComments extends Canonicalizer20010315Excl -{ - - /** - * Constructor Canonicalizer20010315ExclWithComments - * - */ - public - Canonicalizer20010315ExclWithComments() - { - super(true); - } - - /** @inheritDoc */ - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N_EXCL_WITH_COMMENTS; - } - - /** @inheritDoc */ - public final boolean - engineGetIncludeComments() - { - return true; - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315OmitComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315OmitComments.java deleted file mode 100644 index f8585c9680..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315OmitComments.java +++ /dev/null @@ -1,51 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * @author Christian Geuer-Pollmann - */ -public class Canonicalizer20010315OmitComments extends Canonicalizer20010315 -{ - - /** - * Constructor Canonicalizer20010315WithXPathOmitComments - * - */ - public - Canonicalizer20010315OmitComments() - { - super(false); - } - - /** @inheritDoc */ - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N_OMIT_COMMENTS; - } - - /** @inheritDoc */ - public final boolean - engineGetIncludeComments() - { - return false; - } -} diff --git a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315WithComments.java b/ext/java/nokogiri/internals/c14n/Canonicalizer20010315WithComments.java deleted file mode 100644 index 6104ab5de4..0000000000 --- a/ext/java/nokogiri/internals/c14n/Canonicalizer20010315WithComments.java +++ /dev/null @@ -1,50 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -/** - * @author Christian Geuer-Pollmann - */ -public class Canonicalizer20010315WithComments extends Canonicalizer20010315 -{ - - /** - * Constructor Canonicalizer20010315WithXPathWithComments - */ - public - Canonicalizer20010315WithComments() - { - super(true); - } - - /** @inheritDoc */ - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N_WITH_COMMENTS; - } - - /** @inheritDoc */ - public final boolean - engineGetIncludeComments() - { - return true; - } -} diff --git a/ext/java/nokogiri/internals/c14n/CanonicalizerBase.java b/ext/java/nokogiri/internals/c14n/CanonicalizerBase.java deleted file mode 100644 index 7a81f428f5..0000000000 --- a/ext/java/nokogiri/internals/c14n/CanonicalizerBase.java +++ /dev/null @@ -1,660 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.OutputStream; -import java.io.UnsupportedEncodingException; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.ListIterator; -import java.util.Map; -import java.util.Set; - -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Comment; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.w3c.dom.ProcessingInstruction; - -/** - * Abstract base class for canonicalization algorithms. - * - * @author Christian Geuer-Pollmann - */ -public abstract class CanonicalizerBase extends CanonicalizerSpi -{ - public static final String XML = "xml"; - public static final String XMLNS = "xmlns"; - - protected static final AttrCompare COMPARE = new AttrCompare(); - protected static final Attr nullNode; - - private static final byte[] END_PI = {'?', '>'}; - private static final byte[] BEGIN_PI = {'<', '?'}; - private static final byte[] END_COMM = {'-', '-', '>'}; - private static final byte[] BEGIN_COMM = {'<', '!', '-', '-'}; - private static final byte[] XA = {'&', '#', 'x', 'A', ';'}; - private static final byte[] X9 = {'&', '#', 'x', '9', ';'}; - private static final byte[] QUOT = {'&', 'q', 'u', 'o', 't', ';'}; - private static final byte[] XD = {'&', '#', 'x', 'D', ';'}; - private static final byte[] GT = {'&', 'g', 't', ';'}; - private static final byte[] LT = {'&', 'l', 't', ';'}; - private static final byte[] END_TAG = {'<', '/'}; - private static final byte[] AMP = {'&', 'a', 'm', 'p', ';'}; - private static final byte[] equalsStr = {'=', '\"'}; - - protected static final int NODE_BEFORE_DOCUMENT_ELEMENT = -1; - protected static final int NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT = 0; - protected static final int NODE_AFTER_DOCUMENT_ELEMENT = 1; - - static - { - // The null xmlns definition. - try { - DocumentBuilder documentBuilder = DocumentBuilderFactory.newInstance().newDocumentBuilder(); - nullNode = documentBuilder.newDocument().createAttributeNS(Constants.NamespaceSpecNS, XMLNS); - nullNode.setValue(""); - } catch (Exception e) { - throw new RuntimeException("Unable to create nullNode: " + e); - } - } - - private List nodeFilter; - - private final boolean includeComments; - //private Set xpathNodeSet; - /** - * The node to be skipped/excluded from the DOM tree - * in subtree canonicalizations. - */ - private Node excludeNode; - private OutputStream writer = new ByteArrayOutputStream(); - - /** - * Constructor CanonicalizerBase - * - * @param includeComments - */ - public - CanonicalizerBase(boolean includeComments) - { - this.includeComments = includeComments; - } - - /** - * Method engineCanonicalizeSubTree - * @inheritDoc - * @param rootNode - * @throws CanonicalizationException - */ - @Override - public byte[] - engineCanonicalizeSubTree(Node rootNode, CanonicalFilter filter) - throws CanonicalizationException - { - return engineCanonicalizeSubTree(rootNode, (Node)null, filter); - } - - /** - * @param writer The writer to set. - */ - @Override - public void - setWriter(OutputStream writer) - { - this.writer = writer; - } - - /** - * Canonicalizes a Subtree node. - * - * @param rootNode - * the root of the subtree to canonicalize - * @param excludeNode - * a node to be excluded from the canonicalize operation - * @return The canonicalize stream. - * @throws CanonicalizationException - */ - protected byte[] - engineCanonicalizeSubTree(Node rootNode, Node excludeNode, CanonicalFilter filter) - throws CanonicalizationException - { - this.excludeNode = excludeNode; - try { - NameSpaceSymbTable ns = new NameSpaceSymbTable(); - int nodeLevel = NODE_BEFORE_DOCUMENT_ELEMENT; - if (rootNode != null && Node.ELEMENT_NODE == rootNode.getNodeType()) { - //Fills the nssymbtable with the definitions of the parent of the root subnode - getParentNameSpaces((Element)rootNode, ns); - nodeLevel = NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT; - } - this.canonicalizeSubTree(rootNode, ns, rootNode, nodeLevel, filter); - this.writer.flush(); - if (this.writer instanceof ByteArrayOutputStream) { - byte[] result = ((ByteArrayOutputStream)this.writer).toByteArray(); - if (reset) { - ((ByteArrayOutputStream)this.writer).reset(); - } else { - this.writer.close(); - } - return result; - } else { - this.writer.close(); - } - return null; - - } catch (UnsupportedEncodingException ex) { - throw new CanonicalizationException("empty", ex); - } catch (IOException ex) { - throw new CanonicalizationException("empty", ex); - } - } - - - /** - * Method canonicalizeSubTree, this function is a recursive one. - * - * @param currentNode - * @param ns - * @param endnode - * @throws CanonicalizationException - * @throws IOException - */ - protected final void - canonicalizeSubTree( - Node currentNode, NameSpaceSymbTable ns, Node endnode, int documentLevel, CanonicalFilter filter - ) throws CanonicalizationException, IOException - { - if (isVisibleInt(currentNode) == -1) { - return; - } - Node sibling = null; - Node parentNode = null; - final OutputStream writer = this.writer; - final Node excludeNode = this.excludeNode; - final boolean includeComments = this.includeComments; - Map cache = new HashMap(); - do { - switch (currentNode.getNodeType()) { - - case Node.ENTITY_NODE : - case Node.NOTATION_NODE : - case Node.ATTRIBUTE_NODE : - // illegal node type during traversal - throw new CanonicalizationException("empty"); - - case Node.DOCUMENT_FRAGMENT_NODE : - case Node.DOCUMENT_NODE : - ns.outputNodePush(); - sibling = currentNode.getFirstChild(); - break; - - case Node.COMMENT_NODE : - if (includeComments) { - outputCommentToWriter((Comment) currentNode, writer, documentLevel); - } - break; - - case Node.PROCESSING_INSTRUCTION_NODE : - outputPItoWriter((ProcessingInstruction) currentNode, writer, documentLevel); - break; - - case Node.TEXT_NODE : - case Node.CDATA_SECTION_NODE : - outputTextToWriter(currentNode.getNodeValue(), writer); - break; - - case Node.ELEMENT_NODE : - documentLevel = NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT; - if (currentNode == excludeNode) { - break; - } - if (filter != null && !filter.includeNodes(currentNode, parentNode)) { - break; - } - - Element currentElement = (Element)currentNode; - //Add a level to the nssymbtable. So latter can be pop-back. - ns.outputNodePush(); - writer.write('<'); - String name = currentElement.getTagName(); - UtfHelpper.writeByte(name, writer, cache); - - Iterator attrs = this.handleAttributesSubtree(currentElement, ns); - if (attrs != null) { - //we output all Attrs which are available - while (attrs.hasNext()) { - Attr attr = attrs.next(); - outputAttrToWriter(attr.getNodeName(), attr.getNodeValue(), writer, cache); - } - } - writer.write('>'); - sibling = currentNode.getFirstChild(); - if (sibling == null) { - writer.write(END_TAG); - UtfHelpper.writeStringToUtf8(name, writer); - writer.write('>'); - //We finished with this level, pop to the previous definitions. - ns.outputNodePop(); - if (parentNode != null) { - sibling = currentNode.getNextSibling(); - } - } else { - parentNode = currentElement; - } - break; - case Node.DOCUMENT_TYPE_NODE : - default : - break; - } - while (sibling == null && parentNode != null) { - writer.write(END_TAG); - UtfHelpper.writeByte(((Element)parentNode).getTagName(), writer, cache); - writer.write('>'); - //We finished with this level, pop to the previous definitions. - ns.outputNodePop(); - if (parentNode == endnode) { - return; - } - sibling = parentNode.getNextSibling(); - parentNode = parentNode.getParentNode(); - if (parentNode == null || Node.ELEMENT_NODE != parentNode.getNodeType()) { - documentLevel = NODE_AFTER_DOCUMENT_ELEMENT; - parentNode = null; - } - } - if (sibling == null) { - return; - } - currentNode = sibling; - sibling = currentNode.getNextSibling(); - } while (true); - } - - protected int - isVisibleDO(Node currentNode, int level) - { - if (nodeFilter != null) { - Iterator it = nodeFilter.iterator(); - while (it.hasNext()) { - int i = (it.next()).isNodeIncludeDO(currentNode, level); - if (i != 1) { - return i; - } - } - } - //if ((this.xpathNodeSet != null) && !this.xpathNodeSet.contains(currentNode)) { - // return 0; - //} - return 1; - } - - protected int - isVisibleInt(Node currentNode) - { - if (nodeFilter != null) { - Iterator it = nodeFilter.iterator(); - while (it.hasNext()) { - int i = (it.next()).isNodeInclude(currentNode); - if (i != 1) { - return i; - } - } - } - //if ((this.xpathNodeSet != null) && !this.xpathNodeSet.contains(currentNode)) { - // return 0; - //} - return 1; - } - - protected boolean - isVisible(Node currentNode) - { - if (nodeFilter != null) { - Iterator it = nodeFilter.iterator(); - while (it.hasNext()) { - if (it.next().isNodeInclude(currentNode) != 1) { - return false; - } - } - } - //if ((this.xpathNodeSet != null) && !this.xpathNodeSet.contains(currentNode)) { - // return false; - //} - return true; - } - - protected void - handleParent(Element e, NameSpaceSymbTable ns) - { - if (!e.hasAttributes() && e.getNamespaceURI() == null) { - return; - } - NamedNodeMap attrs = e.getAttributes(); - int attrsLength = attrs.getLength(); - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - String NName = attribute.getLocalName(); - String NValue = attribute.getNodeValue(); - - if (Constants.NamespaceSpecNS.equals(attribute.getNamespaceURI()) - && (!XML.equals(NName) || !Constants.XML_LANG_SPACE_SpecNS.equals(NValue))) { - ns.addMapping(NName, NValue, attribute); - } - } - if (e.getNamespaceURI() != null) { - String NName = e.getPrefix(); - String NValue = e.getNamespaceURI(); - String Name; - if (NName == null || NName.equals("")) { - NName = XMLNS; - Name = XMLNS; - } else { - Name = XMLNS + ":" + NName; - } - Attr n = e.getOwnerDocument().createAttributeNS("http://www.w3.org/2000/xmlns/", Name); - n.setValue(NValue); - ns.addMapping(NName, NValue, n); - } - } - - /** - * Adds to ns the definitions from the parent elements of el - * @param el - * @param ns - */ - protected final void - getParentNameSpaces(Element el, NameSpaceSymbTable ns) - { - Node n1 = el.getParentNode(); - if (n1 == null || Node.ELEMENT_NODE != n1.getNodeType()) { - return; - } - //Obtain all the parents of the element - List parents = new ArrayList(); - Node parent = n1; - while (parent != null && Node.ELEMENT_NODE == parent.getNodeType()) { - parents.add((Element)parent); - parent = parent.getParentNode(); - } - //Visit them in reverse order. - ListIterator it = parents.listIterator(parents.size()); - while (it.hasPrevious()) { - Element ele = it.previous(); - handleParent(ele, ns); - } - parents.clear(); - Attr nsprefix; - if (((nsprefix = ns.getMappingWithoutRendered(XMLNS)) != null) - && "".equals(nsprefix.getValue())) { - ns.addMappingAndRender(XMLNS, "", nullNode); - } - } - - /** - * Obtain the attributes to output for this node in XPathNodeSet c14n. - * - * @param element - * @param ns - * @return the attributes nodes to output. - * @throws CanonicalizationException - */ - abstract Iterator handleAttributes(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException; - - /** - * Obtain the attributes to output for this node in a Subtree c14n. - * - * @param element - * @param ns - * @return the attributes nodes to output. - * @throws CanonicalizationException - */ - abstract Iterator handleAttributesSubtree(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException; - - //abstract void circumventBugIfNeeded(XMLSignatureInput input) - // throws CanonicalizationException, ParserConfigurationException, IOException, SAXException; - - /** - * Outputs an Attribute to the internal Writer. - * - * The string value of the node is modified by replacing - *
    - *
  • all ampersands (&) with &amp;
  • - *
  • all open angle brackets (<) with &lt;
  • - *
  • all quotation mark characters with &quot;
  • - *
  • and the whitespace characters #x9, #xA, and #xD, with character - * references. The character references are written in uppercase - * hexadecimal with no leading zeroes (for example, #xD is represented - * by the character reference &#xD;)
  • - *
- * - * @param name - * @param value - * @param writer - * @throws IOException - */ - protected static final void - outputAttrToWriter( - final String name, final String value, - final OutputStream writer, final Map cache - ) throws IOException - { - writer.write(' '); - UtfHelpper.writeByte(name, writer, cache); - writer.write(equalsStr); - byte[] toWrite; - final int length = value.length(); - int i = 0; - while (i < length) { - char c = value.charAt(i++); - - switch (c) { - - case '&' : - toWrite = AMP; - break; - - case '<' : - toWrite = LT; - break; - - case '"' : - toWrite = QUOT; - break; - - case 0x09 : // '\t' - toWrite = X9; - break; - - case 0x0A : // '\n' - toWrite = XA; - break; - - case 0x0D : // '\r' - toWrite = XD; - break; - - default : - if (c < 0x80) { - writer.write(c); - } else { - UtfHelpper.writeCharToUtf8(c, writer); - } - continue; - } - writer.write(toWrite); - } - - writer.write('\"'); - } - - /** - * Outputs a PI to the internal Writer. - * - * @param currentPI - * @param writer where to write the things - * @throws IOException - */ - protected void - outputPItoWriter( - ProcessingInstruction currentPI, OutputStream writer, int position - ) throws IOException - { - if (position == NODE_AFTER_DOCUMENT_ELEMENT) { - writer.write('\n'); - } - writer.write(BEGIN_PI); - - final String target = currentPI.getTarget(); - int length = target.length(); - - for (int i = 0; i < length; i++) { - char c = target.charAt(i); - if (c == 0x0D) { - writer.write(XD); - } else { - if (c < 0x80) { - writer.write(c); - } else { - UtfHelpper.writeCharToUtf8(c, writer); - } - } - } - - final String data = currentPI.getData(); - - length = data.length(); - - if (length > 0) { - writer.write(' '); - - for (int i = 0; i < length; i++) { - char c = data.charAt(i); - if (c == 0x0D) { - writer.write(XD); - } else { - UtfHelpper.writeCharToUtf8(c, writer); - } - } - } - - writer.write(END_PI); - if (position == NODE_BEFORE_DOCUMENT_ELEMENT) { - writer.write('\n'); - } - } - - /** - * Method outputCommentToWriter - * - * @param currentComment - * @param writer writer where to write the things - * @throws IOException - */ - protected void - outputCommentToWriter( - Comment currentComment, OutputStream writer, int position - ) throws IOException - { - if (position == NODE_AFTER_DOCUMENT_ELEMENT) { - writer.write('\n'); - } - writer.write(BEGIN_COMM); - - final String data = currentComment.getData(); - final int length = data.length(); - - for (int i = 0; i < length; i++) { - char c = data.charAt(i); - if (c == 0x0D) { - writer.write(XD); - } else { - if (c < 0x80) { - writer.write(c); - } else { - UtfHelpper.writeCharToUtf8(c, writer); - } - } - } - - writer.write(END_COMM); - if (position == NODE_BEFORE_DOCUMENT_ELEMENT) { - writer.write('\n'); - } - } - - /** - * Outputs a Text of CDATA section to the internal Writer. - * - * @param text - * @param writer writer where to write the things - * @throws IOException - */ - protected static final void - outputTextToWriter( - final String text, final OutputStream writer - ) throws IOException - { - final int length = text.length(); - byte[] toWrite; - for (int i = 0; i < length; i++) { - char c = text.charAt(i); - - switch (c) { - - case '&' : - toWrite = AMP; - break; - - case '<' : - toWrite = LT; - break; - - case '>' : - toWrite = GT; - break; - - case 0xD : - toWrite = XD; - break; - - default : - if (c < 0x80) { - writer.write(c); - } else { - UtfHelpper.writeCharToUtf8(c, writer); - } - continue; - } - writer.write(toWrite); - } - } - -} diff --git a/ext/java/nokogiri/internals/c14n/CanonicalizerPhysical.java b/ext/java/nokogiri/internals/c14n/CanonicalizerPhysical.java deleted file mode 100644 index 2f9a758b8c..0000000000 --- a/ext/java/nokogiri/internals/c14n/CanonicalizerPhysical.java +++ /dev/null @@ -1,194 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.IOException; -import java.io.OutputStream; -import java.util.Iterator; -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Comment; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.w3c.dom.ProcessingInstruction; - -/** - * Serializes the physical representation of the subtree. All the attributes - * present in the subtree are emitted. The attributes are sorted within an element, - * with the namespace declarations appearing before the regular attributes. - * This algorithm is not a true canonicalization since equivalent subtrees - * may produce different output. It is therefore unsuitable for digital signatures. - * This same property makes it ideal for XML Encryption Syntax and Processing, - * because the decrypted XML content will share the same physical representation - * as the original XML content that was encrypted. - */ -public class CanonicalizerPhysical extends CanonicalizerBase -{ - - private final SortedSet result = new TreeSet(COMPARE); - - /** - * Constructor Canonicalizer20010315 - */ - public - CanonicalizerPhysical() - { - super(true); - } - - /** - * Always throws a CanonicalizationException. - * - * @param xpathNodeSet - * @param inclusiveNamespaces - * @return none it always fails - * @throws CanonicalizationException always - */ - public byte[] - engineCanonicalizeXPathNodeSet(Set xpathNodeSet, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException - { - - /** $todo$ well, should we throw UnsupportedOperationException ? */ - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - /** - * Always throws a CanonicalizationException. - * - * @param rootNode - * @param inclusiveNamespaces - * @return none it always fails - * @throws CanonicalizationException - */ - @Override - public byte[] - engineCanonicalizeSubTree(Node rootNode, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException - { - - /** $todo$ well, should we throw UnsupportedOperationException ? */ - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - /** - * Returns the Attr[]s to be output for the given element. - *
- * The code of this method is a copy of {@link #handleAttributes(Element, - * NameSpaceSymbTable)}, - * whereas it takes into account that subtree-c14n is -- well -- subtree-based. - * So if the element in question isRoot of c14n, it's parent is not in the - * node set, as well as all other ancestors. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - */ - @Override - protected Iterator - handleAttributesSubtree(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - if (!element.hasAttributes()) { - return null; - } - - // result will contain all the attrs declared directly on that element - final SortedSet result = this.result; - result.clear(); - - if (element.hasAttributes()) { - NamedNodeMap attrs = element.getAttributes(); - int attrsLength = attrs.getLength(); - - for (int i = 0; i < attrsLength; i++) { - Attr attribute = (Attr) attrs.item(i); - result.add(attribute); - } - } - - return result.iterator(); - } - - /** - * Returns the Attr[]s to be output for the given element. - * - * @param element - * @param ns - * @return the Attr[]s to be output - * @throws CanonicalizationException - */ - @Override - protected Iterator - handleAttributes(Element element, NameSpaceSymbTable ns) - throws CanonicalizationException - { - - /** $todo$ well, should we throw UnsupportedOperationException ? */ - throw new CanonicalizationException("c14n.Canonicalizer.UnsupportedOperation"); - } - - @Override - protected void - handleParent(Element e, NameSpaceSymbTable ns) - { - // nothing to do - } - - /** @inheritDoc */ - @Override - public final String - engineGetURI() - { - return Canonicalizer.ALGO_ID_C14N_PHYSICAL; - } - - /** @inheritDoc */ - @Override - public final boolean - engineGetIncludeComments() - { - return true; - } - - @Override - protected void - outputPItoWriter(ProcessingInstruction currentPI, - OutputStream writer, int position) throws IOException - { - // Processing Instructions before or after the document element are not treated specially - super.outputPItoWriter(currentPI, writer, NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT); - } - - @Override - protected void - outputCommentToWriter(Comment currentComment, - OutputStream writer, int position) throws IOException - { - // Comments before or after the document element are not treated specially - super.outputCommentToWriter(currentComment, writer, NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT); - } - -} diff --git a/ext/java/nokogiri/internals/c14n/CanonicalizerSpi.java b/ext/java/nokogiri/internals/c14n/CanonicalizerSpi.java deleted file mode 100644 index db05ba198f..0000000000 --- a/ext/java/nokogiri/internals/c14n/CanonicalizerSpi.java +++ /dev/null @@ -1,77 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.OutputStream; - - -import org.w3c.dom.Node; - -/** - * Base class which all Canonicalization algorithms extend. - * - * @author Christian Geuer-Pollmann - */ -public abstract class CanonicalizerSpi -{ - - /** Reset the writer after a c14n */ - protected boolean reset = false; - - /** - * Returns the URI of this engine. - * @return the URI - */ - public abstract String engineGetURI(); - - /** - * Returns true if comments are included - * @return true if comments are included - */ - public abstract boolean engineGetIncludeComments(); - - /** - * C14n a node tree. - * - * @param rootNode - * @return the c14n bytes - * @throws CanonicalizationException - */ - public abstract byte[] engineCanonicalizeSubTree(Node rootNode, CanonicalFilter filter) - throws CanonicalizationException; - - /** - * C14n a node tree. - * - * @param rootNode - * @param inclusiveNamespaces - * @return the c14n bytes - * @throws CanonicalizationException - */ - public abstract byte[] engineCanonicalizeSubTree(Node rootNode, String inclusiveNamespaces, CanonicalFilter filter) - throws CanonicalizationException; - - /** - * Sets the writer where the canonicalization ends. ByteArrayOutputStream if - * none is set. - * @param os - */ - public abstract void setWriter(OutputStream os); - -} diff --git a/ext/java/nokogiri/internals/c14n/Constants.java b/ext/java/nokogiri/internals/c14n/Constants.java deleted file mode 100644 index 648c7f83cf..0000000000 --- a/ext/java/nokogiri/internals/c14n/Constants.java +++ /dev/null @@ -1,45 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -/** - * Provides all constants and some translation functions for i18n. - * - * For the used Algorithm identifiers and Namespaces, look at the - * XML - * Signature specification. - * - * @author $Author: coheigea $ - */ -public class Constants -{ - - /** The URI for XML spec*/ - public static final String XML_LANG_SPACE_SpecNS = "http://www.w3.org/XML/1998/namespace"; - - /** The URI for XMLNS spec*/ - public static final String NamespaceSpecNS = "http://www.w3.org/2000/xmlns/"; - - private - Constants() - { - // we don't allow instantiation - } - -} diff --git a/ext/java/nokogiri/internals/c14n/ElementProxy.java b/ext/java/nokogiri/internals/c14n/ElementProxy.java deleted file mode 100644 index 62cb077b77..0000000000 --- a/ext/java/nokogiri/internals/c14n/ElementProxy.java +++ /dev/null @@ -1,325 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.Map; -import java.util.concurrent.ConcurrentHashMap; - - -import org.w3c.dom.Document; -import org.w3c.dom.Element; -import org.w3c.dom.Node; -import org.w3c.dom.NodeList; -import org.w3c.dom.Text; - -/** - * This is the base class to all Objects which have a direct 1:1 mapping to an - * Element in a particular namespace. - */ -public abstract class ElementProxy -{ - - /** Field constructionElement */ - protected Element constructionElement = null; - - /** Field baseURI */ - protected String baseURI = null; - - /** Field doc */ - protected Document doc = null; - - /** Field prefixMappings */ - private static Map prefixMappings = new ConcurrentHashMap(); - - /** - * Constructor ElementProxy - * - */ - public - ElementProxy() - { - } - - /** - * Constructor ElementProxy - * - * @param doc - */ - public - ElementProxy(Document doc) - { - if (doc == null) { - throw new RuntimeException("Document is null"); - } - - this.doc = doc; - this.constructionElement = - createElementForFamilyLocal(this.doc, this.getBaseNamespace(), this.getBaseLocalName()); - } - - /** - * Constructor ElementProxy - * - * @param element - * @param BaseURI - * @throws XMLSecurityException - */ - public - ElementProxy(Element element, String BaseURI) throws CanonicalizationException - { - if (element == null) { - throw new CanonicalizationException("ElementProxy.nullElement"); - } - - //if (System.getProperty("nokogiri.c14.debug") == "on") { - // System.out.println("setElement(\"" + element.getTagName() + "\", \"" + BaseURI + "\")"); - //} - - this.doc = element.getOwnerDocument(); - this.constructionElement = element; - this.baseURI = BaseURI; - - this.guaranteeThatElementInCorrectSpace(); - } - - /** - * Returns the namespace of the Elements of the sub-class. - * - * @return the namespace of the Elements of the sub-class. - */ - public abstract String getBaseNamespace(); - - /** - * Returns the localname of the Elements of the sub-class. - * - * @return the localname of the Elements of the sub-class. - */ - public abstract String getBaseLocalName(); - - - protected Element - createElementForFamilyLocal( - Document doc, String namespace, String localName - ) - { - Element result; - if (namespace == null) { - result = doc.createElementNS(null, localName); - } else { - String baseName = this.getBaseNamespace(); - String prefix = ElementProxy.getDefaultPrefix(baseName); - if ((prefix == null) || (prefix.length() == 0)) { - result = doc.createElementNS(namespace, localName); - result.setAttributeNS(Constants.NamespaceSpecNS, "xmlns", namespace); - } else { - result = doc.createElementNS(namespace, prefix + ":" + localName); - result.setAttributeNS(Constants.NamespaceSpecNS, "xmlns:" + prefix, namespace); - } - } - return result; - } - - - /** - * This method creates an Element in a given namespace with a given localname. - * It uses the {@link ElementProxy#getDefaultPrefix} method to decide whether - * a particular prefix is bound to that namespace. - *
- * This method was refactored out of the constructor. - * - * @param doc - * @param namespace - * @param localName - * @return The element created. - */ - public static Element - createElementForFamily(Document doc, String namespace, String localName) - { - Element result; - String prefix = ElementProxy.getDefaultPrefix(namespace); - - if (namespace == null) { - result = doc.createElementNS(null, localName); - } else { - if ((prefix == null) || (prefix.length() == 0)) { - result = doc.createElementNS(namespace, localName); - result.setAttributeNS(Constants.NamespaceSpecNS, "xmlns", namespace); - } else { - result = doc.createElementNS(namespace, prefix + ":" + localName); - result.setAttributeNS(Constants.NamespaceSpecNS, "xmlns:" + prefix, namespace); - } - } - - return result; - } - - /** - * Returns the Element which was constructed by the Object. - * - * @return the Element which was constructed by the Object. - */ - public final Element - getElement() - { - return this.constructionElement; - } - - /** - * Returns the Element plus a leading and a trailing CarriageReturn Text node. - * - * @return the Element which was constructed by the Object. - */ - public final NodeList - getElementPlusReturns() - { - - HelperNodeList nl = new HelperNodeList(); - - nl.appendChild(this.doc.createTextNode("\n")); - nl.appendChild(this.getElement()); - nl.appendChild(this.doc.createTextNode("\n")); - - return nl; - } - - /** - * Method getDocument - * - * @return the Document where this element is contained. - */ - public Document - getDocument() - { - return this.doc; - } - - /** - * Method getBaseURI - * - * @return the base uri of the namespace of this element - */ - public String - getBaseURI() - { - return this.baseURI; - } - - /** - * Method guaranteeThatElementInCorrectSpace - * - * @throws XMLSecurityException - */ - void - guaranteeThatElementInCorrectSpace() throws CanonicalizationException - { - - String expectedLocalName = this.getBaseLocalName(); - String expectedNamespaceUri = this.getBaseNamespace(); - - String actualLocalName = this.constructionElement.getLocalName(); - String actualNamespaceUri = this.constructionElement.getNamespaceURI(); - - if (!expectedNamespaceUri.equals(actualNamespaceUri) - && !expectedLocalName.equals(actualLocalName)) { - Object exArgs[] = { actualNamespaceUri + ":" + actualLocalName, - expectedNamespaceUri + ":" + expectedLocalName - }; - throw new CanonicalizationException("xml.WrongElement", exArgs); - } - } - - /** - * Method addText - * - * @param text - */ - public void - addText(String text) - { - if (text != null) { - Text t = this.doc.createTextNode(text); - - this.constructionElement.appendChild(t); - } - } - - /** - * Method getTextFromChildElement - * - * @param localname - * @param namespace - * @return the Text of the textNode - */ - public String - getTextFromChildElement(String localname, String namespace) - { - return XMLUtils.selectNode( - this.constructionElement.getFirstChild(), - namespace, - localname, - 0).getTextContent(); - } - - /** - * Method getTextFromTextChild - * - * @return the Text obtained by concatenating all the text nodes of this - * element - */ - public String - getTextFromTextChild() - { - return XMLUtils.getFullTextChildrenFromElement(this.constructionElement); - } - - /** - * Method length - * - * @param namespace - * @param localname - * @return the number of elements {namespace}:localname under this element - */ - public int - length(String namespace, String localname) - { - int number = 0; - Node sibling = this.constructionElement.getFirstChild(); - while (sibling != null) { - if (localname.equals(sibling.getLocalName()) - && namespace.equals(sibling.getNamespaceURI())) { - number++; - } - sibling = sibling.getNextSibling(); - } - return number; - } - - /** - * Method getDefaultPrefix - * - * @param namespace - * @return the default prefix bind to this element. - */ - public static String - getDefaultPrefix(String namespace) - { - return prefixMappings.get(namespace); - } - -} diff --git a/ext/java/nokogiri/internals/c14n/HelperNodeList.java b/ext/java/nokogiri/internals/c14n/HelperNodeList.java deleted file mode 100644 index 5e84282ff5..0000000000 --- a/ext/java/nokogiri/internals/c14n/HelperNodeList.java +++ /dev/null @@ -1,106 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.ArrayList; -import java.util.List; -import org.w3c.dom.Document; -import org.w3c.dom.Node; -import org.w3c.dom.NodeList; - -/** - * @author Christian Geuer-Pollmann - */ -public class HelperNodeList implements NodeList -{ - - /** Field nodes */ - List nodes = new ArrayList(); - boolean allNodesMustHaveSameParent = false; - - /** - * - */ - public - HelperNodeList() - { - this(false); - } - - - /** - * @param allNodesMustHaveSameParent - */ - public - HelperNodeList(boolean allNodesMustHaveSameParent) - { - this.allNodesMustHaveSameParent = allNodesMustHaveSameParent; - } - - /** - * Method item - * - * @param index - * @return node with index i - */ - public Node - item(int index) - { - return nodes.get(index); - } - - /** - * Method getLength - * - * @return length of the list - */ - public int - getLength() - { - return nodes.size(); - } - - /** - * Method appendChild - * - * @param node - * @throws IllegalArgumentException - */ - public void - appendChild(Node node) throws IllegalArgumentException - { - if (this.allNodesMustHaveSameParent && this.getLength() > 0 - && this.item(0).getParentNode() != node.getParentNode()) { - throw new IllegalArgumentException("Nodes have not the same Parent"); - } - nodes.add(node); - } - - /** - * @return the document that contains this nodelist - */ - public Document - getOwnerDocument() - { - if (this.getLength() == 0) { - return null; - } - return XMLUtils.getOwnerDocument(this.item(0)); - } -} diff --git a/ext/java/nokogiri/internals/c14n/IgnoreAllErrorHandler.java b/ext/java/nokogiri/internals/c14n/IgnoreAllErrorHandler.java deleted file mode 100644 index 484dd95bae..0000000000 --- a/ext/java/nokogiri/internals/c14n/IgnoreAllErrorHandler.java +++ /dev/null @@ -1,86 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import org.xml.sax.ErrorHandler; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -/** - * This {@link org.xml.sax.ErrorHandler} does absolutely nothing but log - * the events. - * - * @author Christian Geuer-Pollmann - */ -public class IgnoreAllErrorHandler implements ErrorHandler -{ - - /** Field throwExceptions */ - private static final boolean warnOnExceptions = - System.getProperty("org.apache.xml.security.test.warn.on.exceptions", "false").equals("true"); - - /** Field throwExceptions */ - private static final boolean throwExceptions = - System.getProperty("org.apache.xml.security.test.throw.exceptions", "false").equals("true"); - - - /** @inheritDoc */ - public void - warning(SAXParseException ex) throws SAXException - { - if (IgnoreAllErrorHandler.warnOnExceptions) { - // TODO - // get handler from upper layer - //log.warn("", ex); - } - if (IgnoreAllErrorHandler.throwExceptions) { - throw ex; - } - } - - - /** @inheritDoc */ - public void - error(SAXParseException ex) throws SAXException - { - if (IgnoreAllErrorHandler.warnOnExceptions) { - // TODO - // get handler from upper layer - //log.error("", ex); - } - if (IgnoreAllErrorHandler.throwExceptions) { - throw ex; - } - } - - - /** @inheritDoc */ - public void - fatalError(SAXParseException ex) throws SAXException - { - if (IgnoreAllErrorHandler.warnOnExceptions) { - // TODO - // get handler from upper layer - //log.warn("", ex); - } - if (IgnoreAllErrorHandler.throwExceptions) { - throw ex; - } - } -} diff --git a/ext/java/nokogiri/internals/c14n/InclusiveNamespaces.java b/ext/java/nokogiri/internals/c14n/InclusiveNamespaces.java deleted file mode 100644 index c0a7c8a81e..0000000000 --- a/ext/java/nokogiri/internals/c14n/InclusiveNamespaces.java +++ /dev/null @@ -1,181 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; -//import nokogiri.internals.org.apache.xml.security.exceptions.XMLSecurityException; -//import nokogiri.internals.org.apache.xml.security.transforms.TransformParam; -import org.w3c.dom.Document; -import org.w3c.dom.Element; - -/** - * This Object serves as Content for the ds:Transforms for exclusive - * Canonicalization. - *
- * It implements the {@link Element} interface - * and can be used directly in a DOM tree. - * - * @author Christian Geuer-Pollmann - */ -//public class InclusiveNamespaces extends ElementProxy implements TransformParam { -public class InclusiveNamespaces extends ElementProxy -{ - - /** Field _TAG_EC_INCLUSIVENAMESPACES */ - public static final String _TAG_EC_INCLUSIVENAMESPACES = - "InclusiveNamespaces"; - - /** Field _ATT_EC_PREFIXLIST */ - public static final String _ATT_EC_PREFIXLIST = "PrefixList"; - - /** Field ExclusiveCanonicalizationNamespace */ - public static final String ExclusiveCanonicalizationNamespace = - "http://www.w3.org/2001/10/xml-exc-c14n#"; - - /** - * Constructor XPathContainer - * - * @param doc - * @param prefixList - */ - public - InclusiveNamespaces(Document doc, String prefixList) - { - this(doc, InclusiveNamespaces.prefixStr2Set(prefixList)); - } - - /** - * Constructor InclusiveNamespaces - * - * @param doc - * @param prefixes - */ - public - InclusiveNamespaces(Document doc, Set prefixes) - { - super(doc); - - SortedSet prefixList; - if (prefixes instanceof SortedSet) { - prefixList = (SortedSet)prefixes; - } else { - prefixList = new TreeSet(prefixes); - } - - StringBuilder sb = new StringBuilder(prefixList.size() * 8); - for (String prefix : prefixList) { - if (prefix.equals("xmlns")) { - sb.append("#default "); - } else { - sb.append(prefix).append(' '); - } - } - int last = sb.length() - 1; - while (last >= 0 && sb.charAt(last) == ' ') { sb.setLength(last--); } // trim - - this.constructionElement.setAttributeNS(null, InclusiveNamespaces._ATT_EC_PREFIXLIST, sb.toString()); - } - - /** - * Constructor InclusiveNamespaces - * - * @param element - * @param BaseURI - * @throws XMLSecurityException - */ - public - InclusiveNamespaces(Element element, String BaseURI) - throws CanonicalizationException - { - super(element, BaseURI); - } - - /** - * Method getInclusiveNamespaces - * - * @return The Inclusive Namespace string - */ - public String - getInclusiveNamespaces() - { - return this.constructionElement.getAttributeNS(null, InclusiveNamespaces._ATT_EC_PREFIXLIST); - } - - /** - * Decodes the inclusiveNamespaces String and returns all - * selected namespace prefixes as a Set. The #default - * namespace token is represented as an empty namespace prefix - * ("xmlns"). - *
- * The String inclusiveNamespaces=" xenc ds #default" - * is returned as a Set containing the following Strings: - *
    - *
  • xmlns
  • - *
  • xenc
  • - *
  • ds
  • - *
- * - * @param inclusiveNamespaces - * @return A set to string - */ - public static SortedSet - prefixStr2Set(String inclusiveNamespaces) - { - SortedSet prefixes = new TreeSet(); - - if ((inclusiveNamespaces == null) || (inclusiveNamespaces.length() == 0)) { - return prefixes; - } - - String[] tokens = inclusiveNamespaces.split("\\s"); - for (String prefix : tokens) { - if (prefix.equals("#default")) { - prefixes.add("xmlns"); - } else { - prefixes.add(prefix); - } - } - - return prefixes; - } - - /** - * Method getBaseNamespace - * - * @inheritDoc - */ - public String - getBaseNamespace() - { - return InclusiveNamespaces.ExclusiveCanonicalizationNamespace; - } - - /** - * Method getBaseLocalName - * - * @inheritDoc - */ - public String - getBaseLocalName() - { - return InclusiveNamespaces._TAG_EC_INCLUSIVENAMESPACES; - } -} diff --git a/ext/java/nokogiri/internals/c14n/InvalidCanonicalizerException.java b/ext/java/nokogiri/internals/c14n/InvalidCanonicalizerException.java deleted file mode 100644 index 210d9bd1fb..0000000000 --- a/ext/java/nokogiri/internals/c14n/InvalidCanonicalizerException.java +++ /dev/null @@ -1,87 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - - -public class InvalidCanonicalizerException extends Exception -{ - - /** - * - */ - private static final long serialVersionUID = 1L; - - /** - * Constructor InvalidCanonicalizerException - * - */ - public - InvalidCanonicalizerException() - { - super(); - } - - /** - * Constructor InvalidCanonicalizerException - * - * @param message - */ - public - InvalidCanonicalizerException(String message) - { - super(message); - } - - /** - * Constructor InvalidCanonicalizerException - * - * @param message - * @param exArgs - */ - public - InvalidCanonicalizerException(String message, Object... exArgs) - { - super(C14nHelper.getErrorMessage(message, exArgs)); - } - - /** - * Constructor InvalidCanonicalizerException - * - * @param msgID - * @param originalException - */ - public - InvalidCanonicalizerException(String message, Exception rootCause) - { - super(message, rootCause); - } - - /** - * Constructor InvalidCanonicalizerException - * - * @param msgID - * @param exArgs - * @param originalException - */ - public - InvalidCanonicalizerException(String message, Exception rootCause, Object... exArgs) - { - super(C14nHelper.getErrorMessage(message, exArgs), rootCause); - } -} diff --git a/ext/java/nokogiri/internals/c14n/NameSpaceSymbTable.java b/ext/java/nokogiri/internals/c14n/NameSpaceSymbTable.java deleted file mode 100644 index 3e1dc9a4a7..0000000000 --- a/ext/java/nokogiri/internals/c14n/NameSpaceSymbTable.java +++ /dev/null @@ -1,452 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.ArrayList; -import java.util.Collection; -import java.util.Iterator; -import java.util.List; -import org.w3c.dom.Attr; -import org.w3c.dom.Node; - -/** - * A stack based Symbol Table. - *
For speed reasons all the symbols are introduced in the same map, - * and at the same time in a list so it can be removed when the frame is pop back. - * @author Raul Benito - */ -public class NameSpaceSymbTable -{ - - private static final String XMLNS = "xmlns"; - private static final SymbMap initialMap = new SymbMap(); - - static - { - NameSpaceSymbEntry ne = new NameSpaceSymbEntry("", null, true, XMLNS); - ne.lastrendered = ""; - initialMap.put(XMLNS, ne); - } - - /**The map betwen prefix-> entry table. */ - private SymbMap symb; - - /**The stacks for removing the definitions when doing pop.*/ - private List level; - private boolean cloned = true; - - /** - * Default constractor - **/ - public - NameSpaceSymbTable() - { - level = new ArrayList(); - //Insert the default binding for xmlns. - symb = (SymbMap) initialMap.clone(); - } - - /** - * Get all the unrendered nodes in the name space. - * For Inclusive rendering - * @param result the list where to fill the unrendered xmlns definitions. - **/ - public void - getUnrenderedNodes(Collection result) - { - Iterator it = symb.entrySet().iterator(); - while (it.hasNext()) { - NameSpaceSymbEntry n = it.next(); - //put them rendered? - if ((!n.rendered) && (n.n != null)) { - n = (NameSpaceSymbEntry) n.clone(); - needsClone(); - symb.put(n.prefix, n); - n.lastrendered = n.uri; - n.rendered = true; - - result.add(n.n); - } - } - } - - /** - * Push a frame for visible namespace. - * For Inclusive rendering. - **/ - public void - outputNodePush() - { - push(); - } - - /** - * Pop a frame for visible namespace. - **/ - public void - outputNodePop() - { - pop(); - } - - /** - * Push a frame for a node. - * Inclusive or Exclusive. - **/ - public void - push() - { - //Put the number of namespace definitions in the stack. - level.add(null); - cloned = false; - } - - /** - * Pop a frame. - * Inclusive or Exclusive. - **/ - public void - pop() - { - int size = level.size() - 1; - Object ob = level.remove(size); - if (ob != null) { - symb = (SymbMap)ob; - if (size == 0) { - cloned = false; - } else { - cloned = (level.get(size - 1) != symb); - } - } else { - cloned = false; - } - } - - final void - needsClone() - { - if (!cloned) { - level.set(level.size() - 1, symb); - symb = (SymbMap) symb.clone(); - cloned = true; - } - } - - - /** - * Gets the attribute node that defines the binding for the prefix. - * @param prefix the prefix to obtain the attribute. - * @return null if there is no need to render the prefix. Otherwise the node of - * definition. - **/ - public Attr - getMapping(String prefix) - { - NameSpaceSymbEntry entry = symb.get(prefix); - if (entry == null) { - //There is no definition for the prefix(a bug?). - return null; - } - if (entry.rendered) { - //No need to render an entry already rendered. - return null; - } - // Mark this entry as render. - entry = (NameSpaceSymbEntry) entry.clone(); - needsClone(); - symb.put(prefix, entry); - entry.rendered = true; - entry.lastrendered = entry.uri; - // Return the node for outputing. - return entry.n; - } - - /** - * Gets a definition without mark it as render. - * For render in exclusive c14n the namespaces in the include prefixes. - * @param prefix The prefix whose definition is neaded. - * @return the attr to render, null if there is no need to render - **/ - public Attr - getMappingWithoutRendered(String prefix) - { - NameSpaceSymbEntry entry = symb.get(prefix); - if (entry == null) { - return null; - } - if (entry.rendered) { - return null; - } - return entry.n; - } - - /** - * Adds the mapping for a prefix. - * @param prefix the prefix of definition - * @param uri the Uri of the definition - * @param n the attribute that have the definition - * @return true if there is already defined. - **/ - public boolean - addMapping(String prefix, String uri, Attr n) - { - NameSpaceSymbEntry ob = symb.get(prefix); - if ((ob != null) && uri.equals(ob.uri)) { - //If we have it previously defined. Don't keep working. - return false; - } - //Creates and entry in the table for this new definition. - NameSpaceSymbEntry ne = new NameSpaceSymbEntry(uri, n, false, prefix); - needsClone(); - symb.put(prefix, ne); - if (ob != null) { - //We have a previous definition store it for the pop. - //Check if a previous definition(not the inmidiatly one) has been rendered. - ne.lastrendered = ob.lastrendered; - if ((ob.lastrendered != null) && (ob.lastrendered.equals(uri))) { - //Yes it is. Mark as rendered. - ne.rendered = true; - } - } - return true; - } - - /** - * Adds a definition and mark it as render. - * For inclusive c14n. - * @param prefix the prefix of definition - * @param uri the Uri of the definition - * @param n the attribute that have the definition - * @return the attr to render, null if there is no need to render - **/ - public Node - addMappingAndRender(String prefix, String uri, Attr n) - { - NameSpaceSymbEntry ob = symb.get(prefix); - - if ((ob != null) && uri.equals(ob.uri)) { - if (!ob.rendered) { - ob = (NameSpaceSymbEntry) ob.clone(); - needsClone(); - symb.put(prefix, ob); - ob.lastrendered = uri; - ob.rendered = true; - return ob.n; - } - return null; - } - - NameSpaceSymbEntry ne = new NameSpaceSymbEntry(uri, n, true, prefix); - ne.lastrendered = uri; - needsClone(); - symb.put(prefix, ne); - if ((ob != null) && (ob.lastrendered != null) && (ob.lastrendered.equals(uri))) { - ne.rendered = true; - return null; - } - return ne.n; - } - - public int - getLevel() - { - return level.size(); - } - - public void - removeMapping(String prefix) - { - NameSpaceSymbEntry ob = symb.get(prefix); - - if (ob != null) { - needsClone(); - symb.put(prefix, null); - } - } - - public void - removeMappingIfNotRender(String prefix) - { - NameSpaceSymbEntry ob = symb.get(prefix); - - if (ob != null && !ob.rendered) { - needsClone(); - symb.put(prefix, null); - } - } - - public boolean - removeMappingIfRender(String prefix) - { - NameSpaceSymbEntry ob = symb.get(prefix); - - if (ob != null && ob.rendered) { - needsClone(); - symb.put(prefix, null); - } - return false; - } -} - -/** - * The internal structure of NameSpaceSymbTable. - **/ -class NameSpaceSymbEntry implements Cloneable -{ - - String prefix; - - /**The URI that the prefix defines */ - String uri; - - /**The last output in the URI for this prefix (This for speed reason).*/ - String lastrendered = null; - - /**This prefix-URI has been already render or not.*/ - boolean rendered = false; - - /**The attribute to include.*/ - Attr n; - - NameSpaceSymbEntry(String name, Attr n, boolean rendered, String prefix) - { - this.uri = name; - this.rendered = rendered; - this.n = n; - this.prefix = prefix; - } - - /** @inheritDoc */ - public Object - clone() - { - try { - return super.clone(); - } catch (CloneNotSupportedException e) { - return null; - } - } -} - -class SymbMap implements Cloneable -{ - int free = 23; - NameSpaceSymbEntry[] entries; - String[] keys; - - SymbMap() - { - entries = new NameSpaceSymbEntry[free]; - keys = new String[free]; - } - - void - put(String key, NameSpaceSymbEntry value) - { - int index = index(key); - Object oldKey = keys[index]; - keys[index] = key; - entries[index] = value; - if ((oldKey == null || !oldKey.equals(key)) && (--free == 0)) { - free = entries.length; - int newCapacity = free << 2; - rehash(newCapacity); - } - } - - List - entrySet() - { - List a = new ArrayList(); - for (int i = 0; i < entries.length; i++) { - if ((entries[i] != null) && !("".equals(entries[i].uri))) { - a.add(entries[i]); - } - } - return a; - } - - protected int - index(Object obj) - { - Object[] set = keys; - int length = set.length; - //abs of index - int index = (obj.hashCode() & 0x7fffffff) % length; - Object cur = set[index]; - - if (cur == null || (cur.equals(obj))) { - return index; - } - length--; - do { - index = index == length ? 0 : ++index; - cur = set[index]; - } while (cur != null && (!cur.equals(obj))); - return index; - } - - /** - * rehashes the map to the new capacity. - * - * @param newCapacity an int value - */ - protected void - rehash(int newCapacity) - { - int oldCapacity = keys.length; - String oldKeys[] = keys; - NameSpaceSymbEntry oldVals[] = entries; - - keys = new String[newCapacity]; - entries = new NameSpaceSymbEntry[newCapacity]; - - for (int i = oldCapacity; i-- > 0;) { - if (oldKeys[i] != null) { - String o = oldKeys[i]; - int index = index(o); - keys[index] = o; - entries[index] = oldVals[i]; - } - } - } - - NameSpaceSymbEntry - get(String key) - { - return entries[index(key)]; - } - - protected Object - clone() - { - try { - SymbMap copy = (SymbMap) super.clone(); - copy.entries = new NameSpaceSymbEntry[entries.length]; - System.arraycopy(entries, 0, copy.entries, 0, entries.length); - copy.keys = new String[keys.length]; - System.arraycopy(keys, 0, copy.keys, 0, keys.length); - - return copy; - } catch (CloneNotSupportedException e) { - e.printStackTrace(); - } - return null; - } -} diff --git a/ext/java/nokogiri/internals/c14n/NodeFilter.java b/ext/java/nokogiri/internals/c14n/NodeFilter.java deleted file mode 100644 index 42f959de9f..0000000000 --- a/ext/java/nokogiri/internals/c14n/NodeFilter.java +++ /dev/null @@ -1,52 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import org.w3c.dom.Node; - -/** - * An interface to tell to the c14n if a node is included or not in the output - */ -public interface NodeFilter -{ - - /** - * Tells if a node must be output in c14n. - * @param n - * @return 1 if the node should be output. - * 0 if node must not be output, - * -1 if the node and all it's child must not be output. - * - */ - int isNodeInclude(Node n); - - /** - * Tells if a node must be output in a c14n. - * The caller must assured that this method is always call - * in document order. The implementations can use this - * restriction to optimize the transformation. - * @param n - * @param level the relative level in the tree - * @return 1 if the node should be output. - * 0 if node must not be output, - * -1 if the node and all it's child must not be output. - */ - int isNodeIncludeDO(Node n, int level); - -} diff --git a/ext/java/nokogiri/internals/c14n/UtfHelpper.java b/ext/java/nokogiri/internals/c14n/UtfHelpper.java deleted file mode 100644 index 40866507bf..0000000000 --- a/ext/java/nokogiri/internals/c14n/UtfHelpper.java +++ /dev/null @@ -1,190 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.io.IOException; -import java.io.OutputStream; -import java.util.Map; - -public final class UtfHelpper -{ - - private - UtfHelpper() - { - // complete - } - - public static void - writeByte( - final String str, - final OutputStream out, - Map cache - ) throws IOException - { - byte[] result = cache.get(str); - if (result == null) { - result = getStringInUtf8(str); - cache.put(str, result); - } - - out.write(result); - } - - public static void - writeCharToUtf8(final char c, final OutputStream out) throws IOException - { - if (c < 0x80) { - out.write(c); - return; - } - if ((c >= 0xD800 && c <= 0xDBFF) || (c >= 0xDC00 && c <= 0xDFFF)) { - //No Surrogates in sun java - out.write(0x3f); - return; - } - int bias; - int write; - char ch; - if (c > 0x07FF) { - ch = (char)(c >>> 12); - write = 0xE0; - if (ch > 0) { - write |= (ch & 0x0F); - } - out.write(write); - write = 0x80; - bias = 0x3F; - } else { - write = 0xC0; - bias = 0x1F; - } - ch = (char)(c >>> 6); - if (ch > 0) { - write |= (ch & bias); - } - out.write(write); - out.write(0x80 | ((c) & 0x3F)); - - } - - public static void - writeStringToUtf8( - final String str, - final OutputStream out - ) throws IOException - { - final int length = str.length(); - int i = 0; - char c; - while (i < length) { - c = str.charAt(i++); - if (c < 0x80) { - out.write(c); - continue; - } - if ((c >= 0xD800 && c <= 0xDBFF) || (c >= 0xDC00 && c <= 0xDFFF)) { - //No Surrogates in sun java - out.write(0x3f); - continue; - } - char ch; - int bias; - int write; - if (c > 0x07FF) { - ch = (char)(c >>> 12); - write = 0xE0; - if (ch > 0) { - write |= (ch & 0x0F); - } - out.write(write); - write = 0x80; - bias = 0x3F; - } else { - write = 0xC0; - bias = 0x1F; - } - ch = (char)(c >>> 6); - if (ch > 0) { - write |= (ch & bias); - } - out.write(write); - out.write(0x80 | ((c) & 0x3F)); - - } - - } - - public static byte[] - getStringInUtf8(final String str) - { - final int length = str.length(); - boolean expanded = false; - byte[] result = new byte[length]; - int i = 0; - int out = 0; - char c; - while (i < length) { - c = str.charAt(i++); - if (c < 0x80) { - result[out++] = (byte)c; - continue; - } - if ((c >= 0xD800 && c <= 0xDBFF) || (c >= 0xDC00 && c <= 0xDFFF)) { - //No Surrogates in sun java - result[out++] = 0x3f; - continue; - } - if (!expanded) { - byte newResult[] = new byte[3 * length]; - System.arraycopy(result, 0, newResult, 0, out); - result = newResult; - expanded = true; - } - char ch; - int bias; - byte write; - if (c > 0x07FF) { - ch = (char)(c >>> 12); - write = (byte)0xE0; - if (ch > 0) { - write |= (ch & 0x0F); - } - result[out++] = write; - write = (byte)0x80; - bias = 0x3F; - } else { - write = (byte)0xC0; - bias = 0x1F; - } - ch = (char)(c >>> 6); - if (ch > 0) { - write |= (ch & bias); - } - result[out++] = write; - result[out++] = (byte)(0x80 | ((c) & 0x3F)); - } - if (expanded) { - byte newResult[] = new byte[out]; - System.arraycopy(result, 0, newResult, 0, out); - result = newResult; - } - return result; - } -} diff --git a/ext/java/nokogiri/internals/c14n/XMLUtils.java b/ext/java/nokogiri/internals/c14n/XMLUtils.java deleted file mode 100644 index c29de56601..0000000000 --- a/ext/java/nokogiri/internals/c14n/XMLUtils.java +++ /dev/null @@ -1,540 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 nokogiri.internals.c14n; - -import java.util.ArrayList; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Set; - - -import org.w3c.dom.Attr; -import org.w3c.dom.Document; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.w3c.dom.NodeList; -import org.w3c.dom.ProcessingInstruction; -import org.w3c.dom.Text; - -/** - * DOM and XML accessibility and comfort functions. - * - * @author Christian Geuer-Pollmann - */ -public class XMLUtils -{ - - /** - * Constructor XMLUtils - * - */ - private - XMLUtils() - { - // we don't allow instantiation - } - - /** - * Method getFullTextChildrenFromElement - * - * @param element - * @return the string of children - */ - public static String - getFullTextChildrenFromElement(Element element) - { - StringBuilder sb = new StringBuilder(); - - Node child = element.getFirstChild(); - while (child != null) { - if (child.getNodeType() == Node.TEXT_NODE) { - sb.append(((Text)child).getData()); - } - child = child.getNextSibling(); - } - - return sb.toString(); - } - - /** - * This method returns the owner document of a particular node. - * This method is necessary because it always returns a - * {@link Document}. {@link Node#getOwnerDocument} returns null - * if the {@link Node} is a {@link Document}. - * - * @param node - * @return the owner document of the node - */ - public static Document - getOwnerDocument(Node node) - { - if (node.getNodeType() == Node.DOCUMENT_NODE) { - return (Document) node; - } - try { - return node.getOwnerDocument(); - } catch (NullPointerException npe) { - throw new NullPointerException(npe.getMessage()); - } - } - - /** - * This method returns the first non-null owner document of the Nodes in this Set. - * This method is necessary because it always returns a - * {@link Document}. {@link Node#getOwnerDocument} returns null - * if the {@link Node} is a {@link Document}. - * - * @param xpathNodeSet - * @return the owner document - */ - public static Document - getOwnerDocument(Set xpathNodeSet) - { - NullPointerException npe = null; - for (Node node : xpathNodeSet) { - int nodeType = node.getNodeType(); - if (nodeType == Node.DOCUMENT_NODE) { - return (Document) node; - } - try { - if (nodeType == Node.ATTRIBUTE_NODE) { - return ((Attr)node).getOwnerElement().getOwnerDocument(); - } - return node.getOwnerDocument(); - } catch (NullPointerException e) { - npe = e; - } - } - - throw new NullPointerException(npe.getMessage()); - } - - /** - * Method convertNodelistToSet - * - * @param xpathNodeSet - * @return the set with the nodelist - */ - public static Set - convertNodelistToSet(NodeList xpathNodeSet) - { - if (xpathNodeSet == null) { - return new HashSet(); - } - - int length = xpathNodeSet.getLength(); - Set set = new HashSet(length); - - for (int i = 0; i < length; i++) { - set.add(xpathNodeSet.item(i)); - } - - return set; - } - - /** - * This method spreads all namespace attributes in a DOM document to their - * children. This is needed because the XML Signature XPath transform - * must evaluate the XPath against all nodes in the input, even against - * XPath namespace nodes. Through a bug in XalanJ2, the namespace nodes are - * not fully visible in the Xalan XPath model, so we have to do this by - * hand in DOM spaces so that the nodes become visible in XPath space. - * - * @param doc - * @see - * Namespace axis resolution is not XPath compliant - */ - public static void - circumventBug2650(Document doc) - { - - Element documentElement = doc.getDocumentElement(); - - // if the document element has no xmlns definition, we add xmlns="" - Attr xmlnsAttr = - documentElement.getAttributeNodeNS(Constants.NamespaceSpecNS, "xmlns"); - - if (xmlnsAttr == null) { - documentElement.setAttributeNS(Constants.NamespaceSpecNS, "xmlns", ""); - } - - XMLUtils.circumventBug2650internal(doc); - } - - /** - * This is the work horse for {@link #circumventBug2650}. - * - * @param node - * @see - * Namespace axis resolution is not XPath compliant - */ - @SuppressWarnings("fallthrough") - private static void - circumventBug2650internal(Node node) - { - Node parent = null; - Node sibling = null; - final String namespaceNs = Constants.NamespaceSpecNS; - do { - switch (node.getNodeType()) { - case Node.ELEMENT_NODE : - Element element = (Element) node; - if (!element.hasChildNodes()) { - break; - } - if (element.hasAttributes()) { - NamedNodeMap attributes = element.getAttributes(); - int attributesLength = attributes.getLength(); - - for (Node child = element.getFirstChild(); child != null; - child = child.getNextSibling()) { - - if (child.getNodeType() != Node.ELEMENT_NODE) { - continue; - } - Element childElement = (Element) child; - - for (int i = 0; i < attributesLength; i++) { - Attr currentAttr = (Attr) attributes.item(i); - if (!namespaceNs.equals(currentAttr.getNamespaceURI())) { - continue; - } - if (childElement.hasAttributeNS(namespaceNs, - currentAttr.getLocalName())) { - continue; - } - childElement.setAttributeNS(namespaceNs, - currentAttr.getName(), - currentAttr.getNodeValue()); - } - } - } - case Node.ENTITY_REFERENCE_NODE : - case Node.DOCUMENT_NODE : - parent = node; - sibling = node.getFirstChild(); - break; - } - while ((sibling == null) && (parent != null)) { - sibling = parent.getNextSibling(); - parent = parent.getParentNode(); - } - if (sibling == null) { - return; - } - - node = sibling; - sibling = node.getNextSibling(); - } while (true); - } - - /** - * @param sibling - * @param uri - * @param nodeName - * @param number - * @return nodes with the constrain - */ - public static Text - selectNodeText(Node sibling, String uri, String nodeName, int number) - { - Node n = selectNode(sibling, uri, nodeName, number); - if (n == null) { - return null; - } - n = n.getFirstChild(); - while (n != null && n.getNodeType() != Node.TEXT_NODE) { - n = n.getNextSibling(); - } - return (Text)n; - } - - /** - * @param sibling - * @param uri - * @param nodeName - * @param number - * @return nodes with the constrain - */ - public static Element - selectNode(Node sibling, String uri, String nodeName, int number) - { - while (sibling != null) { - if (sibling.getNamespaceURI() != null && sibling.getNamespaceURI().equals(uri) - && sibling.getLocalName().equals(nodeName)) { - if (number == 0) { - return (Element)sibling; - } - number--; - } - sibling = sibling.getNextSibling(); - } - return null; - } - - /** - * @param sibling - * @param uri - * @param nodeName - * @return nodes with the constraint - */ - public static Element[] - selectNodes(Node sibling, String uri, String nodeName) - { - List list = new ArrayList(); - while (sibling != null) { - if (sibling.getNamespaceURI() != null && sibling.getNamespaceURI().equals(uri) - && sibling.getLocalName().equals(nodeName)) { - list.add((Element)sibling); - } - sibling = sibling.getNextSibling(); - } - return list.toArray(new Element[list.size()]); - } - - /** - * @param signatureElement - * @param inputSet - * @return nodes with the constrain - */ - public static Set - excludeNodeFromSet(Node signatureElement, Set inputSet) - { - Set resultSet = new HashSet(); - Iterator iterator = inputSet.iterator(); - - while (iterator.hasNext()) { - Node inputNode = iterator.next(); - - if (!XMLUtils.isDescendantOrSelf(signatureElement, inputNode)) { - resultSet.add(inputNode); - } - } - return resultSet; - } - - /** - * Method getStrFromNode - * - * @param xpathnode - * @return the string for the node. - */ - public static String - getStrFromNode(Node xpathnode) - { - if (xpathnode.getNodeType() == Node.TEXT_NODE) { - // we iterate over all siblings of the context node because eventually, - // the text is "polluted" with pi's or comments - StringBuilder sb = new StringBuilder(); - - for (Node currentSibling = xpathnode.getParentNode().getFirstChild(); - currentSibling != null; - currentSibling = currentSibling.getNextSibling()) { - if (currentSibling.getNodeType() == Node.TEXT_NODE) { - sb.append(((Text) currentSibling).getData()); - } - } - - return sb.toString(); - } else if (xpathnode.getNodeType() == Node.ATTRIBUTE_NODE) { - return ((Attr) xpathnode).getNodeValue(); - } else if (xpathnode.getNodeType() == Node.PROCESSING_INSTRUCTION_NODE) { - return ((ProcessingInstruction) xpathnode).getNodeValue(); - } - - return null; - } - - /** - * Returns true if the descendantOrSelf is on the descendant-or-self axis - * of the context node. - * - * @param ctx - * @param descendantOrSelf - * @return true if the node is descendant - */ - public static boolean - isDescendantOrSelf(Node ctx, Node descendantOrSelf) - { - if (ctx == descendantOrSelf) { - return true; - } - - Node parent = descendantOrSelf; - - while (true) { - if (parent == null) { - return false; - } - - if (parent == ctx) { - return true; - } - - if (parent.getNodeType() == Node.ATTRIBUTE_NODE) { - parent = ((Attr) parent).getOwnerElement(); - } else { - parent = parent.getParentNode(); - } - } - } - - /** - * Returns the attribute value for the attribute with the specified name. - * Returns null if there is no such attribute, or - * the empty string if the attribute value is empty. - * - *

This works around a limitation of the DOM - * Element.getAttributeNode method, which does not distinguish - * between an unspecified attribute and an attribute with a value of - * "" (it returns "" for both cases). - * - * @param elem the element containing the attribute - * @param name the name of the attribute - * @return the attribute value (may be null if unspecified) - */ - public static String - getAttributeValue(Element elem, String name) - { - Attr attr = elem.getAttributeNodeNS(null, name); - return (attr == null) ? null : attr.getValue(); - } - - /** - * This method is a tree-search to help prevent against wrapping attacks. It checks that no - * two Elements have ID Attributes that match the "value" argument, if this is the case then - * "false" is returned. Note that a return value of "true" does not necessarily mean that - * a matching Element has been found, just that no wrapping attack has been detected. - */ - public static boolean - protectAgainstWrappingAttack(Node startNode, String value) - { - Node startParent = startNode.getParentNode(); - Node processedNode; - Element foundElement = null; - - String id = value.trim(); - if (id.charAt(0) == '#') { - id = id.substring(1); - } - - while (startNode != null) { - if (startNode.getNodeType() == Node.ELEMENT_NODE) { - Element se = (Element) startNode; - - NamedNodeMap attributes = se.getAttributes(); - if (attributes != null) { - for (int i = 0; i < attributes.getLength(); i++) { - Attr attr = (Attr)attributes.item(i); - if (attr.isId() && id.equals(attr.getValue())) { - if (foundElement == null) { - // Continue searching to find duplicates - foundElement = attr.getOwnerElement(); - } else { - //log.debug("Multiple elements with the same 'Id' attribute value!"); - return false; - } - } - } - } - } - - processedNode = startNode; - startNode = startNode.getFirstChild(); - - // no child, this node is done. - if (startNode == null) { - // close node processing, get sibling - startNode = processedNode.getNextSibling(); - } - - // no more siblings, get parent, all children - // of parent are processed. - while (startNode == null) { - processedNode = processedNode.getParentNode(); - if (processedNode == startParent) { - return true; - } - // close parent node processing (processed node now) - startNode = processedNode.getNextSibling(); - } - } - return true; - } - - /** - * This method is a tree-search to help prevent against wrapping attacks. It checks that no other - * Element than the given "knownElement" argument has an ID attribute that matches the "value" - * argument, which is the ID value of "knownElement". If this is the case then "false" is returned. - */ - public static boolean - protectAgainstWrappingAttack( - Node startNode, Element knownElement, String value - ) - { - Node startParent = startNode.getParentNode(); - Node processedNode; - - String id = value.trim(); - if (id.charAt(0) == '#') { - id = id.substring(1); - } - - while (startNode != null) { - if (startNode.getNodeType() == Node.ELEMENT_NODE) { - Element se = (Element) startNode; - - NamedNodeMap attributes = se.getAttributes(); - if (attributes != null) { - for (int i = 0; i < attributes.getLength(); i++) { - Attr attr = (Attr)attributes.item(i); - if (attr.isId() && id.equals(attr.getValue()) && se != knownElement) { - //log.debug("Multiple elements with the same 'Id' attribute value!"); - return false; - } - } - } - } - - processedNode = startNode; - startNode = startNode.getFirstChild(); - - // no child, this node is done. - if (startNode == null) { - // close node processing, get sibling - startNode = processedNode.getNextSibling(); - } - - // no more siblings, get parent, all children - // of parent are processed. - while (startNode == null) { - processedNode = processedNode.getParentNode(); - if (processedNode == startParent) { - return true; - } - // close parent node processing (processed node now) - startNode = processedNode.getNextSibling(); - } - } - return true; - } - -} diff --git a/lib/nokogiri/jruby/com/fasterxml/woodstox/woodstox-core/6.2.6/woodstox-core-6.2.6.jar b/lib/nokogiri/jruby/com/fasterxml/woodstox/woodstox-core/6.2.6/woodstox-core-6.2.6.jar new file mode 100644 index 0000000000..695fb76eba Binary files /dev/null and b/lib/nokogiri/jruby/com/fasterxml/woodstox/woodstox-core/6.2.6/woodstox-core-6.2.6.jar differ diff --git a/lib/nokogiri/jruby/commons-codec/commons-codec/1.15/commons-codec-1.15.jar b/lib/nokogiri/jruby/commons-codec/commons-codec/1.15/commons-codec-1.15.jar new file mode 100644 index 0000000000..f14985ac92 Binary files /dev/null and b/lib/nokogiri/jruby/commons-codec/commons-codec/1.15/commons-codec-1.15.jar differ diff --git a/lib/nokogiri/jruby/jakarta/activation/jakarta.activation-api/1.2.2/jakarta.activation-api-1.2.2.jar b/lib/nokogiri/jruby/jakarta/activation/jakarta.activation-api/1.2.2/jakarta.activation-api-1.2.2.jar new file mode 100644 index 0000000000..3cc969d8f7 Binary files /dev/null and b/lib/nokogiri/jruby/jakarta/activation/jakarta.activation-api/1.2.2/jakarta.activation-api-1.2.2.jar differ diff --git a/lib/nokogiri/jruby/jakarta/xml/bind/jakarta.xml.bind-api/2.3.3/jakarta.xml.bind-api-2.3.3.jar b/lib/nokogiri/jruby/jakarta/xml/bind/jakarta.xml.bind-api/2.3.3/jakarta.xml.bind-api-2.3.3.jar new file mode 100644 index 0000000000..b8c7dc1ec8 Binary files /dev/null and b/lib/nokogiri/jruby/jakarta/xml/bind/jakarta.xml.bind-api/2.3.3/jakarta.xml.bind-api-2.3.3.jar differ diff --git a/lib/nokogiri/jruby/nokogiri_jars.rb b/lib/nokogiri/jruby/nokogiri_jars.rb index f35ee62618..261cfceccf 100644 --- a/lib/nokogiri/jruby/nokogiri_jars.rb +++ b/lib/nokogiri/jruby/nokogiri_jars.rb @@ -2,37 +2,58 @@ begin require 'jar_dependencies' rescue LoadError - require 'xalan/xalan/2.7.2/xalan-2.7.2.jar' + require 'commons-codec/commons-codec/1.15/commons-codec-1.15.jar' require 'net/sourceforge/htmlunit/neko-htmlunit/2.63.0/neko-htmlunit-2.63.0.jar' - require 'nu/validator/jing/20200702VNU/jing-20200702VNU.jar' + require 'com/fasterxml/woodstox/woodstox-core/6.2.6/woodstox-core-6.2.6.jar' require 'xerces/xercesImpl/2.12.2/xercesImpl-2.12.2.jar' + require 'org/apache/santuario/xmlsec/2.3.1/xmlsec-2.3.1.jar' + require 'xalan/serializer/2.7.2/serializer-2.7.2.jar' + require 'isorelax/isorelax/20030108/isorelax-20030108.jar' + require 'org/slf4j/slf4j-api/1.7.36/slf4j-api-1.7.36.jar' + require 'xalan/xalan/2.7.2/xalan-2.7.2.jar' + require 'org/codehaus/woodstox/stax2-api/4.2.1/stax2-api-4.2.1.jar' + require 'nu/validator/jing/20200702VNU/jing-20200702VNU.jar' require 'org/nokogiri/nekodtd/0.1.11.noko1/nekodtd-0.1.11.noko1.jar' require 'net/sf/saxon/Saxon-HE/9.6.0-4/Saxon-HE-9.6.0-4.jar' + require 'jakarta/xml/bind/jakarta.xml.bind-api/2.3.3/jakarta.xml.bind-api-2.3.3.jar' require 'xml-apis/xml-apis/1.4.01/xml-apis-1.4.01.jar' - require 'xalan/serializer/2.7.2/serializer-2.7.2.jar' - require 'isorelax/isorelax/20030108/isorelax-20030108.jar' + require 'jakarta/activation/jakarta.activation-api/1.2.2/jakarta.activation-api-1.2.2.jar' end if defined? Jars - require_jar 'xalan', 'xalan', '2.7.2' + require_jar 'commons-codec', 'commons-codec', '1.15' require_jar 'net.sourceforge.htmlunit', 'neko-htmlunit', '2.63.0' - require_jar 'nu.validator', 'jing', '20200702VNU' + require_jar 'com.fasterxml.woodstox', 'woodstox-core', '6.2.6' require_jar 'xerces', 'xercesImpl', '2.12.2' + require_jar 'org.apache.santuario', 'xmlsec', '2.3.1' + require_jar 'xalan', 'serializer', '2.7.2' + require_jar 'isorelax', 'isorelax', '20030108' + require_jar 'org.slf4j', 'slf4j-api', '1.7.36' + require_jar 'xalan', 'xalan', '2.7.2' + require_jar 'org.codehaus.woodstox', 'stax2-api', '4.2.1' + require_jar 'nu.validator', 'jing', '20200702VNU' require_jar 'org.nokogiri', 'nekodtd', '0.1.11.noko1' require_jar 'net.sf.saxon', 'Saxon-HE', '9.6.0-4' + require_jar 'jakarta.xml.bind', 'jakarta.xml.bind-api', '2.3.3' require_jar 'xml-apis', 'xml-apis', '1.4.01' - require_jar 'xalan', 'serializer', '2.7.2' - require_jar 'isorelax', 'isorelax', '20030108' + require_jar 'jakarta.activation', 'jakarta.activation-api', '1.2.2' end # generated by the :vendor_jars rake task module Nokogiri JAR_DEPENDENCIES = { + "com.fasterxml.woodstox:woodstox-core" => "6.2.6", + "commons-codec:commons-codec" => "1.15", "isorelax:isorelax" => "20030108", + "jakarta.activation:jakarta.activation-api" => "1.2.2", + "jakarta.xml.bind:jakarta.xml.bind-api" => "2.3.3", "net.sf.saxon:Saxon-HE" => "9.6.0-4", "net.sourceforge.htmlunit:neko-htmlunit" => "2.63.0", "nu.validator:jing" => "20200702VNU", + "org.apache.santuario:xmlsec" => "2.3.1", + "org.codehaus.woodstox:stax2-api" => "4.2.1", "org.nokogiri:nekodtd" => "0.1.11.noko1", + "org.slf4j:slf4j-api" => "1.7.36", "xalan:serializer" => "2.7.2", "xalan:xalan" => "2.7.2", "xerces:xercesImpl" => "2.12.2", diff --git a/lib/nokogiri/jruby/org/apache/santuario/xmlsec/2.3.1/xmlsec-2.3.1.jar b/lib/nokogiri/jruby/org/apache/santuario/xmlsec/2.3.1/xmlsec-2.3.1.jar new file mode 100644 index 0000000000..e7df49b033 Binary files /dev/null and b/lib/nokogiri/jruby/org/apache/santuario/xmlsec/2.3.1/xmlsec-2.3.1.jar differ diff --git a/lib/nokogiri/jruby/org/codehaus/woodstox/stax2-api/4.2.1/stax2-api-4.2.1.jar b/lib/nokogiri/jruby/org/codehaus/woodstox/stax2-api/4.2.1/stax2-api-4.2.1.jar new file mode 100644 index 0000000000..28c6a08f40 Binary files /dev/null and b/lib/nokogiri/jruby/org/codehaus/woodstox/stax2-api/4.2.1/stax2-api-4.2.1.jar differ diff --git a/lib/nokogiri/jruby/org/slf4j/slf4j-api/1.7.36/slf4j-api-1.7.36.jar b/lib/nokogiri/jruby/org/slf4j/slf4j-api/1.7.36/slf4j-api-1.7.36.jar new file mode 100644 index 0000000000..7d3ce68d25 Binary files /dev/null and b/lib/nokogiri/jruby/org/slf4j/slf4j-api/1.7.36/slf4j-api-1.7.36.jar differ diff --git a/lib/nokogiri/xml.rb b/lib/nokogiri/xml.rb index 9d16fb1498..16bad274cd 100644 --- a/lib/nokogiri/xml.rb +++ b/lib/nokogiri/xml.rb @@ -11,7 +11,7 @@ def XML(thing, url = nil, encoding = nil, options = XML::ParseOptions::DEFAULT_X module XML # Original C14N 1.0 spec canonicalization - XML_C14N_1_0 = 0 + XML_C14N_1_0 = 0 # Exclusive C14N 1.0 spec canonicalization XML_C14N_EXCLUSIVE_1_0 = 1 # C14N 1.1 spec canonicalization diff --git a/nokogiri.gemspec b/nokogiri.gemspec index 08a4ebb1f1..e0cdf79e25 100644 --- a/nokogiri.gemspec +++ b/nokogiri.gemspec @@ -116,33 +116,6 @@ Gem::Specification.new do |spec| "ext/java/nokogiri/internals/XmlDeclHandler.java", "ext/java/nokogiri/internals/XmlDomParserContext.java", "ext/java/nokogiri/internals/XmlSaxParser.java", - "ext/java/nokogiri/internals/c14n/AttrCompare.java", - "ext/java/nokogiri/internals/c14n/C14nHelper.java", - "ext/java/nokogiri/internals/c14n/CanonicalFilter.java", - "ext/java/nokogiri/internals/c14n/CanonicalizationException.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer11.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer11_OmitComments.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer11_WithComments.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315Excl.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclOmitComments.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315ExclWithComments.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315OmitComments.java", - "ext/java/nokogiri/internals/c14n/Canonicalizer20010315WithComments.java", - "ext/java/nokogiri/internals/c14n/CanonicalizerBase.java", - "ext/java/nokogiri/internals/c14n/CanonicalizerPhysical.java", - "ext/java/nokogiri/internals/c14n/CanonicalizerSpi.java", - "ext/java/nokogiri/internals/c14n/Constants.java", - "ext/java/nokogiri/internals/c14n/ElementProxy.java", - "ext/java/nokogiri/internals/c14n/HelperNodeList.java", - "ext/java/nokogiri/internals/c14n/IgnoreAllErrorHandler.java", - "ext/java/nokogiri/internals/c14n/InclusiveNamespaces.java", - "ext/java/nokogiri/internals/c14n/InvalidCanonicalizerException.java", - "ext/java/nokogiri/internals/c14n/NameSpaceSymbTable.java", - "ext/java/nokogiri/internals/c14n/NodeFilter.java", - "ext/java/nokogiri/internals/c14n/UtfHelpper.java", - "ext/java/nokogiri/internals/c14n/XMLUtils.java", "ext/java/nokogiri/internals/dom2dtm/DOM2DTM.java", "ext/java/nokogiri/internals/dom2dtm/DOM2DTMdefaultNamespaceDeclarationNode.java", "ext/nokogiri/depend", @@ -257,13 +230,20 @@ Gem::Specification.new do |spec| "lib/nokogiri/html5/document.rb", "lib/nokogiri/html5/document_fragment.rb", "lib/nokogiri/html5/node.rb", + "lib/nokogiri/jruby/com/fasterxml/woodstox/woodstox-core/6.2.6/woodstox-core-6.2.6.jar", + "lib/nokogiri/jruby/commons-codec/commons-codec/1.15/commons-codec-1.15.jar", "lib/nokogiri/jruby/dependencies.rb", "lib/nokogiri/jruby/isorelax/isorelax/20030108/isorelax-20030108.jar", + "lib/nokogiri/jruby/jakarta/activation/jakarta.activation-api/1.2.2/jakarta.activation-api-1.2.2.jar", + "lib/nokogiri/jruby/jakarta/xml/bind/jakarta.xml.bind-api/2.3.3/jakarta.xml.bind-api-2.3.3.jar", "lib/nokogiri/jruby/net/sf/saxon/Saxon-HE/9.6.0-4/Saxon-HE-9.6.0-4.jar", "lib/nokogiri/jruby/net/sourceforge/htmlunit/neko-htmlunit/2.63.0/neko-htmlunit-2.63.0.jar", "lib/nokogiri/jruby/nokogiri_jars.rb", "lib/nokogiri/jruby/nu/validator/jing/20200702VNU/jing-20200702VNU.jar", + "lib/nokogiri/jruby/org/apache/santuario/xmlsec/2.3.1/xmlsec-2.3.1.jar", + "lib/nokogiri/jruby/org/codehaus/woodstox/stax2-api/4.2.1/stax2-api-4.2.1.jar", "lib/nokogiri/jruby/org/nokogiri/nekodtd/0.1.11.noko1/nekodtd-0.1.11.noko1.jar", + "lib/nokogiri/jruby/org/slf4j/slf4j-api/1.7.36/slf4j-api-1.7.36.jar", "lib/nokogiri/jruby/xalan/serializer/2.7.2/serializer-2.7.2.jar", "lib/nokogiri/jruby/xalan/xalan/2.7.2/xalan-2.7.2.jar", "lib/nokogiri/jruby/xerces/xercesImpl/2.12.2/xercesImpl-2.12.2.jar", @@ -334,6 +314,7 @@ Gem::Specification.new do |spec| spec.requirements << "jar xalan, xalan, 2.7.2" # https://search.maven.org/artifact/xalan/xalan spec.requirements << "jar xerces, xercesImpl, 2.12.2" # https://search.maven.org/artifact/xerces/xercesImpl spec.requirements << "jar xml-apis, xml-apis, 1.4.01" # https://search.maven.org/artifact/xml-apis/xml-apis + spec.requirements << "jar org.apache.santuario, xmlsec, 2.3.1" # https://search.maven.org/artifact/org.apache.santuario/xmlsec else spec.add_runtime_dependency("mini_portile2", "~> 2.8.0") # keep version in sync with extconf.rb end diff --git a/test/xml/test_c14n.rb b/test/xml/test_c14n.rb index 59a78f740b..f5c5770b46 100644 --- a/test/xml/test_c14n.rb +++ b/test/xml/test_c14n.rb @@ -1,3 +1,4 @@ +# coding: utf-8 # frozen_string_literal: true require "helper" @@ -24,17 +25,32 @@ def test_3_1 eoxml + expected = <<~EOF.strip + + Hello, world! + + EOF c14n = doc.canonicalize - refute_match(/version=/, c14n) - assert_match(/Hello, world/, c14n) - refute_match(/Comment/, c14n) - c14n = doc.canonicalize(nil, nil, true) - assert_match(/Comment/, c14n) + assert_equal(expected, c14n) c14n = doc.canonicalize(nil, nil, false) - refute_match(/Comment/, c14n) + assert_equal(expected, c14n) + + expected = <<~EOF.strip + + Hello, world! + + + + EOF + c14n = doc.canonicalize(nil, nil, true) + assert_equal(expected, c14n) end def test_exclude_block_params + skip("canonicalize block not supported on jruby, see #2547") if Nokogiri.jruby? + xml = "" doc = Nokogiri.XML(xml) @@ -43,20 +59,15 @@ def test_exclude_block_params list << [node, parent] true end - if Nokogiri.jruby? - assert_equal( - ["a", "document", "document", nil, "b", "a"], - list.flatten.map { |x| x ? x.name : x } - ) - else - assert_equal( - ["a", "document", "document", nil, "b", "a", "a", "document"], - list.flatten.map { |x| x ? x.name : x } - ) - end + assert_equal( + ["a", "document", "document", nil, "b", "a", "a", "document"], + list.flatten.map { |x| x ? x.name : x } + ) end def test_exclude_block_true + skip("canonicalize block not supported on jruby, see #2547") if Nokogiri.jruby? + xml = "" doc = Nokogiri.XML(xml) @@ -67,6 +78,8 @@ def test_exclude_block_true end def test_exclude_block_false + skip("canonicalize block not supported on jruby, see #2547") if Nokogiri.jruby? + xml = "" doc = Nokogiri.XML(xml) @@ -76,7 +89,26 @@ def test_exclude_block_false assert_equal("", c14n) end + def test_exclude_block_conditional + skip("canonicalize block not supported on jruby, see #2547") if Nokogiri.jruby? + + xml = "" + doc = Nokogiri.XML(xml) + + c14n = doc.canonicalize do |node, _parent| + node.name == "root" || node.name == "a" || node.name == "c" + end + assert_equal("", c14n) + + c14n = doc.canonicalize do |node, _parent| + node.name == "a" || node.name == "c" + end + assert_equal("", c14n) + end + def test_exclude_block_nil + skip("canonicalize block not supported on jruby, see #2547") if Nokogiri.jruby? + xml = "" doc = Nokogiri.XML(xml) @@ -207,6 +239,21 @@ def test_wrong_params assert_raises(TypeError) { doc.canonicalize(nil, :wrong_type) } doc.canonicalize(nil, nil, :wrong_type) end + + def test_multibyte_unicode + # https://github.com/sparklemotion/nokogiri/issues/2410 + doc = Nokogiri.XML(%{𡏅}, nil, "EUC-JP") + + # I do not understand what's going on here + expected = if Nokogiri.jruby? + %{𡏅} + else + %{} + end + + result = doc.canonicalize + assert_equal(expected, result) + end end end end