Commit dd7fe18
Changed files (3)
lib
saml
spec
saml
lib/saml/kit/service_provider_metadata.rb
@@ -17,7 +17,7 @@ module Saml
private
class Builder
- attr_accessor :id, :entity_id, :acs_urls, :logout_urls, :name_id_formats
+ attr_accessor :id, :entity_id, :acs_urls, :logout_urls, :name_id_formats, :sign
def initialize(configuration = Saml::Kit.configuration)
@id = SecureRandom.uuid
@@ -26,6 +26,7 @@ module Saml
@acs_urls = []
@logout_urls = []
@name_id_formats = [Namespaces::PERSISTENT]
+ @sign = true
end
def add_assertion_consumer_service(url, binding: :post)
@@ -37,31 +38,32 @@ module Saml
end
def to_xml
- signature = Signature.new(id)
- xml = ::Builder::XmlMarkup.new
- xml.instruct!
- xml.EntityDescriptor entity_descriptor_options do
- signature.template(xml)
- xml.SPSSODescriptor descriptor_options do
- xml.KeyDescriptor use: "signing" do
- xml.KeyInfo "xmlns": Namespaces::XMLDSIG do
- xml.X509Data do
- xml.X509Certificate @configuration.stripped_signing_certificate
+ Signature.sign(id, sign: sign) do |xml, signature|
+ xml.instruct!
+ xml.EntityDescriptor entity_descriptor_options do
+ signature.template(xml)
+ xml.SPSSODescriptor descriptor_options do
+ if @configuration.signing_certificate_pem.present?
+ xml.KeyDescriptor use: "signing" do
+ xml.KeyInfo "xmlns": Namespaces::XMLDSIG do
+ xml.X509Data do
+ xml.X509Certificate @configuration.stripped_signing_certificate
+ end
+ end
end
end
- end
- logout_urls.each do |item|
- xml.SingleLogoutService Binding: item[:binding], Location: item[:location]
- end
- name_id_formats.each do |format|
- xml.NameIDFormat format
- end
- acs_urls.each_with_index do |item, index|
- xml.AssertionConsumerService Binding: item[:binding], Location: item[:location], index: index, isDefault: index == 0 ? true : false
+ logout_urls.each do |item|
+ xml.SingleLogoutService Binding: item[:binding], Location: item[:location]
+ end
+ name_id_formats.each do |format|
+ xml.NameIDFormat format
+ end
+ acs_urls.each_with_index do |item, index|
+ xml.AssertionConsumerService Binding: item[:binding], Location: item[:location], index: index, isDefault: index == 0 ? true : false
+ end
end
end
end
- signature.finalize(xml)
end
def build
lib/saml/kit/signature.rb
@@ -16,14 +16,16 @@ module Saml
SHA512: "http://www.w3.org/2001/04/xmlenc#sha512",
}.freeze
- attr_reader :configuration, :reference_id
+ attr_reader :configuration, :reference_id, :sign
- def initialize(reference_id, configuration = Saml::Kit.configuration)
+ def initialize(reference_id, configuration: Saml::Kit.configuration, sign: true)
@reference_id = reference_id
@configuration = configuration
+ @sign = sign
end
def template(xml = ::Builder::XmlMarkup.new)
+ return unless sign
return if reference_id.blank?
xml.Signature "xmlns" => Namespaces::XMLDSIG do
@@ -49,13 +51,20 @@ module Saml
end
def finalize(xml)
- if reference_id.present?
+ if sign && reference_id.present?
document = Xmldsig::SignedDocument.new(xml.target!)
document.sign(configuration.signing_private_key)
else
xml.target!
end
end
+
+ def self.sign(id, sign: true)
+ xml = ::Builder::XmlMarkup.new
+ signature = new(id, sign: sign)
+ yield xml, signature
+ signature.finalize(xml)
+ end
end
end
end
spec/saml/signature_spec.rb
@@ -1,7 +1,7 @@
require "spec_helper"
RSpec.describe Saml::Kit::Signature do
- subject { described_class.new(reference_id, configuration) }
+ subject { described_class.new(reference_id, configuration: configuration) }
let(:configuration) do
config = Saml::Kit::Configuration.new
config.signing_certificate_pem = certificate
@@ -61,4 +61,16 @@ RSpec.describe Saml::Kit::Signature do
expect(signature['SignatureValue']).to be_present
expect(OpenSSL::X509::Certificate.new(Base64.decode64(signature['KeyInfo']['X509Data']['X509Certificate']))).to be_present
end
+
+ it 'does not add a signature' do
+ subject = described_class.new(reference_id, sign: false, configuration: configuration)
+ xml = ::Builder::XmlMarkup.new
+ xml.AuthnRequest do
+ subject.template(xml)
+ xml.Issuer "MyEntityID"
+ end
+ result = Hash.from_xml(subject.finalize(xml))
+ expect(result['AuthnRequest']).to be_present
+ expect(result["AuthnRequest"]["Signature"]).to be_nil
+ end
end