src/share/classes/com/sun/org/apache/xml/internal/security/utils/IdResolver.java
Print this page
*** 1,294 ****
/*
* reserved comment block
* DO NOT REMOVE OR ALTER!
*/
! /*
! * Copyright 1999-2004 The Apache Software Foundation.
! *
! * Licensed under the Apache License, Version 2.0 (the "License");
! * you may not use this file except in compliance with the License.
! * You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
! * Unless required by applicable law or agreed to in writing, software
! * distributed under the License is distributed on an "AS IS" BASIS,
! * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
! * See the License for the specific language governing permissions and
! * limitations under the License.
! *
*/
package com.sun.org.apache.xml.internal.security.utils;
- import java.lang.ref.WeakReference;
- import java.util.Arrays;
- import java.util.WeakHashMap;
- import java.util.Map;
-
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;
/**
* Purpose of this class is to enable the XML Parser to keep track of ID
* attributes. This is done by 'registering' attributes of type ID at the
! * IdResolver. This is necessary if we create a document from scratch and we
! * sign some resources with a URI using a fragent identifier...
! * <BR />
! * The problem is that if you do not validate a document, you cannot use the
! * <CODE>getElementByID</CODE> functionality. So this modules uses some implicit
! * knowledge on selected Schemas and DTDs to pick the right Element for a given
! * ID: We know that all <CODE>@Id</CODE> attributes in an Element from the XML
! * Signature namespace are of type <CODE>ID</CODE>.
! *
! * @author $Author: mullan $
! * @see <A HREF="http://www.xml.com/lpt/a/2001/11/07/id.html">"Identity Crisis" on xml.com</A>
*/
public class IdResolver {
- /** {@link java.util.logging} logging facility */
- private static java.util.logging.Logger log =
- java.util.logging.Logger.getLogger(IdResolver.class.getName());
-
- private static Map<Document, Map<String, WeakReference<Element>>> docMap =
- new WeakHashMap<Document, Map<String, WeakReference<Element>>>();
-
- /**
- * Constructor IdResolver
- *
- */
private IdResolver() {
// we don't allow instantiation
}
/**
* Method registerElementById
*
* @param element the element to register
- * @param idValue the value of the ID attribute
- */
- public static void registerElementById(Element element, String idValue) {
- Document doc = element.getOwnerDocument();
- Map<String, WeakReference<Element>> elementMap;
- synchronized (docMap) {
- elementMap = docMap.get(doc);
- if (elementMap == null) {
- elementMap = new WeakHashMap<String, WeakReference<Element>>();
- docMap.put(doc, elementMap);
- }
- }
- elementMap.put(idValue, new WeakReference<Element>(element));
- }
-
- /**
- * Method registerElementById
- *
- * @param element the element to register
* @param id the ID attribute
*/
public static void registerElementById(Element element, Attr id) {
! IdResolver.registerElementById(element, id.getNodeValue());
}
/**
* Method getElementById
*
* @param doc the document
* @param id the value of the ID
* @return the element obtained by the id, or null if it is not found.
*/
public static Element getElementById(Document doc, String id) {
-
- Element result = IdResolver.getElementByIdType(doc, id);
-
- if (result != null) {
- log.log(java.util.logging.Level.FINE,
- "I could find an Element using the simple getElementByIdType method: "
- + result.getTagName());
-
- return result;
- }
-
- result = IdResolver.getElementByIdUsingDOM(doc, id);
-
- if (result != null) {
- log.log(java.util.logging.Level.FINE,
- "I could find an Element using the simple getElementByIdUsingDOM method: "
- + result.getTagName());
-
- return result;
- }
- // this must be done so that Xalan can catch ALL namespaces
- //XMLUtils.circumventBug2650(doc);
- result = IdResolver.getElementBySearching(doc, id);
-
- if (result != null) {
- IdResolver.registerElementById(result, id);
-
- return result;
- }
-
- return null;
- }
-
-
- /**
- * Method getElementByIdUsingDOM
- *
- * @param doc the document
- * @param id the value of the ID
- * @return the element obtained by the id, or null if it is not found.
- */
- private static Element getElementByIdUsingDOM(Document doc, String id) {
- if (log.isLoggable(java.util.logging.Level.FINE))
- log.log(java.util.logging.Level.FINE, "getElementByIdUsingDOM() Search for ID " + id);
return doc.getElementById(id);
}
- /**
- * Method getElementByIdType
- *
- * @param doc the document
- * @param id the value of the ID
- * @return the element obtained by the id, or null if it is not found.
- */
- private static Element getElementByIdType(Document doc, String id) {
- if (log.isLoggable(java.util.logging.Level.FINE))
- log.log(java.util.logging.Level.FINE, "getElementByIdType() Search for ID " + id);
- Map<String, WeakReference<Element>> elementMap;
- synchronized (docMap) {
- elementMap = docMap.get(doc);
- }
- if (elementMap != null) {
- WeakReference<Element> weakReference = elementMap.get(id);
- if (weakReference != null) {
- return weakReference.get();
- }
- }
- return null;
- }
-
- private static java.util.List<String> names;
- private static int namesLength;
- static {
- String namespaces[]={
- Constants.SignatureSpecNS,
- EncryptionConstants.EncryptionSpecNS,
- "http://schemas.xmlsoap.org/soap/security/2000-12",
- "http://www.w3.org/2002/03/xkms#",
- "urn:oasis:names:tc:SAML:1.0:assertion",
- "urn:oasis:names:tc:SAML:1.0:protocol"
- };
- names = Arrays.asList(namespaces);
- namesLength = names.size();
- }
-
-
- private static Element getElementBySearching(Node root,String id) {
- Element []els=new Element[namesLength + 1];
- getEl(root,id,els);
- for (int i=0;i<els.length;i++) {
- if (els[i]!=null) {
- return els[i];
- }
- }
- return null;
- }
-
- private static int getEl(Node currentNode,String id,Element []els) {
- Node sibling=null;
- Node parentNode=null;
- do {
- switch (currentNode.getNodeType()) {
- case Node.DOCUMENT_FRAGMENT_NODE :
- case Node.DOCUMENT_NODE :
- sibling= currentNode.getFirstChild();
- break;
-
-
- case Node.ELEMENT_NODE :
- Element currentElement = (Element) currentNode;
- if (isElement(currentElement, id, els)==1)
- return 1;
- sibling= currentNode.getFirstChild();
- if (sibling==null) {
- if (parentNode != null) {
- sibling= currentNode.getNextSibling();
- }
- } else {
- parentNode=currentElement;
- }
- break;
- } while (sibling==null && parentNode!=null) {
- sibling=parentNode.getNextSibling();
- parentNode=parentNode.getParentNode();
- if (parentNode != null && parentNode.getNodeType() != Node.ELEMENT_NODE) {
- parentNode=null;
- }
- }
- if (sibling==null)
- return 1;
- currentNode=sibling;
- sibling=currentNode.getNextSibling();
- } while(true);
-
- }
- public static int isElement(Element el, String id,Element[] els) {
- if (!el.hasAttributes()) {
- return 0;
- }
- NamedNodeMap ns=el.getAttributes();
- int elementIndex=names.indexOf(el.getNamespaceURI());
- elementIndex=(elementIndex<0) ? namesLength : elementIndex;
- for (int length=ns.getLength(), i=0; i<length; i++) {
- Attr n=(Attr)ns.item(i);
- String s=n.getNamespaceURI();
-
- int index=s==null ? elementIndex : names.indexOf(n.getNamespaceURI());
- index=(index<0) ? namesLength : index;
- String name=n.getLocalName();
- if (name == null)
- name = n.getName();
- if (name.length()>2)
- continue;
- String value=n.getNodeValue();
- if (name.charAt(0)=='I') {
- char ch=name.charAt(1);
- if (ch=='d' && value.equals(id)) {
- els[index]=el;
- if (index==0) {
- return 1;
- }
- } else if (ch=='D' &&value.endsWith(id)) {
- if (index!=3) {
- index=namesLength;
- }
- els[index]=el;
- }
- } else if ( "id".equals(name) && value.equals(id) ) {
- if (index!=2) {
- index=namesLength;
- }
- els[index]=el;
- }
- }
- //For an element namespace search for importants
- if ((elementIndex==3)&&(
- el.getAttribute("OriginalRequestID").equals(id) ||
- el.getAttribute("RequestID").equals(id) ||
- el.getAttribute("ResponseID").equals(id))) {
- els[3]=el;
- } else if ((elementIndex==4)&&(
- el.getAttribute("AssertionID").equals(id))) {
- els[4]=el;
- } else if ((elementIndex==5)&&(
- el.getAttribute("RequestID").equals(id) ||
- el.getAttribute("ResponseID").equals(id))) {
- els[5]=el;
- }
- return 0;
- }
}
--- 1,64 ----
/*
* reserved comment block
* DO NOT REMOVE OR ALTER!
*/
! /**
! * 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 com.sun.org.apache.xml.internal.security.utils;
import org.w3c.dom.Attr;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
/**
* Purpose of this class is to enable the XML Parser to keep track of ID
* attributes. This is done by 'registering' attributes of type ID at the
! * IdResolver.
! * @deprecated
*/
+ @Deprecated
public class IdResolver {
private IdResolver() {
// we don't allow instantiation
}
/**
* Method registerElementById
*
* @param element the element to register
* @param id the ID attribute
*/
public static void registerElementById(Element element, Attr id) {
! element.setIdAttributeNode(id, true);
}
/**
* Method getElementById
*
* @param doc the document
* @param id the value of the ID
* @return the element obtained by the id, or null if it is not found.
*/
public static Element getElementById(Document doc, String id) {
return doc.getElementById(id);
}
}