From 0d5e6d568cd0945e18a8b54b7d75e9f5a352c41b Mon Sep 17 00:00:00 2001 From: Scott Cantor Date: Thu, 10 Jul 2008 21:34:55 +0000 Subject: [PATCH] Multi-line svn commit, see body. https://issues.shibboleth.net/jira/browse/CPPOST-14 Also adds cacheDuration support to XML plugin. --- saml/saml2/metadata/impl/MetadataProvider.cpp | 8 ++- .../impl/RequireValidUntilMetadataFilter.cpp | 82 ++++++++++++++++++++++ saml/saml2/metadata/impl/XMLMetadataProvider.cpp | 24 +++---- 3 files changed, 99 insertions(+), 15 deletions(-) create mode 100644 saml/saml2/metadata/impl/RequireValidUntilMetadataFilter.cpp diff --git a/saml/saml2/metadata/impl/MetadataProvider.cpp b/saml/saml2/metadata/impl/MetadataProvider.cpp index 6c27a18..0741b62 100644 --- a/saml/saml2/metadata/impl/MetadataProvider.cpp +++ b/saml/saml2/metadata/impl/MetadataProvider.cpp @@ -1,6 +1,6 @@ /* * 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. * You may obtain a copy of the License at @@ -16,7 +16,7 @@ /** * MetadataProvider.cpp - * + * * Registration of factories for built-in providers */ @@ -44,6 +44,7 @@ namespace opensaml { SAML_DLLLOCAL PluginManager::Factory BlacklistMetadataFilterFactory; SAML_DLLLOCAL PluginManager::Factory WhitelistMetadataFilterFactory; SAML_DLLLOCAL PluginManager::Factory SignatureMetadataFilterFactory; + SAML_DLLLOCAL PluginManager::Factory RequireValidUntilMetadataFilterFactory; }; }; @@ -61,6 +62,7 @@ void SAML_API opensaml::saml2md::registerMetadataFilters() SAMLConfig::getConfig().MetadataFilterManager.registerFactory(BLACKLIST_METADATA_FILTER, BlacklistMetadataFilterFactory); SAMLConfig::getConfig().MetadataFilterManager.registerFactory(WHITELIST_METADATA_FILTER, WhitelistMetadataFilterFactory); SAMLConfig::getConfig().MetadataFilterManager.registerFactory(SIGNATURE_METADATA_FILTER, SignatureMetadataFilterFactory); + SAMLConfig::getConfig().MetadataFilterManager.registerFactory(REQUIREVALIDUNTIL_METADATA_FILTER, RequireValidUntilMetadataFilterFactory); } static const XMLCh _MetadataFilter[] = UNICODE_LITERAL_14(M,e,t,a,d,a,t,a,F,i,l,t,e,r); @@ -78,7 +80,7 @@ MetadataProvider::MetadataProvider(const DOMElement* e) #endif Category& log = Category::getInstance(SAML_LOGCAT".Metadata"); SAMLConfig& conf=SAMLConfig::getConfig(); - + // Locate any default recognized filters and plugins. try { DOMElement* child = e ? XMLHelper::getFirstChildElement(e) : NULL; diff --git a/saml/saml2/metadata/impl/RequireValidUntilMetadataFilter.cpp b/saml/saml2/metadata/impl/RequireValidUntilMetadataFilter.cpp new file mode 100644 index 0000000..8281cd3 --- /dev/null +++ b/saml/saml2/metadata/impl/RequireValidUntilMetadataFilter.cpp @@ -0,0 +1,82 @@ +/* + * Copyright 2001-2008 Internet2 + * + * 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. + */ + +/** + * RequireValidUntilMetadataFilter.cpp + * + * MetadataFilter that enforces expiration requirements. + */ + +#include "internal.h" +#include "saml2/metadata/Metadata.h" +#include "saml2/metadata/MetadataFilter.h" + +#include +#include + +using namespace opensaml::saml2md; +using namespace xmltooling::logging; +using namespace xmltooling; +using namespace std; + +namespace opensaml { + namespace saml2md { + + class SAML_DLLLOCAL RequireValidUntilMetadataFilter : public MetadataFilter + { + public: + RequireValidUntilMetadataFilter(const DOMElement* e); + ~RequireValidUntilMetadataFilter() {} + + const char* getId() const { return BLACKLIST_METADATA_FILTER; } + void doFilter(XMLObject& xmlObject) const; + + private: + time_t m_maxValidityInterval; + }; + + MetadataFilter* SAML_DLLLOCAL RequireValidUntilMetadataFilterFactory(const DOMElement* const & e) + { + return new RequireValidUntilMetadataFilter(e); + } + + }; +}; + +static const XMLCh maxValidityInterval[] = UNICODE_LITERAL_19(m,a,x,V,a,l,i,d,i,t,y,I,n,t,e,r,v,a,l); + +RequireValidUntilMetadataFilter::RequireValidUntilMetadataFilter(const DOMElement* e) : m_maxValidityInterval(60 * 60 * 24 * 7) +{ + const XMLCh* mvi = e ? e->getAttributeNS(NULL,maxValidityInterval) : NULL; + if (mvi && *mvi) { + m_maxValidityInterval = XMLString::parseInt(mvi); + if (m_maxValidityInterval == 0) + m_maxValidityInterval = 60 * 60 * 24 * 7; + } +} + +void RequireValidUntilMetadataFilter::doFilter(XMLObject& xmlObject) const +{ + const TimeBoundSAMLObject* tbo = dynamic_cast(&xmlObject); + if (!tbo) + throw MetadataFilterException("Metadata root element was invalid."); + + if (!tbo->getValidUntil()) + throw MetadataFilterException("Metadata did not include a validUntil attribute."); + + if (tbo->getValidUntilEpoch() - time(NULL) > m_maxValidityInterval) + throw MetadataFilterException("Metadata validity interval is larger than permitted."); +} diff --git a/saml/saml2/metadata/impl/XMLMetadataProvider.cpp b/saml/saml2/metadata/impl/XMLMetadataProvider.cpp index adcdee8..03deb22 100644 --- a/saml/saml2/metadata/impl/XMLMetadataProvider.cpp +++ b/saml/saml2/metadata/impl/XMLMetadataProvider.cpp @@ -41,16 +41,12 @@ using namespace std; namespace opensaml { namespace saml2md { - static const XMLCh requireValidUntil[] = UNICODE_LITERAL_17(r,e,q,u,i,r,e,V,a,l,i,d,U,n,t,i,l); - class SAML_DLLLOCAL XMLMetadataProvider : public AbstractMetadataProvider, public ReloadableXMLFile { public: XMLMetadataProvider(const DOMElement* e) : AbstractMetadataProvider(e), ReloadableXMLFile(e, Category::getInstance(SAML_LOGCAT".MetadataProvider.XML")), - m_object(NULL), m_requireValidUntil(false) { - const XMLCh* flag = e ? e->getAttributeNS(NULL,requireValidUntil) : NULL; - m_requireValidUntil = (flag && (*flag == chLatin_t || *flag == chDigit_1)); + m_object(NULL), m_maxCacheDuration(m_reloadInterval) { } virtual ~XMLMetadataProvider() { delete m_object; @@ -72,7 +68,7 @@ namespace opensaml { void index(); XMLObject* m_object; - bool m_requireValidUntil; + time_t m_maxCacheDuration; }; MetadataProvider* SAML_DLLLOCAL XMLMetadataProviderFactory(const DOMElement* const & e) @@ -104,12 +100,6 @@ pair XMLMetadataProvider::load() "Root of metadata instance not recognized: $1", params(1,xmlObject->getElementQName().toString().c_str()) ); - if (m_requireValidUntil) { - const TimeBoundSAMLObject* tbo = dynamic_cast(xmlObject.get()); - if (!tbo || tbo->getValidUntil() == NULL) - throw MetadataException("Root of metadata instance does not have validUntil atttribute."); - } - // Preprocess the metadata. doFilters(*xmlObject.get()); xmlObject->releaseThisAndChildrenDOM(); @@ -122,6 +112,16 @@ pair XMLMetadataProvider::load() index(); if (changed) emitChangeEvent(); + + // If a remote resource, reduce the reload interval if cacheDuration is set. + if (!m_local) { + const CacheableSAMLObject* cacheable = dynamic_cast(m_object); + if (cacheable && cacheable->getCacheDuration() && cacheable->getCacheDurationEpoch() < m_maxCacheDuration) + m_reloadInterval = cacheable->getCacheDurationEpoch(); + else + m_reloadInterval = m_maxCacheDuration; + } + return make_pair(false,(DOMElement*)NULL); } -- 2.1.4