//************************************************************************** // Filename : WsTokenRef.java, WSSE Toolkit 2005 // // Author : Denis Pilipchuk // // Purpose : Base class for token references. It defines a mechanism for // referring to tokens in different locations (XML, files, object, etc). // Derived classes have to provide concrete implementation of the // retrieval logic. // // Disclaimer: This software is provided "as-is" and does not imply // any warranty or responsibility. //**************************************************************************** package wsse.Toolkit.Tokens.Refs; // W3C DOM includes import org.w3c.dom.Element; import wsse.Toolkit.Tokens.WsToken; import wsse.Toolkit.Tokens.WsTokenHelper; import wsse.Toolkit.Tokens.WsTokenException; import wsse.Toolkit.Utils.Xml.XmlDocHelper; public abstract class WsTokenRef extends WsToken { public WsTokenRef(XmlDocHelper docHelper) { if (null == docHelper) { throw new NullPointerException("Null or documenr helper passed"); } m_owner = docHelper.GetDocument().getDocumentElement(); m_tokenHelper = new WsTokenHelper(docHelper); } public WsTokenRef(WsTokenRef refOwner) throws WsTokenRefException, WsTokenException { if (null == refOwner) { throw new NullPointerException("Null owner reference object passed: " + this); } WsToken owner = refOwner.GetToken(true); if (null != owner) { m_owner = owner.GetXml(); m_ownerToken = owner; m_tokenHelper = owner.GetTokenHelper(); } else { throw new WsTokenRefException("Can not resolve owner reference",refOwner,null); } } public WsTokenRef(WsToken owner) throws WsTokenException { if (null == owner) { throw new NullPointerException("Null owner object passed: " + this); } m_ownerToken = owner; m_owner = owner.GetXml(); m_tokenHelper = owner.GetTokenHelper(); } public WsTokenRef(Element owner) { if (null == owner) { throw new NullPointerException("Null owner XML element passed: " + this); } m_owner = owner; // Create a new doc helper to wrap this document m_tokenHelper = new WsTokenHelper(new XmlDocHelper(owner.getOwnerDocument())); } // Compare owners by reference only! public final boolean IsOwner(Element owner) { return m_owner == owner; } public boolean equals(Object obj) { WsTokenRef ref = (WsTokenRef)obj; boolean res = false; if (null != ref && ref.IsOwner(m_owner)) { try { res = IsMatch(ref.GetToken()); } catch (WsTokenRefException ex) { // TODO: logging System.out.println("Error token comparing references: " + this); ex.printStackTrace(); } } return res; } // Default implementation resolves this references to an actual token. // It'd be more efficient to perform match test without resolving the reference, // but this should be done by overriding this method in the derivatives. public boolean IsMatch(WsToken token) { // Passed token is allowed to be NULL - the implementation should check for it WsToken wsToken = null; try { wsToken = GetToken(); } catch (WsTokenRefException ex) { // TODO: logging System.out.println("Error checking token match: " + this); ex.printStackTrace(); } return null != wsToken && (wsToken == token || wsToken.equals(token)); } public Element GetXmlElement() { return GetXmlElement(false); } public Element GetXmlElement(boolean refresh) { if (null == m_element || refresh) { m_element = ResolveXmlReference(m_owner); } // May be resolved as null, it's not an error return m_element; } public WsToken GetToken() throws WsTokenRefException { return GetToken(false); } public WsToken GetToken(boolean refresh) throws WsTokenRefException { if (null != m_ownerToken) { try { // Refresh owner's XML, if needed m_owner = m_ownerToken.GetXml(refresh); } catch (WsTokenException ex) { throw new WsTokenRefException("Can not get owners XML",this,ex); } } if (null == m_wsToken || refresh) { m_wsToken = ResolveReference(m_owner); // Set the token helper assert null != m_tokenHelper; m_wsToken.SetTokenHelper(m_tokenHelper); } // May be resolved as null, it's not an error return m_wsToken; } public final Element GetOwner() { return m_owner; } //////////////////////////////////////////////////////////////////////////////////////// // In general, references are not going to be insertable. // Those that are should override the functions below and generate meaningful XML content. protected Element GenerateTokenXml() throws WsTokenException { throw new IllegalStateException("This reference is not insertable"); } protected void RefreshTokenXml(Element token) throws WsTokenException { throw new IllegalStateException("This reference is not insertable"); } // Override this method to verify XML content of a token against the standards protected void VerifyElement(Element token) throws WsTokenException { throw new IllegalStateException("This reference is not insertable"); } //////////////////////////////////////////////////////////////////////////////////////// protected abstract WsToken ResolveReference(Element owner) throws WsTokenRefException; protected abstract Element ResolveXmlReference(Element owner); //////////////////////////////////////////////////////////////////////////////////////// // Cached token that this reference represents private WsToken m_wsToken, m_ownerToken; private WsTokenHelper m_tokenHelper; // Owner structure of this reference's addressee to perform searches private Element m_owner, m_element; }