def __init__(self, code=None, headers=None, stream=None): """ @param code: The HTTP status code for this Response @type code: C{int} @param headers: Headers to be sent to the client. @type headers: C{dict}, L{ipython1.external.twisted.web2.http_headers.Headers}, or C{None} @param stream: Content body to send to the HTTP client @type stream: L{ipython1.external.twisted.web2.stream.IByteStream} """ if code is not None: self.code = int(code) if headers is not None: if isinstance(headers, dict): headers = http_headers.Headers(headers) self.headers = headers else: self.headers = http_headers.Headers() if stream is not None: self.stream = IByteStream(stream)
def makeRequest(self, vars): headers = http_headers.Headers() http_vers = http.parseVersion(vars['SERVER_PROTOCOL']) if http_vers[0] != 'http' or http_vers[1] > 1: _abortWithError(responsecode.INTERNAL_SERVER_ERROR, "Twisted.web CGITransport: Unknown HTTP version: " % vars['SERVER_PROTOCOL']) secure = vars.get("HTTPS") in ("1", "on") # apache extension? port = vars.get('SERVER_PORT') or 80 server_host = vars.get('SERVER_NAME') or vars.get('SERVER_ADDR') or 'localhost' self.hostinfo = address.IPv4Address('TCP', server_host, port), bool(secure) self.remoteinfo = address.IPv4Address( 'TCP', vars.get('REMOTE_ADDR', ''), vars.get('REMOTE_PORT', 0)) uri = vars.get('REQUEST_URI') # apache extension? if not uri: qstr = vars.get('QUERY_STRING', '') if qstr: qstr = "?"+urllib.quote(qstr, safe="") uri = urllib.quote(vars['SCRIPT_NAME'])+urllib.quote(vars.get('PATH_INFO', ''))+qstr for name,val in vars.iteritems(): if name.startswith('HTTP_'): name = name[5:].replace('_', '-') elif name == 'CONTENT_TYPE': name = 'content-type' else: continue headers.setRawHeaders(name, (val,)) self._dataRemaining = int(vars.get('CONTENT_LENGTH', '0')) self.request = self.requestFactory(self, vars['REQUEST_METHOD'], uri, http_vers[1:3], self._dataRemaining, headers, prepathuri=vars['SCRIPT_NAME'])
def __init__(self, method, uri, headers, stream): """ @param method: The HTTP method to for this request, ex: 'GET', 'HEAD', 'POST', etc. @type method: C{str} @param uri: The URI of the resource to request, this may be absolute or relative, however the interpretation of this URI is left up to the remote server. @type uri: C{str} @param headers: Headers to be sent to the server. It is important to note that this object does not create any implicit headers. So it is up to the HTTP Client to add required headers such as 'Host'. @type headers: C{dict}, L{ipython1.external.twisted.web2.http_headers.Headers}, or C{None} @param stream: Content body to send to the remote HTTP server. @type stream: L{ipython1.external.twisted.web2.stream.IByteStream} """ self.method = method self.uri = uri if isinstance(headers, http_headers.Headers): self.headers = headers else: self.headers = http_headers.Headers(headers or {}) if stream is not None: self.stream = stream_mod.IByteStream(stream) else: self.stream = None
def _abortWithError(self, errorcode, text=''): """Handle low level protocol errors.""" headers = http_headers.Headers() headers.setHeader('content-length', len(text) + 1) self.abortConnection(closeWrite=False) self.writeHeaders(errorcode, headers) self.write(text) self.write("\n") self.finish() raise AbortedException
def NotModifiedResponse(oldResponse=None): if oldResponse is not None: headers = http_headers.Headers() for header in ( # Required from sec 10.3.5: 'date', 'etag', 'content-location', 'expires', 'cache-control', 'vary', # Others: 'server', 'proxy-authenticate', 'www-authenticate', 'warning'): value = oldResponse.headers.getRawHeaders(header) if value is not None: headers.setRawHeaders(header, value) else: headers = None return Response(code=responsecode.NOT_MODIFIED, headers=headers)
def _set(self, newheaders): headers = http_headers.Headers() for n, v in newheaders.items(): headers.setRawHeaders(n, (v, )) newheaders = headers getattr(self, where).headers = newheaders
def __init__(self, channel): self.inHeaders = http_headers.Headers() self.channel = channel
def splitConnectionHeaders(self): """ Split off connection control headers from normal headers. The normal headers are then passed on to user-level code, while the connection headers are stashed in .connHeaders and used for things like request/response framing. This corresponds roughly with the HTTP RFC's description of 'hop-by-hop' vs 'end-to-end' headers in RFC2616 S13.5.1, with the following exceptions: * proxy-authenticate and proxy-authorization are not treated as connection headers. * content-length is, as it is intimiately related with low-level HTTP parsing, and is made available to user-level code via the stream length, rather than a header value. (except for HEAD responses, in which case it is NOT used by low-level HTTP parsing, and IS kept in the normal headers. """ def move(name): h = inHeaders.getRawHeaders(name, None) if h is not None: inHeaders.removeHeader(name) connHeaders.setRawHeaders(name, h) # NOTE: According to HTTP spec, we're supposed to eat the # 'Proxy-Authenticate' and 'Proxy-Authorization' headers also, but that # doesn't sound like a good idea to me, because it makes it impossible # to have a non-authenticating transparent proxy in front of an # authenticating proxy. An authenticating proxy can eat them itself. # # 'Proxy-Connection' is an undocumented HTTP 1.0 abomination. connHeaderNames = [ 'content-length', 'connection', 'keep-alive', 'te', 'trailers', 'transfer-encoding', 'upgrade', 'proxy-connection' ] inHeaders = self.inHeaders connHeaders = http_headers.Headers() move('connection') if self.version < (1, 1): # Remove all headers mentioned in Connection, because a HTTP 1.0 # proxy might have erroneously forwarded it from a 1.1 client. for name in connHeaders.getHeader('connection', ()): if inHeaders.hasHeader(name): inHeaders.removeHeader(name) else: # Otherwise, just add the headers listed to the list of those to move connHeaderNames.extend(connHeaders.getHeader('connection', ())) # If the request was HEAD, self.length has been set to 0 by # HTTPClientRequest.submit; in this case, Content-Length should # be treated as a response header, not a connection header. # Note: this assumes the invariant that .length will always be None # coming into this function, unless this is a HEAD request. if self.length is not None: connHeaderNames.remove('content-length') for headername in connHeaderNames: move(headername) return connHeaders
def render(self, req): return http.Response( responsecode.OK, http_headers.Headers({'content-type': self.contentType()}), stream=self.data)