X-Git-Url: http://www.project-moonshot.org/gitweb/?a=blobdiff_plain;f=xmltooling%2Fio%2FAbstractXMLObjectMarshaller.cpp;h=622240dbc18eb99af2074ccb91c9f3a5a145e647;hb=ebb2772c2c65d4fe6f52e7978b9c7f656829614e;hp=4822fbeb812b63cba6566bcc05dc5629ef856570;hpb=f4a896a316898e7bcdddb95e7f896b4d7b6a50a6;p=shibboleth%2Fxmltooling.git diff --git a/xmltooling/io/AbstractXMLObjectMarshaller.cpp b/xmltooling/io/AbstractXMLObjectMarshaller.cpp index 4822fbe..622240d 100644 --- a/xmltooling/io/AbstractXMLObjectMarshaller.cpp +++ b/xmltooling/io/AbstractXMLObjectMarshaller.cpp @@ -1,5 +1,5 @@ /* -* Copyright 2001-2006 Internet2 +* Copyright 2001-2007 Internet2 * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -24,6 +24,7 @@ #include "exceptions.h" #include "io/AbstractXMLObjectMarshaller.h" #ifndef XMLTOOLING_NO_XMLSEC + #include "security/Credential.h" #include "signature/Signature.h" #endif #include "util/NDC.h" @@ -33,22 +34,19 @@ #include #include #include -#include #ifndef XMLTOOLING_NO_XMLSEC using namespace xmlsignature; #endif using namespace xmlconstants; using namespace xmltooling; -using namespace log4cpp; using namespace std; -#define XT_log (*static_cast(m_log)) - DOMElement* AbstractXMLObjectMarshaller::marshall( DOMDocument* document #ifndef XMLTOOLING_NO_XMLSEC - ,const std::vector* sigs + ,const vector* sigs + ,const Credential* credential #endif ) const { @@ -56,14 +54,14 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( xmltooling::NDC ndc("marshall"); #endif - if (XT_log.isDebugEnabled()) { - XT_log.debug("starting to marshal %s", getElementQName().toString().c_str()); + if (m_log.isDebugEnabled()) { + m_log.debug("starting to marshal %s", getElementQName().toString().c_str()); } DOMElement* cachedDOM=getDOM(); if (cachedDOM) { if (!document || document==cachedDOM->getOwnerDocument()) { - XT_log.debug("XMLObject has a usable cached DOM, reusing it"); + m_log.debug("XMLObject has a usable cached DOM, reusing it"); if (document) setDocumentElement(cachedDOM->getOwnerDocument(),cachedDOM); releaseParentDOM(true); @@ -89,18 +87,18 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( XercesJanitor janitor(bindDocument ? document : NULL); - XT_log.debug("creating root element to marshall"); + m_log.debug("creating root element to marshall"); DOMElement* domElement = document->createElementNS( getElementQName().getNamespaceURI(), getElementQName().getLocalPart() ); setDocumentElement(document, domElement); #ifndef XMLTOOLING_NO_XMLSEC - marshallInto(domElement, sigs); + marshallInto(domElement, sigs, credential); #else marshallInto(domElement); #endif //Recache the DOM. - XT_log.debug("caching DOM for XMLObject (document is %sbound)", bindDocument ? "" : "not "); + m_log.debug("caching DOM for XMLObject (document is %sbound)", bindDocument ? "" : "not "); setDOM(domElement, bindDocument); janitor.release(); // safely transferred releaseParentDOM(true); @@ -111,7 +109,8 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( DOMElement* AbstractXMLObjectMarshaller::marshall( DOMElement* parentElement #ifndef XMLTOOLING_NO_XMLSEC - ,const std::vector* sigs + ,const vector* sigs + ,const Credential* credential #endif ) const { @@ -119,14 +118,14 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( xmltooling::NDC ndc("marshall"); #endif - if (XT_log.isDebugEnabled()) { - XT_log.debug("starting to marshalling %s", getElementQName().toString().c_str()); + if (m_log.isDebugEnabled()) { + m_log.debug("starting to marshalling %s", getElementQName().toString().c_str()); } DOMElement* cachedDOM=getDOM(); if (cachedDOM) { if (parentElement->getOwnerDocument()==cachedDOM->getOwnerDocument()) { - XT_log.debug("XMLObject has a usable cached DOM, reusing it"); + m_log.debug("XMLObject has a usable cached DOM, reusing it"); if (parentElement!=cachedDOM->getParentNode()) { parentElement->appendChild(cachedDOM); releaseParentDOM(true); @@ -144,19 +143,19 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( } // If we get here, we didn't have a usable DOM (and/or we released the one we had). - XT_log.debug("creating root element to marshall"); + m_log.debug("creating root element to marshall"); DOMElement* domElement = parentElement->getOwnerDocument()->createElementNS( getElementQName().getNamespaceURI(), getElementQName().getLocalPart() ); parentElement->appendChild(domElement); #ifndef XMLTOOLING_NO_XMLSEC - marshallInto(domElement, sigs); + marshallInto(domElement, sigs, credential); #else marshallInto(domElement); #endif //Recache the DOM. - XT_log.debug("caching DOM for XMLObject"); + m_log.debug("caching DOM for XMLObject"); setDOM(domElement, false); releaseParentDOM(true); @@ -166,28 +165,66 @@ DOMElement* AbstractXMLObjectMarshaller::marshall( void AbstractXMLObjectMarshaller::marshallInto( DOMElement* targetElement #ifndef XMLTOOLING_NO_XMLSEC - ,const std::vector* sigs + ,const vector* sigs + ,const Credential* credential #endif ) const { if (getElementQName().hasPrefix()) targetElement->setPrefix(getElementQName().getPrefix()); - if (m_schemaLocation) { - static const XMLCh schemaLocation[]= UNICODE_LITERAL_14(s,c,h,e,m,a,L,o,c,a,t,i,o,n); - if (targetElement->getParentNode()==NULL || targetElement->getParentNode()->getNodeType()==DOMNode::DOCUMENT_NODE) - targetElement->setAttributeNS(XSI_NS,schemaLocation,m_schemaLocation); + if (m_schemaLocation || m_noNamespaceSchemaLocation) { + static const XMLCh schemaLocation[] = { + chLatin_x, chLatin_s, chLatin_i, chColon, + chLatin_s, chLatin_c, chLatin_h, chLatin_e, chLatin_m, chLatin_a, + chLatin_L, chLatin_o, chLatin_c, chLatin_a, chLatin_t, chLatin_i, chLatin_o, chLatin_n, chNull + }; + static const XMLCh noNamespaceSchemaLocation[] = { + chLatin_x, chLatin_s, chLatin_i, chColon, + chLatin_n, chLatin_o, chLatin_N, chLatin_a, chLatin_m, chLatin_e, chLatin_s, chLatin_p, chLatin_a, chLatin_c, chLatin_e, + chLatin_S, chLatin_c, chLatin_h, chLatin_e, chLatin_m, chLatin_a, + chLatin_L, chLatin_o, chLatin_c, chLatin_a, chLatin_t, chLatin_i, chLatin_o, chLatin_n, chNull + }; + if (targetElement->getParentNode()==NULL || targetElement->getParentNode()->getNodeType()==DOMNode::DOCUMENT_NODE) { + if (m_schemaLocation) + targetElement->setAttributeNS(XSI_NS,schemaLocation,m_schemaLocation); + if (m_noNamespaceSchemaLocation) + targetElement->setAttributeNS(XSI_NS,noNamespaceSchemaLocation,m_noNamespaceSchemaLocation); + } + } + + static const XMLCh _nil[] = { chLatin_x, chLatin_s, chLatin_i, chColon, chLatin_n, chLatin_i, chLatin_l, chNull }; + + if (m_nil != xmlconstants::XML_BOOL_NULL) { + switch (m_nil) { + case xmlconstants::XML_BOOL_TRUE: + targetElement->setAttributeNS(XSI_NS, _nil, xmlconstants::XML_TRUE); + break; + case xmlconstants::XML_BOOL_ONE: + targetElement->setAttributeNS(XSI_NS, _nil, xmlconstants::XML_ONE); + break; + case xmlconstants::XML_BOOL_FALSE: + targetElement->setAttributeNS(XSI_NS, _nil, xmlconstants::XML_FALSE); + break; + case xmlconstants::XML_BOOL_ZERO: + targetElement->setAttributeNS(XSI_NS, _nil, xmlconstants::XML_ZERO); + break; + } + m_log.debug("adding XSI namespace to list of namespaces used by XMLObject"); + addNamespace(Namespace(XSI_NS, XSI_PREFIX)); } marshallElementType(targetElement); marshallNamespaces(targetElement); marshallAttributes(targetElement); - marshallContent(targetElement); #ifndef XMLTOOLING_NO_XMLSEC + marshallContent(targetElement,credential); if (sigs) { - for_each(sigs->begin(),sigs->end(),mem_fun(&Signature::sign)); + for_each(sigs->begin(),sigs->end(),bind2nd(mem_fun1_t(&Signature::sign),credential)); } +#else + marshallContent(targetElement); #endif } @@ -195,7 +232,7 @@ void AbstractXMLObjectMarshaller::marshallElementType(DOMElement* domElement) co { const QName* type = getSchemaType(); if (type) { - XT_log.debug("setting xsi:type attribute for XMLObject"); + m_log.debug("setting xsi:type attribute for XMLObject"); const XMLCh* typeLocalName = type->getLocalPart(); if (!typeLocalName || !*typeLocalName) { @@ -220,7 +257,7 @@ void AbstractXMLObjectMarshaller::marshallElementType(DOMElement* domElement) co if (xsivalue != typeLocalName) XMLString::release(&xsivalue); - XT_log.debug("Adding XSI namespace to list of namespaces used by XMLObject"); + m_log.debug("adding XSI namespace to list of namespaces used by XMLObject"); addNamespace(Namespace(XSI_NS, XSI_PREFIX)); } } @@ -246,6 +283,7 @@ public: XMLString::catString(xmlns,colon); XMLString::catString(xmlns,prefix); domElement->setAttributeNS(XMLNS_NS, xmlns, uri); + XMLString::release(&xmlns); } else { domElement->setAttributeNS(XMLNS_NS, XMLNS_PREFIX, uri); @@ -285,26 +323,36 @@ public: void AbstractXMLObjectMarshaller::marshallNamespaces(DOMElement* domElement) const { - XT_log.debug("marshalling namespace attributes for XMLObject"); + m_log.debug("marshalling namespace attributes for XMLObject"); const set& namespaces = getNamespaces(); for_each(namespaces.begin(),namespaces.end(),bind1st(_addns(),domElement)); } -void AbstractXMLObjectMarshaller::marshallContent(DOMElement* domElement) const +void AbstractXMLObjectMarshaller::marshallContent( + DOMElement* domElement +#ifndef XMLTOOLING_NO_XMLSEC + ,const Credential* credential +#endif + ) const { - XT_log.debug("marshalling text and child elements for XMLObject"); + m_log.debug("marshalling text and child elements for XMLObject"); - const XMLCh* val; unsigned int pos=0; + const XMLCh* val = getTextContent(pos); + if (val && *val) + domElement->appendChild(domElement->getOwnerDocument()->createTextNode(val)); + const list& children=getOrderedChildren(); - for (list::const_iterator i=children.begin(); i!=children.end(); ++i, ++pos) { - val = getTextContent(pos); - if (val && *val) - domElement->appendChild(domElement->getOwnerDocument()->createTextNode(val)); - if (*i) + for (list::const_iterator i=children.begin(); i!=children.end(); ++i) { + if (*i) { +#ifndef XMLTOOLING_NO_XMLSEC + (*i)->marshall(domElement,NULL,credential); +#else (*i)->marshall(domElement); +#endif + val = getTextContent(++pos); + if (val && *val) + domElement->appendChild(domElement->getOwnerDocument()->createTextNode(val)); + } } - val = getTextContent(pos); - if (val && *val) - domElement->appendChild(domElement->getOwnerDocument()->createTextNode(val)); }