require "rexml/document" require "rexml/xpath" require "uri" # Class to return SP metadata based on the settings requested. # Return this XML in a controller, then give that URL to the the # IdP administrator. The IdP will poll the URL and your settings # will be updated automatically module Onelogin module Saml include REXML class Metadata def generate(settings) meta_doc = REXML::Document.new root = meta_doc.add_element "md:EntityDescriptor", { "xmlns:md" => "urn:oasis:names:tc:SAML:2.0:metadata" } sp_sso = root.add_element "md:SPSSODescriptor", { "protocolSupportEnumeration" => "urn:oasis:names:tc:SAML:2.0:protocol", # Metadata request need not be signed (as we don't publish our cert) "AuthnRequestsSigned" => false, # However we would like assertions signed if idp_cert_fingerprint or idp_cert is set "WantAssertionsSigned" => (!settings.idp_cert_fingerprint.nil? || !settings.idp_cert.nil?) } if settings.issuer != nil root.attributes["entityID"] = settings.issuer end if settings.assertion_consumer_logout_service_url != nil sp_sso.add_element "md:SingleLogoutService", { # Add this as a setting to create different bindings? "Binding" => "urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect", "Location" => settings.assertion_consumer_logout_service_url, "ResponseLocation" => settings.assertion_consumer_logout_service_url, "isDefault" => true, "index" => 0 } end if settings.name_identifier_format != nil name_id = sp_sso.add_element "md:NameIDFormat" name_id.text = settings.name_identifier_format end if settings.assertion_consumer_service_url != nil sp_sso.add_element "md:AssertionConsumerService", { # Add this as a setting to create different bindings? "Binding" => "urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST", "Location" => settings.assertion_consumer_service_url, "isDefault" => true, "index" => 0 } end if settings.assertion_consumer_service_url != nil sp_sso.add_element "md:AssertionConsumerService", { # Add this as a setting to create different bindings? "Binding" => "urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect", "Location" => settings.assertion_consumer_service_url, "isDefault" => true, "index" => 0 } end # With OpenSSO, it might be required to also include # # meta_doc << REXML::XMLDecl.new ret = "" # pretty print the XML so IdP administrators can easily see what the SP supports meta_doc.write(ret, 1) Logging.debug "Generated metadata:\n#{ret}" ret end end end end