From: Gustaf N. <ne...@wu...> - 2006-01-03 21:57:27
|
Stephen Deasey wrote: >> The driver thread gets the connection and reads all up to maxreadahead. >> It then passes the connection to the conn thread. >> The conn thread decides to run that connection entirely (POST of a >> simple form >> or GET, all content read-in) OR it decides to pass the connection to the >> spooling thread(s). >> > > > What happens to the conn thread after this? It can't wait for > completion, that would defeat the purpose. > > Do traces (logging etc.) run now, in the conn thread, or later in a > spool thread? If logging runs now, but the upload fails, the log will > be wrong. If traces run in the spool threads they may block. > > In my setup, we have currently the spooling thread just for sending data. The code sent yesterday is a replacement for ns_returnfile. The connection thread finishes asynchronously, before all data is spooled. This means, that the connection thread finishes after it delegates the file delivery to the spool-thread. In order to get the correct sent-content-length in the logfile, i had to set (somewhat optimistic) the sent-contentlength manually. The traces are run immediately after the delegation. So the request lifecycle (state flow) for get request for a large file is currently accept(DT) -> preauth(CT) -> postauth(CT) -> procs(CT) -> trace(CT) -> spool(ST) DT: driver thread, CT: connection thread, ST: spool thread To make the implementation cleaner, it would preferable to provide means to pass the connection + context back to a connection thread that should run the final trace accept(DT) -> preauth(CT1) -> postauth(CT1) -> procs(CT1) -> spool(ST) -> trace(CT2) i would think, that if we can solve this part cleanly, the upload would work with the same mechanism. if the states are handled explicitely, one could think about a tcl command ns_enqueue $state $client_data that will enqueue a job for the connection thread pools, containing the state, file where the connection should continue together with a tcl stucture client_data that passes around connection specific context information (e.g user_id, ...) and the information from ns_conn (socket, head info, ..). For the example above, there would be an (implicit) ns_enqueue preauth "" issued from the driver thread, an ns_spool send $filename (or $fd) $context to pass the control to the spooling-thread, an ns_enqueue trace $context issued from the spooling trace to pass control back to a connection thread. > If further processing must be done after upload, does the spool thread > pass control back to a conn thread? Does this look like a new > request? The state of any running Tcl script will be lost at this > point (the conn thread will have cleaned up after hand-off to a spool > thread, right?). > upload could be done with the same machanisms_ 1) driver thread: request-head processing 2) start connection thread with a new filter (e.g. request-head) 3) the request-head filter will call pass control to the spooling-thread (e.g. ns_spool receive $length $context) 4) when the spool file is fully received (e.g. fcopy -command-callback) it enqueues the request for the connection threads (e.g. ns_enqueue preauth $context). 5) the connection thread obtains the context starts request processing as usual in the preauth state (start preauth, postauth, trace, ... unless control is passed back to the spool threads) So the request lifecycle (state flow) for a file upload could be: accept(DT) -> request-head(CT1) -> spool(ST) -> preauth(CT2) -> postauth(CT2) -> procs(CT2) -> trace(CT2) i would think that with the two commands ns_enqueue and ns_spool, which switch the control flow between connection threads and spooling threads and copy connection state information (from ns_conn) and client_data, one would have a very flexible framework. -gustaf PS: this model would be still compatible with aolserver, but would require that e.g. authentification code will be called from the request-head filter callback as well as from the preauth callback (maybe avoided by data in the client_data) Moving preauth and postauth to CT1 would be logically cleaner, but might be incompatible with aolserver, since these callback might want already to access the posted data. |