From b5d5cdb00973f7e9900bc752ef0e492826b19054 Mon Sep 17 00:00:00 2001 From: Roland Hedberg Date: Wed, 13 Oct 2010 13:35:17 +0200 Subject: [PATCH] Configuration files for tests --- tests/idp_aa.xml | 32 ++++++++++ tests/idp_soap.xml | 17 ++++++ tests/server2.config | 46 ++++++++++++++ tests/server3.config | 46 ++++++++++++++ tests/test_12_s_utils.py | 9 +++ tests/test_32_cache.py | 4 +- tests/test_44_authnresp.py | 6 +- tests/test_50_server.py | 44 ++++++++++++-- tests/test_51_client.py | 121 +++++++++++++++++++++++++++++++++++-- tests/test_60_sp.py | 6 +- 10 files changed, 313 insertions(+), 18 deletions(-) create mode 100644 tests/idp_aa.xml create mode 100644 tests/idp_soap.xml create mode 100644 tests/server2.config create mode 100644 tests/server3.config diff --git a/tests/idp_aa.xml b/tests/idp_aa.xml new file mode 100644 index 0000000..c0288d9 --- /dev/null +++ b/tests/idp_aa.xml @@ -0,0 +1,32 @@ + +MIICsDCCAhmgAwIBAgIJAJrzqSSwmDY9MA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV +BAYTAkFVMRMwEQYDVQQIEwpTb21lLVN0YXRlMSEwHwYDVQQKExhJbnRlcm5ldCBX +aWRnaXRzIFB0eSBMdGQwHhcNMDkxMDA2MTk0OTQxWhcNMDkxMTA1MTk0OTQxWjBF +MQswCQYDVQQGEwJBVTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50 +ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB +gQDJg2cms7MqjniT8Fi/XkNHZNPbNVQyMUMXE9tXOdqwYCA1cc8vQdzkihscQMXy +3iPw2cMggBu6gjMTOSOxECkuvX5ZCclKr8pXAJM5cY6gVOaVO2PdTZcvDBKGbiaN +efiEw5hnoZomqZGp8wHNLAUkwtH9vjqqvxyS/vclc6k2ewIDAQABo4GnMIGkMB0G +A1UdDgQWBBRePsKHKYJsiojE78ZWXccK9K4aJTB1BgNVHSMEbjBsgBRePsKHKYJs +iojE78ZWXccK9K4aJaFJpEcwRTELMAkGA1UEBhMCQVUxEzARBgNVBAgTClNvbWUt +U3RhdGUxITAfBgNVBAoTGEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZIIJAJrzqSSw +mDY9MAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQADgYEAJSrKOEzHO7TL5cy6 +h3qh+3+JAk8HbGBW+cbX6KBCAw/mzU8flK25vnWwXS3dv2FF3Aod0/S7AWNfKib5 +U/SA9nJaz/mWeF9S0farz9AQFc8/NSzAzaVq7YbM4F6f6N2FRl7GikdXRCed45j6 +mrPzGzk3ECbupFnqyREH3+ZPSdk= +Exempel ABExempel ABExample Co.http://www.example.com/rolandJohnSmithjohn.smith@example.comMIICsDCCAhmgAwIBAgIJAJrzqSSwmDY9MA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV +BAYTAkFVMRMwEQYDVQQIEwpTb21lLVN0YXRlMSEwHwYDVQQKExhJbnRlcm5ldCBX +aWRnaXRzIFB0eSBMdGQwHhcNMDkxMDA2MTk0OTQxWhcNMDkxMTA1MTk0OTQxWjBF +MQswCQYDVQQGEwJBVTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50 +ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB +gQDJg2cms7MqjniT8Fi/XkNHZNPbNVQyMUMXE9tXOdqwYCA1cc8vQdzkihscQMXy +3iPw2cMggBu6gjMTOSOxECkuvX5ZCclKr8pXAJM5cY6gVOaVO2PdTZcvDBKGbiaN +efiEw5hnoZomqZGp8wHNLAUkwtH9vjqqvxyS/vclc6k2ewIDAQABo4GnMIGkMB0G +A1UdDgQWBBRePsKHKYJsiojE78ZWXccK9K4aJTB1BgNVHSMEbjBsgBRePsKHKYJs +iojE78ZWXccK9K4aJaFJpEcwRTELMAkGA1UEBhMCQVUxEzARBgNVBAgTClNvbWUt +U3RhdGUxITAfBgNVBAoTGEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZIIJAJrzqSSw +mDY9MAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQADgYEAJSrKOEzHO7TL5cy6 +h3qh+3+JAk8HbGBW+cbX6KBCAw/mzU8flK25vnWwXS3dv2FF3Aod0/S7AWNfKib5 +U/SA9nJaz/mWeF9S0farz9AQFc8/NSzAzaVq7YbM4F6f6N2FRl7GikdXRCed45j6 +mrPzGzk3ECbupFnqyREH3+ZPSdk= +Exempel ABExempel ABExample Co.http://www.example.com/rolandJohnSmithjohn.smith@example.com diff --git a/tests/idp_soap.xml b/tests/idp_soap.xml new file mode 100644 index 0000000..0902dc5 --- /dev/null +++ b/tests/idp_soap.xml @@ -0,0 +1,17 @@ + +MIICsDCCAhmgAwIBAgIJAJrzqSSwmDY9MA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV +BAYTAkFVMRMwEQYDVQQIEwpTb21lLVN0YXRlMSEwHwYDVQQKExhJbnRlcm5ldCBX +aWRnaXRzIFB0eSBMdGQwHhcNMDkxMDA2MTk0OTQxWhcNMDkxMTA1MTk0OTQxWjBF +MQswCQYDVQQGEwJBVTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50 +ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB +gQDJg2cms7MqjniT8Fi/XkNHZNPbNVQyMUMXE9tXOdqwYCA1cc8vQdzkihscQMXy +3iPw2cMggBu6gjMTOSOxECkuvX5ZCclKr8pXAJM5cY6gVOaVO2PdTZcvDBKGbiaN +efiEw5hnoZomqZGp8wHNLAUkwtH9vjqqvxyS/vclc6k2ewIDAQABo4GnMIGkMB0G +A1UdDgQWBBRePsKHKYJsiojE78ZWXccK9K4aJTB1BgNVHSMEbjBsgBRePsKHKYJs +iojE78ZWXccK9K4aJaFJpEcwRTELMAkGA1UEBhMCQVUxEzARBgNVBAgTClNvbWUt +U3RhdGUxITAfBgNVBAoTGEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZIIJAJrzqSSw +mDY9MAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQADgYEAJSrKOEzHO7TL5cy6 +h3qh+3+JAk8HbGBW+cbX6KBCAw/mzU8flK25vnWwXS3dv2FF3Aod0/S7AWNfKib5 +U/SA9nJaz/mWeF9S0farz9AQFc8/NSzAzaVq7YbM4F6f6N2FRl7GikdXRCed45j6 +mrPzGzk3ECbupFnqyREH3+ZPSdk= +Exempel ABExempel ABExample Co.http://www.example.com/rolandJohnSmithjohn.smith@example.com diff --git a/tests/server2.config b/tests/server2.config new file mode 100644 index 0000000..f605835 --- /dev/null +++ b/tests/server2.config @@ -0,0 +1,46 @@ +{ + "entityid" : "urn:mace:example.com:saml:roland:sp", + "service": { + "sp":{ + "name" : "urn:mace:example.com:saml:roland:sp", + "description": "My own SP", + "endpoints":{ + "assertion_consumer_service": ["http://lingon.catalogix.se:8087/"], + }, + "required_attributes": ["surName", "givenName", "mail"], + "optional_attributes": ["title"], + "idp":{ + "urn:mace:example.com:saml:roland:idp":None, + }, + } + }, + "debug" : 1, + "key_file" : "test.key", + "cert_file" : "test.pem", + "xmlsec_binary" : "/usr/local/bin/xmlsec1", + "metadata": { + "local": ["idp_soap.xml", "vo_metadata.xml"], + }, + "virtual_organization" : { + "urn:mace:example.com:it:tek":{ + "nameid_format" : "urn:oid:1.3.6.1.4.1.1466.115.121.1.15-NameID", + "common_identifier": "umuselin", + } + }, + "subject_data": "subject_data.db", + "accept_time_diff": 60, + "attribute_map_dir" : "attributemaps", + "organization": { + "name": ("AB Exempel", "se"), + "display_name": ("AB Exempel", "se"), + "url": "http://www.example.org", + }, + "contact_person": [{ + "given_name": "Roland", + "sur_name": "Hedberg", + "telephone_number": "+46 70 100 0000", + "email_address": ["tech@example.com", "tech@example.org"], + "contact_type": "technical" + }, + ] +} \ No newline at end of file diff --git a/tests/server3.config b/tests/server3.config new file mode 100644 index 0000000..f89c204 --- /dev/null +++ b/tests/server3.config @@ -0,0 +1,46 @@ +{ + "entityid" : "urn:mace:example.com:saml:roland:sp", + "service": { + "sp":{ + "name" : "urn:mace:example.com:saml:roland:sp", + "description": "My own SP", + "endpoints":{ + "assertion_consumer_service": ["http://lingon.catalogix.se:8087/"], + }, + "required_attributes": ["surName", "givenName", "mail"], + "optional_attributes": ["title"], + "idp":{ + "urn:mace:example.com:saml:roland:idp":None, + }, + } + }, + "debug" : 1, + "key_file" : "test.key", + "cert_file" : "test.pem", + "xmlsec_binary" : "/usr/local/bin/xmlsec1", + "metadata": { + "local": ["idp_aa.xml", "vo_metadata.xml"], + }, + "virtual_organization" : { + "urn:mace:example.com:it:tek":{ + "nameid_format" : "urn:oid:1.3.6.1.4.1.1466.115.121.1.15-NameID", + "common_identifier": "umuselin", + } + }, + "subject_data": "subject_data.db", + "accept_time_diff": 60, + "attribute_map_dir" : "attributemaps", + "organization": { + "name": ("AB Exempel", "se"), + "display_name": ("AB Exempel", "se"), + "url": "http://www.example.org", + }, + "contact_person": [{ + "given_name": "Roland", + "sur_name": "Hedberg", + "telephone_number": "+46 70 100 0000", + "email_address": ["tech@example.com", "tech@example.org"], + "contact_type": "technical" + }, + ] +} \ No newline at end of file diff --git a/tests/test_12_s_utils.py b/tests/test_12_s_utils.py index ba317a7..dfdd894 100644 --- a/tests/test_12_s_utils.py +++ b/tests/test_12_s_utils.py @@ -442,3 +442,12 @@ def test_authn_statement(): assert _eq(ast.keyswv(),["authn_instant","session_index", "session_not_on_or_after", "authn_context"]) + +def test_signature(): + arr = ["foobar", "1234567890"] + csum = utils.signature("abcdef", arr) + arr.append(csum) + + assert utils.verify_signature("abcdef", arr) + + \ No newline at end of file diff --git a/tests/test_32_cache.py b/tests/test_32_cache.py index c305f13..9fc4c41 100644 --- a/tests/test_32_cache.py +++ b/tests/test_32_cache.py @@ -59,8 +59,8 @@ class TestClass: def test_remove_info(self): self.cache.reset("1234", "bcde") - assert self.cache.active("1234","bcde") == False - assert self.cache.active("1234","abcd") + assert self.cache.active("1234", "bcde") == False + assert self.cache.active("1234", "abcd") (ava, inactive) = self.cache.get_identity("1234") assert inactive == ['bcde'] diff --git a/tests/test_44_authnresp.py b/tests/test_44_authnresp.py index a5d9cef..46388e3 100644 --- a/tests/test_44_authnresp.py +++ b/tests/test_44_authnresp.py @@ -4,7 +4,7 @@ from saml2 import samlp, BINDING_HTTP_POST from saml2 import saml, config, class_name, make_instance from saml2.server import Server -from saml2.response import authn_response +from saml2.response import authn_response, StatusResponse XML_RESPONSE_FILE = "saml_signed.xml" XML_RESPONSE_FILE2 = "saml2_response.xml" @@ -45,11 +45,14 @@ class TestAuthnResponse: authn=(saml.AUTHN_PASSWORD, "http://www.example.com/login") ) + self._logout_resp = server.logout_response("id12") + conf = config.Config() try: conf.load_file("tests/server.config") except IOError: conf.load_file("server.config") + self.conf = conf self.ar = authn_response(conf, "urn:mace:example.com:saml:roland:sp", "http://lingon.catalogix.se:8087/") @@ -116,3 +119,4 @@ class TestAuthnResponse: assert authn_info[0][1] == ["http://www.example.com/login"] session_info = self.ar.session_info() assert session_info["authn_info"] == authn_info + diff --git a/tests/test_50_server.py b/tests/test_50_server.py index 9fdb87f..b0faa53 100644 --- a/tests/test_50_server.py +++ b/tests/test_50_server.py @@ -9,6 +9,7 @@ from saml2 import time_util from saml2.s_utils import OtherError from saml2.s_utils import do_attribute_statement, factory from saml2.soap import make_soap_enveloped_saml_thingy +from saml2 import BINDING_HTTP_POST from py.test import raises import shelve @@ -294,7 +295,7 @@ class TestServer1(): # value. Just that there should be one assert assertion.signature.signature_value.text != "" - def test_slo(self): + def test_slo_http_post(self): soon = time_util.in_a_while(days=1) sinfo = { "name_id": "foba0001", @@ -307,13 +308,44 @@ class TestServer1(): } self.client.users.add_information_about_person(sinfo) - (dest, logout_request) = self.client.make_logout_requests( - subject_id = "foba0001", - reason = "I'm tired of this", - )[0] + logout_request = self.client.logout_requests(subject_id = "foba0001", + destination = "http://localhost:8088/slo", + entity_id = "urn:mace:example.com:saml:roland:idp", + reason = "I'm tired of this") + + intermed = s_utils.deflate_and_base64_encode("%s" % (logout_request,)) + + #saml_soap = make_soap_enveloped_saml_thingy(logout_request) + request = self.server.parse_logout_request(intermed, BINDING_HTTP_POST) + assert request + + def test_slo_soap(self): + soon = time_util.in_a_while(days=1) + sinfo = { + "name_id": "foba0001", + "issuer": "urn:mace:example.com:saml:roland:idp", + "not_on_or_after" : soon, + "user": { + "givenName": "Leo", + "surName": "Laport", + } + } + conf = config.Config() + conf.load_file("server2.config") + sp = client.Saml2Client(conf) + + sp.users.add_information_about_person(sinfo) + + logout_request = sp.logout_requests(subject_id = "foba0001", + destination = "http://localhost:8088/slo", + entity_id = "urn:mace:example.com:saml:roland:idp", + reason = "I'm tired of this") + + intermed = s_utils.deflate_and_base64_encode("%s" % (logout_request,)) saml_soap = make_soap_enveloped_saml_thingy(logout_request) - request = self.server.parse_logout_request(saml_soap) + idp = Server("idp_soap.conf") + request = idp.parse_logout_request(saml_soap) assert request #------------------------------------------------------------------------ diff --git a/tests/test_51_client.py b/tests/test_51_client.py index 2c5e683..b407c6c 100644 --- a/tests/test_51_client.py +++ b/tests/test_51_client.py @@ -4,12 +4,16 @@ import base64 from urlparse import urlparse, parse_qs -from saml2.client import Saml2Client -from saml2 import samlp, client, BINDING_HTTP_POST +from saml2.client import Saml2Client, LogoutError +from saml2 import samlp, client, BINDING_HTTP_POST, BINDING_HTTP_REDIRECT +from saml2 import BINDING_SOAP from saml2 import saml, s_utils, config, class_name #from saml2.sigver import correctly_signed_authn_request, verify_signature from saml2.server import Server from saml2.s_utils import decode_base64_and_inflate +from saml2.time_util import in_a_while + +from py.test import raises import os @@ -352,7 +356,7 @@ class TestClient: assert authnreq.destination == "http://localhost:8088/sso" assert authnreq.assertion_consumer_service_url == "http://lingon.catalogix.se:8087/" assert authnreq.provider_name == "urn:mace:example.com:saml:roland:sp" - assert authnreq.protocol_binding == "urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" + assert authnreq.protocol_binding == BINDING_HTTP_POST name_id_policy = authnreq.name_id_policy assert name_id_policy.allow_create == "true" assert name_id_policy.format == "urn:oasis:names:tc:SAML:2.0:nameid-format:transient" @@ -360,5 +364,112 @@ class TestClient: assert issuer.text == "urn:mace:example.com:saml:roland:sp" - # def test_logout_request(self): - \ No newline at end of file + def test_logout_1(self): + """ one IdP/AA with BINDING_HTTP_REDIRECT on single_logout_service""" + + # information about the user from an IdP + session_info = { + "name_id": "123456", + "issuer": "urn:mace:example.com:saml:roland:idp", + "not_on_or_after": in_a_while(minutes=15), + "ava": { + "givenName": "Anders", + "surName": "Andersson", + "mail": "anders.andersson@example.com" + } + } + self.client.users.add_information_about_person(session_info) + entity_ids = self.client.users.issuers_of_info("123456") + assert entity_ids == ["urn:mace:example.com:saml:roland:idp"] + resp = self.client.global_logout("123456", "Tired", in_a_while(minutes=5)) + print resp + assert resp + assert resp[0] # a session_id + assert resp[1] == [('Content-type', 'text/html')] + assert resp[2][0] == '' + assert resp[2][1] == 'SAML 2.0 POST' + session_info = self.client.state[resp[0]] + print session_info + assert session_info["entity_id"] == entity_ids[0] + assert session_info["subject_id"] == "123456" + assert session_info["reason"] == "Tired" + assert session_info["operation"] == "SLO" + assert session_info["entity_ids"] == entity_ids + assert session_info["sign"] == False + + def test_logout_2(self): + """ one IdP/AA with BINDING_SOAP, can't actually send something""" + + conf = config.Config() + conf.load_file("server2.config") + client = Saml2Client(conf) + + # information about the user from an IdP + session_info = { + "name_id": "123456", + "issuer": "urn:mace:example.com:saml:roland:idp", + "not_on_or_after": in_a_while(minutes=15), + "ava": { + "givenName": "Anders", + "surName": "Andersson", + "mail": "anders.andersson@example.com" + } + } + client.users.add_information_about_person(session_info) + entity_ids = self.client.users.issuers_of_info("123456") + assert entity_ids == ["urn:mace:example.com:saml:roland:idp"] + destination = client.config.logout_service(entity_ids[0], BINDING_SOAP) + print destination + assert destination == 'http://localhost:8088/slo' + + # Will raise an error since there is noone at the other end. + raises(LogoutError, 'client.global_logout("123456", "Tired", in_a_while(minutes=5))') + + def test_logout_3(self): + """ two or more IdP/AA with BINDING_HTTP_REDIRECT""" + + conf = config.Config() + conf.load_file("server3.config") + client = Saml2Client(conf) + + # information about the user from an IdP + session_info_authn = { + "name_id": "123456", + "issuer": "urn:mace:example.com:saml:roland:idp", + "not_on_or_after": in_a_while(minutes=15), + "ava": { + "givenName": "Anders", + "surName": "Andersson", + "mail": "anders.andersson@example.com" + } + } + client.users.add_information_about_person(session_info_authn) + session_info_aa = { + "name_id": "123456", + "issuer": "urn:mace:example.com:saml:roland:aa", + "not_on_or_after": in_a_while(minutes=15), + "ava": { + "eduPersonEntitlement": "Foobar", + } + } + client.users.add_information_about_person(session_info_aa) + entity_ids = client.users.issuers_of_info("123456") + assert _leq(entity_ids, ["urn:mace:example.com:saml:roland:idp", + "urn:mace:example.com:saml:roland:aa"]) + resp = client.global_logout("123456", "Tired", in_a_while(minutes=5)) + print resp + assert resp + assert resp[0] # a session_id + # HTTP POST + assert resp[1] == [('Content-type', 'text/html')] + assert resp[2][0] == '' + assert resp[2][1] == 'SAML 2.0 POST' + + state_info = client.state[resp[0]] + print state_info + assert state_info["entity_id"] == entity_ids[0] + assert state_info["subject_id"] == "123456" + assert state_info["reason"] == "Tired" + assert state_info["operation"] == "SLO" + assert state_info["entity_ids"] == entity_ids + assert state_info["sign"] == False diff --git a/tests/test_60_sp.py b/tests/test_60_sp.py index 4b193d8..c6de169 100644 --- a/tests/test_60_sp.py +++ b/tests/test_60_sp.py @@ -48,10 +48,8 @@ class TestSP(): resp_str = "\n".join(self.server.authn_response(ava, "id1", "http://lingon.catalogix.se:8087/", "urn:mace:example.com:saml:roland:sp", - make_instance(samlp.NameIDPolicy, - utils.args2dict( - format=saml.NAMEID_FORMAT_TRANSIENT, - allow_create="true")), + samlp.NameIDPolicy(format=saml.NAMEID_FORMAT_TRANSIENT, + allow_create="true"), "foba0001@example.com")) resp_str = base64.encodestring(resp_str)