示例#1
0
def test_class_instances_from_soap_enveloped_saml_thingies_xxe():
    xml = """<?xml version="1.0"?>
    <!DOCTYPE lolz [
    <!ENTITY lol "lol">
    <!ELEMENT lolz (#PCDATA)>
    <!ENTITY lol1 "&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;">
    ]>
    <lolz>&lol1;</lolz>
    """
    with raises(soap.XmlParseError):
        soap.class_instances_from_soap_enveloped_saml_thingies(xml, None)
示例#2
0
def test_class_instances_from_soap_enveloped_saml_thingies_xxe():
    xml = """<?xml version="1.0"?>
    <!DOCTYPE lolz [
    <!ENTITY lol "lol">
    <!ELEMENT lolz (#PCDATA)>
    <!ENTITY lol1 "&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;">
    ]>
    <lolz>&lol1;</lolz>
    """
    with raises(soap.XmlParseError):
        soap.class_instances_from_soap_enveloped_saml_thingies(xml, None)
示例#3
0
    def parse_soap_message(text):
        """

        :param text: The SOAP message
        :return: A dictionary with two keys "body" and "header"
        """
        return class_instances_from_soap_enveloped_saml_thingies(
            text, [paos, ecp, samlp])
示例#4
0
文件: entity.py 项目: gbel/pysaml2
    def parse_soap_message(self, text):
        """

        :param text: The SOAP message
        :return: A dictionary with two keys "body" and "header"
        """
        return class_instances_from_soap_enveloped_saml_thingies(text, [paos,
                                                                        ecp,
                                                                        samlp])
示例#5
0
    def parse_ecp_authn_response(self, txt, outstanding=None):
        rdict = soap.class_instances_from_soap_enveloped_saml_thingies(
            txt, [paos, ecp, samlp])

        _relay_state = None
        for item in rdict["header"]:
            if item.c_tag == "RelayState" and \
                            item.c_namespace == ecp.NAMESPACE:
                _relay_state = item

        response = self.parse_authn_request_response(rdict["body"],
                                                     BINDING_PAOS, outstanding)

        return response, _relay_state
示例#6
0
    def parse_ecp_authn_response(self, txt, outstanding=None):
        rdict = soap.class_instances_from_soap_enveloped_saml_thingies(txt,
                                                                       [paos,
                                                                        ecp,
                                                                        samlp])

        _relay_state = None
        for item in rdict["header"]:
            if item.c_tag == "RelayState" and\
                    item.c_namespace == ecp.NAMESPACE:
                _relay_state = item

        response = self.parse_authn_request_response(rdict["body"],
                                                     BINDING_PAOS, outstanding)

        return response, _relay_state
示例#7
0
文件: ecp.py 项目: lorenzogil/pysaml2
def handle_ecp_authn_response(cls, soap_message, outstanding=None):
    rdict = soap.class_instances_from_soap_enveloped_saml_thingies(
        soap_message, [paos, ecp, samlp])

    _relay_state = None
    for item in rdict["header"]:
        if item.c_tag == "RelayState" and item.c_namespace == ecp.NAMESPACE:
            _relay_state = item

    response = authn_response(cls.config, cls.service_url(), outstanding,
                              allow_unsolicited=True)

    response.loads("%s" % rdict["body"], False, soap_message)
    response.verify()
    cls.users.add_information_about_person(response.session_info())

    return response, _relay_state
示例#8
0
def handle_ecp_authn_response(cls, soap_message, outstanding=None):
    rdict = soap.class_instances_from_soap_enveloped_saml_thingies(
        soap_message, [paos, ecp, samlp])

    _relay_state = None
    for item in rdict["header"]:
        if item.c_tag == "RelayState" and item.c_namespace == ecp.NAMESPACE:
            _relay_state = item

    response = authn_response(cls.config, cls.service_url(), outstanding,
                              allow_unsolicited=True)

    response.loads("%s" % rdict["body"], False, soap_message)
    response.verify()
    cls.users.add_information_about_person(response.session_info())

    return response, _relay_state
示例#9
0
 def test_ecp_authn(self):
     ssid, soap_req = ecp.ecp_auth_request(self.client,
                                         "urn:mace:example.com:saml:roland:idp",
                                         "id1")
     print soap_req
     response = soap.class_instances_from_soap_enveloped_saml_thingies(
                                                                 soap_req,
                                                                 [paos,
                                                                  ecp_prof,
                                                                  samlp])
     print response
     assert len(response["header"]) == 2
     assert response["body"].c_tag == "AuthnRequest"
     assert response["body"].c_namespace == samlp.NAMESPACE
     headers = ["{%s}%s" % (i.c_namespace,
                            i.c_tag) for i in response["header"]]
     print headers
     assert _eq(headers,['{urn:liberty:paos:2003-08}Request',
                 #'{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}Request',
                 '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}RelayState'])
示例#10
0
 def test_ecp_authn(self):
     ssid, soap_req = ecp.ecp_auth_request(
         self.client, "urn:mace:example.com:saml:roland:idp", "id1")
     print soap_req
     response = soap.class_instances_from_soap_enveloped_saml_thingies(
         soap_req, [paos, ecp_prof, samlp])
     print response
     assert len(response["header"]) == 2
     assert response["body"].c_tag == "AuthnRequest"
     assert response["body"].c_namespace == samlp.NAMESPACE
     headers = [
         "{%s}%s" % (i.c_namespace, i.c_tag) for i in response["header"]
     ]
     print headers
     assert _eq(
         headers,
         [
             '{urn:liberty:paos:2003-08}Request',
             #'{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}Request',
             '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}RelayState'
         ])
示例#11
0
def test_multiple_soap_headers():
    xml_str = open("ecp_soap.xml").read()
    res = soap.class_instances_from_soap_enveloped_saml_thingies(
        xml_str, [ecp_prof, paos, samlp])

    assert res["body"].c_tag == "AuthnRequest"

    assert len(res["header"]) == 3
    headers = ["{%s}%s" % (i.c_namespace, i.c_tag) for i in res["header"]]
    print headers
    assert _eq(headers, [
        '{urn:liberty:paos:2003-08}Request',
        '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}Request',
        '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}RelayState'
    ])

    _relay_state = None

    for item in res["header"]:
        if item.c_tag == "RelayState" and item.c_namespace == ecp_prof.NAMESPACE:
            _relay_state = item

    assert _relay_state
    assert _relay_state.actor == "http://schemas.xmlsoap.org/soap/actor/next"
示例#12
0
def test_multiple_soap_headers():
    xml_str = open("ecp_soap.xml").read()
    res = soap.class_instances_from_soap_enveloped_saml_thingies(xml_str,
                                                                 [ecp_prof,
                                                                  paos,
                                                                  samlp])

    assert res["body"].c_tag == "AuthnRequest"

    assert len(res["header"]) == 3
    headers = ["{%s}%s" % (i.c_namespace, i.c_tag) for i in res["header"]]
    print headers
    assert _eq(headers,['{urn:liberty:paos:2003-08}Request',
                        '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}Request',
                        '{urn:oasis:names:tc:SAML:2.0:profiles:SSO:ecp}RelayState'])

    _relay_state = None

    for item in res["header"]:
        if item.c_tag == "RelayState" and item.c_namespace == ecp_prof.NAMESPACE:
            _relay_state = item

    assert _relay_state
    assert _relay_state.actor == "http://schemas.xmlsoap.org/soap/actor/next"
示例#13
0
文件: ecp_client.py 项目: GSA/pysaml2
    def operation(self, idp_entity_id, op, **opargs):
        if "path" not in opargs:
            opargs["path"] = self._sp

        # ********************************************
        # Phase 1 - First conversation with the SP
        # ********************************************
        # headers needed to indicate to the SP that I'm ECP enabled

        if "headers" in opargs and opargs["headers"]:
            opargs["headers"]["PAOS"] = PAOS_HEADER_INFO
            if "Accept" in opargs["headers"]:
                opargs["headers"]["Accept"] += ";application/vnd.paos+xml"
            elif "accept" in opargs["headers"]:
                opargs["headers"]["Accept"] = opargs["headers"]["accept"]
                opargs["headers"]["Accept"] += ";application/vnd.paos+xml"
                del opargs["headers"]["accept"]
        else:
            opargs["headers"] = {
                'Accept': 'text/html; application/vnd.paos+xml',
                'PAOS': PAOS_HEADER_INFO
            }

        # request target from SP
        # can remove the PAOS header now
#        try:
#            del opargs["headers"]["PAOS"]
#        except KeyError:
#            pass
        
        response = op(**opargs)
        self._debug_info("[Op] SP response: %s" % response)

        if not response:
            raise Exception(
                "Request to SP failed: %s" % self.http.error_description)

        # The response might be a AuthnRequest instance in a SOAP envelope
        # body. If so it's the start of the ECP conversation
        # Two SOAP header blocks; paos:Request and ecp:Request
        # may also contain a ecp:RelayState SOAP header block
        # If channel-binding was part of the PAOS header any number of
        # <cb:ChannelBindings> header blocks may also be present
        # if 'holder-of-key' option then one or more <ecp:SubjectConfirmation>
        # header blocks may also be present
        try:
            respdict = soap.class_instances_from_soap_enveloped_saml_thingies(
                                                response,[paos, ecp,samlp])
            self.ecp_conversation(respdict, idp_entity_id)
            # should by now be authenticated so this should go smoothly
            response = op(**opargs)
        except (soap.XmlParseError, AssertionError, KeyError):
            pass

        #print "RESP",response, self.http.response

        if not response:
            if  self.http.response.status != 404:
                raise Exception("Error performing operation: %s" % (
                    self.http.error_description,))

        return response
示例#14
0
文件: ecp_client.py 项目: GSA/pysaml2
    def phase2(self, authn_request, rc_url, idp_entity_id, headers=None,
               idp_endpoint=None, sign=False, sec=""):
        """
        Doing the second phase of the ECP conversation

        :param authn_request: The AuthenticationRequest
        :param rc_url: The assertion consumer service url
        :param idp_entity_id: The EntityID of the IdP
        :param headers: Possible extra headers
        :param idp_endpoint: Where to send it all
        :param sign: If the message should be signed
        :param sec: security context
        :return: The response from the IdP
        """
        idp_request = soap.make_soap_enveloped_saml_thingy(authn_request)
        if sign:
            _signed = sec.sign_statement_using_xmlsec(idp_request,
                                                      class_name(authn_request),
                                                      nodeid=authn_request.id)
            idp_request = _signed

        if not idp_endpoint:
            idp_endpoint = self.find_idp_endpoint(idp_entity_id)

        if self.user and self.passwd:
            self.http.add_credentials(self.user, self.passwd)

        self._debug_info("[P2] Sending request: %s" % idp_request)
            
        # POST the request to the IdP
        response = self.http.post(idp_request, headers=headers,
                                  path=idp_endpoint)

        self._debug_info("[P2] Got IdP response: %s" % response)

        if response is None or response is False:
            raise Exception(
                "Request to IdP failed (%s): %s" % (self.http.response.status,
                                                self.http.error_description))

        # SAMLP response in a SOAP envelope body, ecp response in headers
        respdict = soap.class_instances_from_soap_enveloped_saml_thingies(
                                                response, [paos, ecp,samlp])

        if respdict is None:
            raise Exception("Unexpected reply from the IdP")

        self._debug_info("[P2] IdP response dict: %s" % respdict)

        idp_response = respdict["body"]
        assert idp_response.c_tag == "Response"

        self._debug_info("[P2] IdP AUTHN response: %s" % idp_response)

        _ecp_response = None
        for item in respdict["header"]:
            if item.c_tag == "Response" and\
               item.c_namespace == ecp.NAMESPACE:
                _ecp_response = item

        _acs_url = _ecp_response.assertion_consumer_service_url
        if rc_url != _acs_url:
            error = ("response_consumer_url '%s' does not match" % rc_url,
                     "assertion_consumer_service_url '%s" % _acs_url)
            # Send an error message to the SP
            fault_text = soap.soap_fault(error)
            _ = self.http.post(fault_text, path=rc_url)
            # Raise an exception so the user knows something went wrong
            raise Exception(error)
        
        return idp_response
示例#15
0
    def operation(self, idp_entity_id, op, **opargs):
        if "path" not in opargs:
            opargs["path"] = self._sp

        # ********************************************
        # Phase 1 - First conversation with the SP
        # ********************************************
        # headers needed to indicate to the SP that I'm ECP enabled

        if "headers" in opargs and opargs["headers"]:
            opargs["headers"]["PAOS"] = PAOS_HEADER_INFO
            if "Accept" in opargs["headers"]:
                opargs["headers"]["Accept"] += ";application/vnd.paos+xml"
            elif "accept" in opargs["headers"]:
                opargs["headers"]["Accept"] = opargs["headers"]["accept"]
                opargs["headers"]["Accept"] += ";application/vnd.paos+xml"
                del opargs["headers"]["accept"]
        else:
            opargs["headers"] = {
                'Accept': 'text/html; application/vnd.paos+xml',
                'PAOS': PAOS_HEADER_INFO
            }

        # request target from SP
        # can remove the PAOS header now
#        try:
#            del opargs["headers"]["PAOS"]
#        except KeyError:
#            pass

        response = op(**opargs)
        self._debug_info("[Op] SP response: %s" % response)

        if not response:
            raise Exception("Request to SP failed: %s" %
                            self.http.error_description)

        # The response might be a AuthnRequest instance in a SOAP envelope
        # body. If so it's the start of the ECP conversation
        # Two SOAP header blocks; paos:Request and ecp:Request
        # may also contain a ecp:RelayState SOAP header block
        # If channel-binding was part of the PAOS header any number of
        # <cb:ChannelBindings> header blocks may also be present
        # if 'holder-of-key' option then one or more <ecp:SubjectConfirmation>
        # header blocks may also be present
        try:
            respdict = soap.class_instances_from_soap_enveloped_saml_thingies(
                response, [paos, ecp, samlp])
            self.ecp_conversation(respdict, idp_entity_id)
            # should by now be authenticated so this should go smoothly
            response = op(**opargs)
        except (soap.XmlParseError, AssertionError, KeyError):
            pass

        #print "RESP",response, self.http.response

        if not response:
            if self.http.response.status != 404:
                raise Exception("Error performing operation: %s" %
                                (self.http.error_description, ))

        return response
示例#16
0
    def phase2(self,
               authn_request,
               rc_url,
               idp_entity_id,
               headers=None,
               idp_endpoint=None,
               sign=False,
               sec=""):
        """
        Doing the second phase of the ECP conversation

        :param authn_request: The AuthenticationRequest
        :param rc_url: The assertion consumer service url
        :param idp_entity_id: The EntityID of the IdP
        :param headers: Possible extra headers
        :param idp_endpoint: Where to send it all
        :param sign: If the message should be signed
        :param sec: security context
        :return: The response from the IdP
        """
        idp_request = soap.make_soap_enveloped_saml_thingy(authn_request)
        if sign:
            _signed = sec.sign_statement_using_xmlsec(
                idp_request,
                class_name(authn_request),
                nodeid=authn_request.id)
            idp_request = _signed

        if not idp_endpoint:
            idp_endpoint = self.find_idp_endpoint(idp_entity_id)

        if self.user and self.passwd:
            self.http.add_credentials(self.user, self.passwd)

        self._debug_info("[P2] Sending request: %s" % idp_request)

        # POST the request to the IdP
        response = self.http.post(idp_request,
                                  headers=headers,
                                  path=idp_endpoint)

        self._debug_info("[P2] Got IdP response: %s" % response)

        if response is None or response is False:
            raise Exception(
                "Request to IdP failed (%s): %s" %
                (self.http.response.status, self.http.error_description))

        # SAMLP response in a SOAP envelope body, ecp response in headers
        respdict = soap.class_instances_from_soap_enveloped_saml_thingies(
            response, [paos, ecp, samlp])

        if respdict is None:
            raise Exception("Unexpected reply from the IdP")

        self._debug_info("[P2] IdP response dict: %s" % respdict)

        idp_response = respdict["body"]
        assert idp_response.c_tag == "Response"

        self._debug_info("[P2] IdP AUTHN response: %s" % idp_response)

        _ecp_response = None
        for item in respdict["header"]:
            if item.c_tag == "Response" and\
               item.c_namespace == ecp.NAMESPACE:
                _ecp_response = item

        _acs_url = _ecp_response.assertion_consumer_service_url
        if rc_url != _acs_url:
            error = ("response_consumer_url '%s' does not match" % rc_url,
                     "assertion_consumer_service_url '%s" % _acs_url)
            # Send an error message to the SP
            fault_text = soap.soap_fault(error)
            _ = self.http.post(fault_text, path=rc_url)
            # Raise an exception so the user knows something went wrong
            raise Exception(error)

        return idp_response