lyrebird 1.0.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +50 -9
- data/lib/lyrebird/assertion.rb +6 -4
- data/lib/lyrebird/certificate.rb +20 -7
- data/lib/lyrebird/encryption.rb +2 -2
- data/lib/lyrebird/response.rb +14 -7
- data/lib/lyrebird/signature.rb +9 -9
- data/lib/lyrebird/version.rb +1 -1
- data/lib/lyrebird.rb +0 -2
- metadata +6 -18
- data/.github/workflows/ci.yml +0 -25
- data/.github/workflows/publish.yml +0 -20
- data/Rakefile +0 -11
- data/lyrebird.gemspec +0 -33
- data/sig/lyrebird.rbs +0 -4
- data/test/lyrebird/assertion_test.rb +0 -348
- data/test/lyrebird/certificate_test.rb +0 -120
- data/test/lyrebird/defaults_test.rb +0 -58
- data/test/lyrebird/encryption_test.rb +0 -139
- data/test/lyrebird/id_test.rb +0 -18
- data/test/lyrebird/integration_test.rb +0 -243
- data/test/lyrebird/namespaces_test.rb +0 -63
- data/test/lyrebird/response_test.rb +0 -250
- data/test/lyrebird/signature_test.rb +0 -171
- data/test/test_helper.rb +0 -4
|
@@ -1,243 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require "test_helper"
|
|
4
|
-
require "onelogin/ruby-saml"
|
|
5
|
-
|
|
6
|
-
module Lyrebird
|
|
7
|
-
class IntegrationTest < Minitest::Test
|
|
8
|
-
def setup
|
|
9
|
-
unless defined?(@@idp_cert)
|
|
10
|
-
@@idp_cert = Certificate.build
|
|
11
|
-
@@sp_cert = Certificate.build
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
@idp_cert = @@idp_cert
|
|
15
|
-
@sp_cert = @@sp_cert
|
|
16
|
-
end
|
|
17
|
-
|
|
18
|
-
def test_ruby_saml_parses_signed_response
|
|
19
|
-
name_id = "user@example.com"
|
|
20
|
-
|
|
21
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
22
|
-
r.name_id = name_id
|
|
23
|
-
end
|
|
24
|
-
|
|
25
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
26
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
27
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
28
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
29
|
-
end
|
|
30
|
-
|
|
31
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
32
|
-
response.mimic,
|
|
33
|
-
settings: settings
|
|
34
|
-
)
|
|
35
|
-
|
|
36
|
-
assert saml_response.is_valid?, saml_response.errors
|
|
37
|
-
assert_equal name_id, saml_response.nameid
|
|
38
|
-
end
|
|
39
|
-
|
|
40
|
-
def test_ruby_saml_decrypts_signed_and_encrypted_response
|
|
41
|
-
name_id = "user@example.com"
|
|
42
|
-
email = "test@example.com"
|
|
43
|
-
role = "admin"
|
|
44
|
-
|
|
45
|
-
response = Response.build(
|
|
46
|
-
sign_with: @idp_cert,
|
|
47
|
-
encrypt_with: @sp_cert
|
|
48
|
-
) do |r|
|
|
49
|
-
r.name_id = name_id
|
|
50
|
-
|
|
51
|
-
r.attributes do |a|
|
|
52
|
-
a.email = email
|
|
53
|
-
a.role = role
|
|
54
|
-
end
|
|
55
|
-
end
|
|
56
|
-
|
|
57
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
58
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
59
|
-
s.private_key = @sp_cert.key_pem
|
|
60
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
61
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
62
|
-
end
|
|
63
|
-
|
|
64
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
65
|
-
response.mimic,
|
|
66
|
-
settings: settings
|
|
67
|
-
)
|
|
68
|
-
|
|
69
|
-
assert saml_response.is_valid?, saml_response.errors
|
|
70
|
-
assert_equal name_id, saml_response.nameid
|
|
71
|
-
assert_equal email, saml_response.attributes["email"]
|
|
72
|
-
assert_equal role, saml_response.attributes["role"]
|
|
73
|
-
end
|
|
74
|
-
|
|
75
|
-
def test_ruby_saml_parses_idp_initiated_response
|
|
76
|
-
name_id = "user@example.com"
|
|
77
|
-
email = "test@example.com"
|
|
78
|
-
|
|
79
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
80
|
-
r.in_response_to = nil
|
|
81
|
-
r.destination = nil
|
|
82
|
-
r.name_id = name_id
|
|
83
|
-
|
|
84
|
-
r.attributes do |a|
|
|
85
|
-
a.email = email
|
|
86
|
-
end
|
|
87
|
-
end
|
|
88
|
-
|
|
89
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
90
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
91
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
92
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
93
|
-
end
|
|
94
|
-
|
|
95
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
96
|
-
response.mimic,
|
|
97
|
-
settings: settings
|
|
98
|
-
)
|
|
99
|
-
|
|
100
|
-
assert saml_response.is_valid?, saml_response.errors
|
|
101
|
-
assert_equal name_id, saml_response.nameid
|
|
102
|
-
assert_equal email, saml_response.attributes["email"]
|
|
103
|
-
end
|
|
104
|
-
|
|
105
|
-
def test_ruby_saml_parses_multi_value_attributes
|
|
106
|
-
name_id = "user@example.com"
|
|
107
|
-
groups = ["admin", "users", "developers"]
|
|
108
|
-
roles = ["editor", "viewer"]
|
|
109
|
-
|
|
110
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
111
|
-
r.name_id = name_id
|
|
112
|
-
|
|
113
|
-
r.attributes do |a|
|
|
114
|
-
a.groups = groups
|
|
115
|
-
a.roles = roles
|
|
116
|
-
end
|
|
117
|
-
end
|
|
118
|
-
|
|
119
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
120
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
121
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
122
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
123
|
-
end
|
|
124
|
-
|
|
125
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
126
|
-
response.mimic,
|
|
127
|
-
settings: settings
|
|
128
|
-
)
|
|
129
|
-
|
|
130
|
-
assert saml_response.is_valid?, saml_response.errors
|
|
131
|
-
assert_equal name_id, saml_response.nameid
|
|
132
|
-
assert_equal groups, saml_response.attributes.multi("groups")
|
|
133
|
-
assert_equal roles, saml_response.attributes.multi("roles")
|
|
134
|
-
end
|
|
135
|
-
|
|
136
|
-
def test_ruby_saml_validates_custom_validity_period
|
|
137
|
-
name_id = "user@example.com"
|
|
138
|
-
not_before = Time.now.utc - 60
|
|
139
|
-
valid_for = 600
|
|
140
|
-
|
|
141
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
142
|
-
r.name_id = name_id
|
|
143
|
-
r.not_before = not_before
|
|
144
|
-
r.valid_for = valid_for
|
|
145
|
-
end
|
|
146
|
-
|
|
147
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
148
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
149
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
150
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
151
|
-
end
|
|
152
|
-
|
|
153
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
154
|
-
response.mimic,
|
|
155
|
-
settings: settings
|
|
156
|
-
)
|
|
157
|
-
|
|
158
|
-
assert saml_response.is_valid?, saml_response.errors
|
|
159
|
-
assert_equal name_id, saml_response.nameid
|
|
160
|
-
end
|
|
161
|
-
|
|
162
|
-
def test_ruby_saml_rejects_expired_assertion
|
|
163
|
-
name_id = "user@example.com"
|
|
164
|
-
|
|
165
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
166
|
-
r.name_id = name_id
|
|
167
|
-
r.valid_for = -10
|
|
168
|
-
end
|
|
169
|
-
|
|
170
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
171
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
172
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
173
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
174
|
-
end
|
|
175
|
-
|
|
176
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
177
|
-
response.mimic,
|
|
178
|
-
settings: settings
|
|
179
|
-
)
|
|
180
|
-
|
|
181
|
-
assert_operator Time.now.utc, :>=, saml_response.not_on_or_after
|
|
182
|
-
refute saml_response.is_valid?
|
|
183
|
-
end
|
|
184
|
-
|
|
185
|
-
def test_ruby_saml_rejects_not_yet_valid_assertion
|
|
186
|
-
name_id = "user@example.com"
|
|
187
|
-
not_before = Time.now.utc + 600
|
|
188
|
-
|
|
189
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
190
|
-
r.name_id = name_id
|
|
191
|
-
r.not_before = not_before
|
|
192
|
-
end
|
|
193
|
-
|
|
194
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
195
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
196
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
197
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
198
|
-
end
|
|
199
|
-
|
|
200
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
201
|
-
response.mimic,
|
|
202
|
-
settings: settings
|
|
203
|
-
)
|
|
204
|
-
|
|
205
|
-
assert_operator Time.now.utc, :<, saml_response.not_before
|
|
206
|
-
refute saml_response.is_valid?
|
|
207
|
-
end
|
|
208
|
-
|
|
209
|
-
def test_ruby_saml_rejects_tampered_signed_response
|
|
210
|
-
original_email = "user@example.com"
|
|
211
|
-
tampered_email = "attacker@evil.com"
|
|
212
|
-
|
|
213
|
-
response = Response.build(sign_with: @idp_cert) do |r|
|
|
214
|
-
r.name_id = "user@example.com"
|
|
215
|
-
|
|
216
|
-
r.attributes do |a|
|
|
217
|
-
a.email = original_email
|
|
218
|
-
a.role = "user"
|
|
219
|
-
end
|
|
220
|
-
end
|
|
221
|
-
|
|
222
|
-
doc = Nokogiri::XML(Base64.strict_decode64(response.mimic))
|
|
223
|
-
xpath = "//saml:Attribute[@Name='email']/saml:AttributeValue"
|
|
224
|
-
email_attr = doc.at_xpath(xpath, { "saml" => SAML_ASSERTION_NS })
|
|
225
|
-
email_attr.content = tampered_email
|
|
226
|
-
tampered = Base64.strict_encode64(doc.to_xml(save_with: 0))
|
|
227
|
-
|
|
228
|
-
settings = OneLogin::RubySaml::Settings.new.tap do |s|
|
|
229
|
-
s.idp_cert = @idp_cert.x509_pem
|
|
230
|
-
s.sp_entity_id = DEFAULTS.audience
|
|
231
|
-
s.assertion_consumer_service_url = DEFAULTS.recipient
|
|
232
|
-
end
|
|
233
|
-
|
|
234
|
-
saml_response = OneLogin::RubySaml::Response.new(
|
|
235
|
-
tampered,
|
|
236
|
-
settings: settings
|
|
237
|
-
)
|
|
238
|
-
|
|
239
|
-
refute saml_response.is_valid?
|
|
240
|
-
assert_includes saml_response.errors.join(" "), "Signature"
|
|
241
|
-
end
|
|
242
|
-
end
|
|
243
|
-
end
|
|
@@ -1,63 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require "test_helper"
|
|
4
|
-
|
|
5
|
-
module Lyrebird
|
|
6
|
-
class NamespacesTest < Minitest::Test
|
|
7
|
-
def test_saml_assertion_ns
|
|
8
|
-
assert_equal "urn:oasis:names:tc:SAML:2.0:assertion", SAML_ASSERTION_NS
|
|
9
|
-
end
|
|
10
|
-
|
|
11
|
-
def test_saml_protocol_ns
|
|
12
|
-
assert_equal "urn:oasis:names:tc:SAML:2.0:protocol", SAML_PROTOCOL_NS
|
|
13
|
-
end
|
|
14
|
-
|
|
15
|
-
def test_xmldsig_ns
|
|
16
|
-
assert_equal "http://www.w3.org/2000/09/xmldsig#", XMLDSIG_NS
|
|
17
|
-
end
|
|
18
|
-
|
|
19
|
-
def test_enveloped_sig
|
|
20
|
-
expected = "http://www.w3.org/2000/09/xmldsig#enveloped-signature"
|
|
21
|
-
assert_equal expected, ENVELOPED_SIG
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
def test_exc_c14n
|
|
25
|
-
assert_equal "http://www.w3.org/2001/10/xml-exc-c14n#", EXC_C14N
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
def test_sha256_digest
|
|
29
|
-
assert_equal "http://www.w3.org/2001/04/xmlenc#sha256", SHA256_DIGEST
|
|
30
|
-
end
|
|
31
|
-
|
|
32
|
-
def test_rsa_sha256
|
|
33
|
-
expected = "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"
|
|
34
|
-
assert_equal expected, RSA_SHA256
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
def test_cm_bearer
|
|
38
|
-
assert_equal "urn:oasis:names:tc:SAML:2.0:cm:bearer", CM_BEARER
|
|
39
|
-
end
|
|
40
|
-
|
|
41
|
-
def test_attr_name_format
|
|
42
|
-
expected = "urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified"
|
|
43
|
-
assert_equal expected, ATTR_NAME_FORMAT
|
|
44
|
-
end
|
|
45
|
-
|
|
46
|
-
def test_status_success
|
|
47
|
-
assert_equal "urn:oasis:names:tc:SAML:2.0:status:Success", STATUS_SUCCESS
|
|
48
|
-
end
|
|
49
|
-
|
|
50
|
-
def test_xmlenc_ns
|
|
51
|
-
assert_equal "http://www.w3.org/2001/04/xmlenc#", XMLENC_NS
|
|
52
|
-
end
|
|
53
|
-
|
|
54
|
-
def test_aes256_cbc
|
|
55
|
-
assert_equal "http://www.w3.org/2001/04/xmlenc#aes256-cbc", AES256_CBC
|
|
56
|
-
end
|
|
57
|
-
|
|
58
|
-
def test_rsa_oaep
|
|
59
|
-
expected = "http://www.w3.org/2001/04/xmlenc#rsa-oaep-mgf1p"
|
|
60
|
-
assert_equal expected, RSA_OAEP
|
|
61
|
-
end
|
|
62
|
-
end
|
|
63
|
-
end
|
|
@@ -1,250 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require "test_helper"
|
|
4
|
-
|
|
5
|
-
module Lyrebird
|
|
6
|
-
class ResponseTest < Minitest::Test
|
|
7
|
-
NAMESPACES = {
|
|
8
|
-
"saml" => SAML_ASSERTION_NS,
|
|
9
|
-
"samlp" => SAML_PROTOCOL_NS,
|
|
10
|
-
"ds" => XMLDSIG_NS,
|
|
11
|
-
"xenc" => XMLENC_NS
|
|
12
|
-
}.freeze
|
|
13
|
-
|
|
14
|
-
def setup
|
|
15
|
-
@response = Response.new
|
|
16
|
-
@root = @response.document.root
|
|
17
|
-
end
|
|
18
|
-
|
|
19
|
-
def test_build_with_defaults
|
|
20
|
-
response = Response.build
|
|
21
|
-
root = response.document.root
|
|
22
|
-
issuer = root.at_xpath("saml:Issuer", NAMESPACES)
|
|
23
|
-
assert_equal DEFAULTS.issuer, issuer.text
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def test_build_with_kwargs
|
|
27
|
-
issuer = "https://test.example.com"
|
|
28
|
-
refute_equal issuer, DEFAULTS.issuer
|
|
29
|
-
response = Response.build(issuer: issuer)
|
|
30
|
-
root = response.document.root
|
|
31
|
-
assert_equal issuer, root.at_xpath("saml:Issuer", NAMESPACES).text
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
def test_build_with_block
|
|
35
|
-
issuer = "https://test.example.com"
|
|
36
|
-
refute_equal issuer, DEFAULTS.issuer
|
|
37
|
-
response = Response.build { |r| r.issuer = issuer }
|
|
38
|
-
root = response.document.root
|
|
39
|
-
assert_equal issuer, root.at_xpath("saml:Issuer", NAMESPACES).text
|
|
40
|
-
end
|
|
41
|
-
|
|
42
|
-
def test_build_with_kwargs_and_block
|
|
43
|
-
issuer = "https://test.example.com"
|
|
44
|
-
email = "test@example.com"
|
|
45
|
-
|
|
46
|
-
refute_equal issuer, DEFAULTS.issuer
|
|
47
|
-
refute_equal email, DEFAULTS.name_id
|
|
48
|
-
|
|
49
|
-
response = Response.build(issuer: issuer) do |r|
|
|
50
|
-
r.name_id = email
|
|
51
|
-
end
|
|
52
|
-
|
|
53
|
-
root = response.document.root
|
|
54
|
-
assert_equal issuer, root.at_xpath("saml:Issuer", NAMESPACES).text
|
|
55
|
-
xpath = "saml:Assertion/saml:Subject/saml:NameID"
|
|
56
|
-
assert_equal email, root.at_xpath(xpath, NAMESPACES).text
|
|
57
|
-
end
|
|
58
|
-
|
|
59
|
-
def test_build_with_attributes_block
|
|
60
|
-
email = "test@example.com"
|
|
61
|
-
role = "admin"
|
|
62
|
-
|
|
63
|
-
response = Response.build do |r|
|
|
64
|
-
r.attributes do |a|
|
|
65
|
-
a.email = email
|
|
66
|
-
a.role = role
|
|
67
|
-
end
|
|
68
|
-
end
|
|
69
|
-
|
|
70
|
-
root = response.document.root
|
|
71
|
-
statement_xpath = "saml:Assertion/saml:AttributeStatement"
|
|
72
|
-
statement = root.at_xpath(statement_xpath, NAMESPACES)
|
|
73
|
-
email_xpath = "saml:Attribute[@Name='email']/saml:AttributeValue"
|
|
74
|
-
role_xpath = "saml:Attribute[@Name='role']/saml:AttributeValue"
|
|
75
|
-
email_element = statement.at_xpath(email_xpath, NAMESPACES)
|
|
76
|
-
role_element = statement.at_xpath(role_xpath, NAMESPACES)
|
|
77
|
-
|
|
78
|
-
assert_equal email, email_element.text
|
|
79
|
-
assert_equal role, role_element.text
|
|
80
|
-
end
|
|
81
|
-
|
|
82
|
-
def test_build_with_attributes_hash
|
|
83
|
-
email = "user@example.com"
|
|
84
|
-
|
|
85
|
-
response = Response.build do |r|
|
|
86
|
-
r.attributes = { email: email }
|
|
87
|
-
end
|
|
88
|
-
|
|
89
|
-
root = response.document.root
|
|
90
|
-
statement_xpath = "saml:Assertion/saml:AttributeStatement"
|
|
91
|
-
attr_xpath = "saml:Attribute[@Name='email']/saml:AttributeValue"
|
|
92
|
-
statement = root.at_xpath(statement_xpath, NAMESPACES)
|
|
93
|
-
assert_equal email, statement.at_xpath(attr_xpath, NAMESPACES).text
|
|
94
|
-
end
|
|
95
|
-
|
|
96
|
-
def test_mimic_returns_base64
|
|
97
|
-
encoded = @response.mimic
|
|
98
|
-
decoded = Base64.strict_decode64(encoded)
|
|
99
|
-
assert decoded.include?("<samlp:Response")
|
|
100
|
-
assert decoded.include?("<saml:Assertion")
|
|
101
|
-
end
|
|
102
|
-
|
|
103
|
-
def test_root_name
|
|
104
|
-
assert_equal "Response", @root.name
|
|
105
|
-
assert_equal "samlp", @root.namespace.prefix
|
|
106
|
-
end
|
|
107
|
-
|
|
108
|
-
def test_root_namespace
|
|
109
|
-
assert_equal SAML_PROTOCOL_NS, @root.namespace.href
|
|
110
|
-
end
|
|
111
|
-
|
|
112
|
-
def test_saml_namespace_declared
|
|
113
|
-
assert_equal SAML_ASSERTION_NS, @root.namespaces["xmlns:saml"]
|
|
114
|
-
end
|
|
115
|
-
|
|
116
|
-
def test_root_id
|
|
117
|
-
assert @root["ID"].start_with?("_")
|
|
118
|
-
end
|
|
119
|
-
|
|
120
|
-
def test_root_version
|
|
121
|
-
assert_equal "2.0", @root["Version"]
|
|
122
|
-
end
|
|
123
|
-
|
|
124
|
-
def test_root_issue_instant
|
|
125
|
-
instant = Time.iso8601(@root["IssueInstant"])
|
|
126
|
-
assert_in_delta Time.now.to_i, instant.to_i, 1
|
|
127
|
-
end
|
|
128
|
-
|
|
129
|
-
def test_destination_default
|
|
130
|
-
assert_equal DEFAULTS.recipient, @root["Destination"]
|
|
131
|
-
end
|
|
132
|
-
|
|
133
|
-
def test_destination_override
|
|
134
|
-
destination = "https://test.example.com/acs"
|
|
135
|
-
refute_equal destination, DEFAULTS.recipient
|
|
136
|
-
root = Response.new(destination: destination).document.root
|
|
137
|
-
assert_equal destination, root["Destination"]
|
|
138
|
-
end
|
|
139
|
-
|
|
140
|
-
def test_in_response_to_default
|
|
141
|
-
assert_equal DEFAULTS.in_response_to, @root["InResponseTo"]
|
|
142
|
-
end
|
|
143
|
-
|
|
144
|
-
def test_in_response_to_override
|
|
145
|
-
in_response_to = "_test_request"
|
|
146
|
-
refute_equal in_response_to, DEFAULTS.in_response_to
|
|
147
|
-
root = Response.new(in_response_to: in_response_to).document.root
|
|
148
|
-
assert_equal in_response_to, root["InResponseTo"]
|
|
149
|
-
end
|
|
150
|
-
|
|
151
|
-
def test_destination_omitted_when_nil
|
|
152
|
-
root = Response.new(destination: nil).document.root
|
|
153
|
-
assert_nil root["Destination"]
|
|
154
|
-
end
|
|
155
|
-
|
|
156
|
-
def test_in_response_to_omitted_when_nil
|
|
157
|
-
root = Response.new(in_response_to: nil).document.root
|
|
158
|
-
assert_nil root["InResponseTo"]
|
|
159
|
-
end
|
|
160
|
-
|
|
161
|
-
def test_issuer
|
|
162
|
-
issuer = @root.at_xpath("saml:Issuer", NAMESPACES)
|
|
163
|
-
assert_equal "Issuer", issuer.name
|
|
164
|
-
assert_equal "saml", issuer.namespace.prefix
|
|
165
|
-
assert_equal DEFAULTS.issuer, issuer.text
|
|
166
|
-
end
|
|
167
|
-
|
|
168
|
-
def test_issuer_override
|
|
169
|
-
url = "https://test.idp.example.com"
|
|
170
|
-
refute_equal url, DEFAULTS.issuer
|
|
171
|
-
root = Response.new(issuer: url).document.root
|
|
172
|
-
issuer = root.at_xpath("saml:Issuer", NAMESPACES)
|
|
173
|
-
assert_equal url, issuer.text
|
|
174
|
-
end
|
|
175
|
-
|
|
176
|
-
def test_status
|
|
177
|
-
status = @root.at_xpath("samlp:Status", NAMESPACES)
|
|
178
|
-
assert_equal "Status", status.name
|
|
179
|
-
assert_equal "samlp", status.namespace.prefix
|
|
180
|
-
end
|
|
181
|
-
|
|
182
|
-
def test_status_code
|
|
183
|
-
status_code = @root.at_xpath("samlp:Status/samlp:StatusCode", NAMESPACES)
|
|
184
|
-
assert_equal "StatusCode", status_code.name
|
|
185
|
-
assert_equal "samlp", status_code.namespace.prefix
|
|
186
|
-
assert_equal STATUS_SUCCESS, status_code["Value"]
|
|
187
|
-
end
|
|
188
|
-
|
|
189
|
-
def test_assertion_embedded
|
|
190
|
-
assertion = @root.at_xpath("saml:Assertion", NAMESPACES)
|
|
191
|
-
assert_equal "Assertion", assertion.name
|
|
192
|
-
assert_equal "saml", assertion.namespace.prefix
|
|
193
|
-
end
|
|
194
|
-
|
|
195
|
-
def test_assertion_has_id
|
|
196
|
-
assertion = @root.at_xpath("saml:Assertion", NAMESPACES)
|
|
197
|
-
assert assertion["ID"].start_with?("_")
|
|
198
|
-
end
|
|
199
|
-
|
|
200
|
-
def test_assertion_inherits_issuer
|
|
201
|
-
url = "https://test.idp.example.com"
|
|
202
|
-
refute_equal url, DEFAULTS.issuer
|
|
203
|
-
root = Response.new(issuer: url).document.root
|
|
204
|
-
issuer = root.at_xpath("saml:Assertion/saml:Issuer", NAMESPACES)
|
|
205
|
-
assert_equal url, issuer.text
|
|
206
|
-
end
|
|
207
|
-
|
|
208
|
-
def test_assertion_options_flow_through
|
|
209
|
-
email = "test@example.com"
|
|
210
|
-
refute_equal email, DEFAULTS.name_id
|
|
211
|
-
root = Response.new(name_id: email).document.root
|
|
212
|
-
xpath = "saml:Assertion/saml:Subject/saml:NameID"
|
|
213
|
-
assert_equal email, root.at_xpath(xpath, NAMESPACES).text
|
|
214
|
-
end
|
|
215
|
-
|
|
216
|
-
def test_unsigned_by_default
|
|
217
|
-
assert_nil @root.at_xpath("ds:Signature", NAMESPACES)
|
|
218
|
-
assert_nil @root.at_xpath("saml:Assertion/ds:Signature", NAMESPACES)
|
|
219
|
-
end
|
|
220
|
-
|
|
221
|
-
def test_sign_with_signs_response_and_assertion
|
|
222
|
-
root = Response.new(sign_with: Certificate.build).document.root
|
|
223
|
-
refute_nil root.at_xpath("ds:Signature", NAMESPACES)
|
|
224
|
-
refute_nil root.at_xpath("saml:Assertion/ds:Signature", NAMESPACES)
|
|
225
|
-
end
|
|
226
|
-
|
|
227
|
-
def test_not_encrypted_by_default
|
|
228
|
-
assert_nil @root.at_xpath("saml:EncryptedAssertion", NAMESPACES)
|
|
229
|
-
end
|
|
230
|
-
|
|
231
|
-
def test_encrypt_with_creates_encrypted_assertion
|
|
232
|
-
root = Response.new(encrypt_with: Certificate.build).document.root
|
|
233
|
-
ea = root.at_xpath("saml:EncryptedAssertion", NAMESPACES)
|
|
234
|
-
assert_equal "EncryptedAssertion", ea.name
|
|
235
|
-
assert_equal "saml", ea.namespace.prefix
|
|
236
|
-
end
|
|
237
|
-
|
|
238
|
-
def test_encrypt_with_removes_plain_assertion
|
|
239
|
-
root = Response.new(encrypt_with: Certificate.build).document.root
|
|
240
|
-
assert_nil root.at_xpath("saml:Assertion", NAMESPACES)
|
|
241
|
-
end
|
|
242
|
-
|
|
243
|
-
def test_encrypt_with_contains_encrypted_data
|
|
244
|
-
root = Response.new(encrypt_with: Certificate.build).document.root
|
|
245
|
-
xpath = "saml:EncryptedAssertion/xenc:EncryptedData"
|
|
246
|
-
ed = root.at_xpath(xpath, NAMESPACES)
|
|
247
|
-
assert_equal "EncryptedData", ed.name
|
|
248
|
-
end
|
|
249
|
-
end
|
|
250
|
-
end
|