Example #1
0
 def handle_error(fail):
     if fail.check(error.Error):
         err = fail.value
         status = int(err.status)
         if not mpost and status == http.NOT_ALLOWED:
             # new attempt
             # don't pass the deferred here, because we're already
             # within the callback/errback chain
             return send_soap_message_deferred(url, msg, mpost=True)
         elif status == http.INTERNAL_SERVER_ERROR:
             # return to the callback chain
             return SoapError.parse(err.response)
     log.err(fail, "Failed to send SOAP message to %s" % (url, ))
     fail.raiseException()
Example #2
0
def send_soap_message(url, msg, mpost=False):
    """
    Send a SOAP message to the given URL.
    
    The HTTP headers mandated by the UPnP specification are added. Also, if
    posting fails with a 405 error, another attempt is made with slightly
    different headers and method set to M-POST.

    Return a SoapMessage or a SoapError, depending on the outcome of the call.

    Raise a urllib2.URLError or a urllib2.HTTPError if something goes wrong.

    """
    req = MPOSTRequest(url) if mpost else urllib2.Request(url)

    # add headers to the request
    req.add_header('CONTENT-TYPE', 'text/xml; charset="utf-8"')
    req.add_header('USER-AGENT', 'OS/1.0 UPnP/1.0 airpnp/1.0')
    if mpost:
        req.add_header('MAN',
                       '"http://schemas.xmlsoap.org/soap/envelope/"; ns=01')
        req.add_header('01-SOAPACTION', msg.get_header())
    else:
        req.add_header('SOAPACTION', msg.get_header())

    # add the SOAP message as data
    req.add_data(msg.tostring().encode("utf-8"))

    try:
        handle = urllib2.urlopen(req)
        response = SoapMessage.parse(handle)
    except urllib2.HTTPError, err:
        if err.code == 405 and not mpost:
            log.msg('Got 405 response in response to SOAP message, trying' +
                    'the M-POST way', ll=2)
            return send_soap_message(url, msg, True)
        elif err.code == 500:
            # SOAP error
            response = SoapError.parse(err.read())
        else:
            log.err(err, 'Failed to send SOAP message')
            raise err