blob: f57a8b2380b55bfaaa1ae4007af5f4688771a072 [file] [log] [blame]
- 0.0.0.0 / IPv6.
- Speed tweaking.
- Anticipate multivalue and single-value-only headers in request headers in
parser.py.
- Timeout functests.
- Complex pipelining functests (with intermediate connection: close).
- Killthreads support.
- "TCP segment of a reassembled PDU" in wireshark.
- Jim F. would like the server to log request start, request queue (to thread
pool), app start, app finish, and request finish (all data has been
flushed to client) events.
Some challenges exist trying to divine per-request end time. We currently
have the potential for request pipelining; the channel might service more
than one request before it closes. We currently don't preserve any
information about which request a response's data belongs to while flushing
response data from a connection's output buffer.
While accepting request data from a client, Waitress will obtain N request
bodies and schedule all the requests it receives with the task manager.
For example, if it obtains two request bodies in a single recv() call it
will create two request objects and schedule *both* of these requests to be
serviced by the task manager immediately.
The task thread manager will service these synchronously: the first request
will be run first, then the second. When the first request runs, it will
push data to the out buffer, then it will end. Then the second request
will run, and push data to the same out buffer, and it will end. While
these requests are executing, the channel from whence they came stops
accepting requests until the previously scheduled requests have actually
been serviced. The request-burdened channel will be *sending* data to the
client while the requests are being serviced, it just won't accept any more
data until existing requests have been serviced. In the meantime, other
channels may still be generating requests and adding tasks to the task
manager.
To capture request-end time we could create an output buffer per request or
we could keep a dictionary of the final bytestream position of the
outbuffer for each response to to request id; either would be a
straightforward way to capture the fact that a particular request's
response data has been flushed. We currently don't do that though.
Here's what we can currently log without changing anything:
An example of the events logged for a connection that receives two requests
and each request succeeds, and the connection is closed after sending all
data::
channel created: channel 1 at time 10
request created: channel 1, request id 1 at time 11
request created: channel 1, request id 2 at time 12
channel requests queued: channel 1, request ids 1,2 at time 13
request started: request id 1 at time 14
request serviced: request id 1 at time 15
request started: request id 2 at time 16
request serviced: request id 2 at time 17
channel closed: channel 1 at time 18
An example of the events logged for a connection that receives two requests
and the first request fails in such a way that the next request cannot
proceed (content-length header of the first response does not match number
of bytes sent in response to the first request, for example)::
channel created: channel 1 at time 10
request created: channel 1, request id 1 at time 11
request created: channel 1, request id 2 at time 12
channel requests queued: channel 1, request ids 1,2 at time 13
request started: request id 1 at time 14
request serviced: request id 1 at time 15
request cancelled: request id 2 at time 17
channel closed: channel 1 at time 18
An example of the events logged for a connection that receives four
requests (which all succeed in generating successful responses) but where
the client waits for the first two responses to send the second two
requests:
channel created: channel 1 at time 10
request created: channel 1, request id 1 at time 11
request created: channel 1, request id 2 at time 12
channel requests queued: channel 1, request ids 1,2 at time 13
request started: request id 1 at time 14
request serviced: request id 1 at time 15
request started: request id 2 at time 15
request serviced: request id 2 at time 16
request created: channel 1, request id 3 at time 17
request created: channel 1, request id 4 at time 18
channel requests queued: channel 1, request ids 3,4 at time 18
request started: request id 3 at time 19
request serviced: request id 3 at time 20
request started: request id 4 at time 21
request serviced: request id 4 at time 22
channel closed: channel 1 at time 23