Skip to content

Commit 787bd1f

Browse files
committed
Allow encryption key to be specified in the metadata.xml
1 parent 5c8c6dc commit 787bd1f

File tree

4 files changed

+55
-6
lines changed

4 files changed

+55
-6
lines changed

lib/Net/SAML2/SP.pm

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,11 @@ Path to the signing certificate
6464
6565
Path to the private key for the signing certificate
6666
67+
=item B<encryption_key>
68+
69+
Path to the public key that the IdP should use for encryption. This
70+
is used when generating the metadata.
71+
6772
=item B<cacert>
6873
6974
Path to the CA certificate for verification
@@ -156,6 +161,7 @@ has 'cert' => (isa => 'Str', is => 'ro', required => 1);
156161
has 'key' => (isa => 'Str', is => 'ro', required => 1);
157162
has 'cacert' => (isa => 'Str', is => 'rw', required => 0, predicate => 'has_cacert');
158163

164+
has 'encryption_key' => (isa => 'Str', is => 'ro', required => 0, predicate => 'has_encryption_key');
159165
has 'error_url' => (isa => Uri, is => 'ro', required => 1, coerce => 1);
160166
has 'org_name' => (isa => 'Str', is => 'ro', required => 1);
161167
has 'org_display_name' => (isa => 'Str', is => 'ro', required => 1);
@@ -172,6 +178,7 @@ has 'acs_url_artifact' => (isa => 'Str', is => 'ro', required => 0);
172178

173179
has '_cert_text' => (isa => 'Str', is => 'ro', init_arg => undef, builder => '_build_cert_text', lazy => 1);
174180

181+
has '_encryption_key_text' => (isa => 'Str', is => 'ro', init_arg => undef, builder => '_build_encryption_key_text', lazy => 1);
175182
has 'authnreq_signed' => (isa => 'Bool', is => 'ro', required => 0, default => 1);
176183
has 'want_assertions_signed' => (isa => 'Bool', is => 'ro', required => 0, default => 1);
177184

@@ -268,6 +275,15 @@ around BUILDARGS => sub {
268275
return $self->$orig(%args);
269276
};
270277

278+
sub _build_encryption_key_text {
279+
my ($self) = @_;
280+
281+
my $cert = Crypt::OpenSSL::X509->new_from_file($self->encryption_key);
282+
my $text = $cert->as_string;
283+
$text =~ s/-----[^-]*-----//gm;
284+
return $text;
285+
}
286+
271287
sub _build_cert_text {
272288
my ($self) = @_;
273289

@@ -520,7 +536,9 @@ sub generate_metadata {
520536
protocolSupportEnumeration => URN_PROTOCOL,
521537
},
522538

523-
$self->_generate_key_descriptors($x),
539+
$self->_generate_key_descriptors($x, 'signing'),
540+
541+
$self->has_encryption_key ? $self->_generate_key_descriptors($x, 'encryption') : (),
524542

525543
$self->_generate_single_logout_service($x),
526544

@@ -554,6 +572,7 @@ sub generate_metadata {
554572
sub _generate_key_descriptors {
555573
my $self = shift;
556574
my $x = shift;
575+
my $use = shift;
557576

558577
return
559578
if !$self->authnreq_signed
@@ -562,22 +581,21 @@ sub _generate_key_descriptors {
562581

563582
return $x->KeyDescriptor(
564583
$md,
565-
{ use => 'signing' },
584+
{ use => $use },
566585
$x->KeyInfo(
567586
$ds,
568587
$x->X509Data(
569588
$ds,
570589
$x->X509Certificate(
571590
$ds,
572-
$self->_cert_text,
591+
$use eq 'signing' ? $self->_cert_text : $self->_encryption_key_text,
573592
)
574593
),
575594
$x->KeyName(
576595
$ds,
577-
Digest::MD5::md5_hex($self->_cert_text)
596+
Digest::MD5::md5_hex($use eq 'signing' ? $self->_cert_text : $self->_encryption_key_text)
578597
),
579-
580-
)
598+
),
581599
);
582600
}
583601

t/02-create-sp.t

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,11 @@ use URN::OASIS::SAML2 qw(:bindings :urn);
162162
is($kd->getAttribute('use'),
163163
"signing", "Key descriptor is there for signing only");
164164

165+
ok(
166+
!$kd->getAttribute('encryption'),
167+
"Key descriptor encryption is undefined"
168+
);
169+
165170
my $ki = get_single_node_ok($xpath, $kd->nodePath() . "/ds:KeyInfo");
166171

167172
my $cert = get_single_node_ok($xpath,
@@ -193,6 +198,30 @@ use URN::OASIS::SAML2 qw(:bindings :urn);
193198

194199
}
195200

201+
}
202+
{
203+
my $sp = net_saml2_sp( ( encryption_key => 't/sign-nopw-cert.pem' ) );
204+
205+
my $xpath = get_xpath(
206+
$sp->metadata,
207+
md => URN_METADATA,
208+
ds => URN_SIGNATURE,
209+
);
210+
211+
# Test SPSSODescriptor
212+
my $node = get_single_node_ok($xpath, '/node()/md:SPSSODescriptor');
213+
my $p = $node->nodePath();
214+
215+
my $kd = get_single_node_ok($xpath, "$p/md:KeyDescriptor[\@use='signing']");
216+
217+
is($kd->getAttribute('use'),
218+
"signing", "Key descriptor is there for signing");
219+
220+
$kd = get_single_node_ok($xpath, "$p/md:KeyDescriptor[\@use='encryption']");
221+
222+
is($kd->getAttribute('use'),
223+
"encryption", "Key descriptor is there for encryption");
224+
196225
}
197226

198227
{

xt/testapp/config.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ template: "template_toolkit"
66
issuer: "https://netsaml2-testapp.local"
77
url: "https://netsaml2-testapp.local"
88
cert: "sign-certonly.pem"
9+
encryption_key: "sign-certonly.pem"
910
key: "sign-nopw-cert.pem"
1011
slo_url_soap: "/slo-soap"
1112
slo_url_redirect: "/sls-redirect-response"

xt/testapp/lib/Saml2Test.pm

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,7 @@ sub _sp {
262262
url => config->{url},
263263
cert => config->{cert},
264264
key => config->{key},
265+
config->{encryption_key} ? (encryption_key => config->{encryption_key}) : (),
265266
cacert => config->{cacert} || '',
266267
slo_url_soap => config->{slo_url_soap},
267268
slo_url_redirect => config->{slo_url_redirect},

0 commit comments

Comments
 (0)