'Send soap message.
@param soapenv: A soap envelope to send.
@type soapenv: L{Document}
@return: The reply to the sent message.
@rtype: I{builtin} or I{subclass of} L{Object}'

def send(self, soapenv):

    result = None
    location = self.location()
    binding = self.method.binding.input
    transport = self.options.transport
    retxml = self.options.retxml
    prettyxml = self.options.prettyxml
    log.debug('sending    to    (%s)\nmessage:\n%s', location, soapenv)
    try:
        self.last_sent(soapenv)
        plugins = PluginContainer(self.options.plugins)
        plugins.message.marshalled(envelope=soapenv.root())
        if prettyxml:
            soapenv = soapenv.str()
        else:
            soapenv = soapenv.plain()
        soapenv = soapenv.encode('utf-8')
        plugins.message.sending(envelope=soapenv)
        request = Request(location, soapenv)
        request.headers = self.headers()
        reply = transport.send(request)
        ctx = plugins.message.received(reply=reply.message)
        reply.message = ctx.reply
        if retxml:
            result = reply.message
        else:
            result = self.succeeded(binding, reply.message)
    except TransportError as e:
        if (e.httpcode in (202, 204)):
            result = None
        else:
            log.error(self.last_sent())
            result = self.failed(binding, e)
    return result
