def _finish(self): self.channel.reply_code=self.status DebugLogger.log('A', id(self.channel), '%d %d' % ( self.status, self.stdout.length)) t=self._tempfile if t is not None: self.stdout.write((file_close_producer(t), 0)) self._tempfile=None self.channel.sendStreamTerminator(FCGI_STDOUT) self.channel.sendEndRecord() self.stdout.close() self.stderr.close() if not self.channel.closed: self.channel.push_with_producer(LoggingProducer(self.channel, self.stdout.length, 'log_request'), 0) if self._shutdownRequested(): self.channel.push(ShutdownProducer(), 0) Wakeup(lambda: asyncore.close_all()) else: self.channel.push(None,0) Wakeup() self.channel=None
def close(self): DebugLogger.log('A', id(self._request), '%s %s' % (self._request.reply_code, self._bytes)) if not self._channel.closed: self._channel.push(LoggingProducer(self._request, self._bytes), 0) self._channel.push(CallbackProducer(self._channel.done), 0) self._channel.push(CallbackProducer( lambda t=('E', id(self._request)): apply(DebugLogger.log, t)), 0) if self._shutdown: self._channel.push(ShutdownProducer(), 0) Wakeup() else: if self._close: self._channel.push(None, 0) Wakeup() else: # channel closed too soon self._request.log(self._bytes) DebugLogger.log('E', id(self._request)) if self._shutdown: Wakeup(lambda: asyncore.close_all()) else: Wakeup() self._channel=None #need to break cycles? self._request=None
def close(self): if not self._channel.closed: data = self._data.getvalue() l = len(data) DebugLogger.log('A', id(self._channel), '%s %s' % (self._channel.reply_code, l)) self._channel.push('%010d%s%010d' % (l, data, 0), 0) self._channel.push( LoggingProducer(self._channel, l, 'log_request'), 0) self._channel.push( CallbackProducer(lambda t=('E', id(self._channel)): apply( DebugLogger.log, t)), 0) if self._shutdown: try: r = self._shutdown[0] except: r = 0 ZServer.exit_code = r self._channel.push(ShutdownProducer(), 0) Wakeup(lambda: asyncore.close_all()) else: self._channel.push(None, 0) Wakeup() self._data = None self._channel = None
def close(self): DebugLogger.log('A', id(self._request), '%s %s' % (self._request.reply_code, self._bytes)) if not self._channel.closed: self._channel.push(LoggingProducer(self._request, self._bytes), 0) self._channel.push(CallbackProducer(self._channel.done), 0) self._channel.push( CallbackProducer(lambda t=('E', id(self._request)): apply( DebugLogger.log, t)), 0) if self._shutdown: self._channel.push(ShutdownProducer(), 0) Wakeup() else: if self._close: self._channel.push(None, 0) Wakeup() else: # channel closed too soon self._request.log(self._bytes) DebugLogger.log('E', id(self._request)) if self._shutdown: Wakeup(lambda: asyncore.close_all()) else: Wakeup() self._channel = None #need to break cycles? self._request = None
def log_request(self, bytes): DebugLogger.log('E', id(self)) if self.env.has_key('HTTP_USER_AGENT'): user_agent=self.env['HTTP_USER_AGENT'] else: user_agent='' if self.env.has_key('HTTP_REFERER'): referer=self.env['HTTP_REFERER'] else: referer='' if self.env.has_key('PATH_INFO'): path=self.env['PATH_INFO'] else: path='' if self.env.has_key('REQUEST_METHOD'): method=self.env['REQUEST_METHOD'] else: method="GET" user_name = '-' if self.env.has_key('HTTP_AUTHORIZATION'): http_authorization=self.env['HTTP_AUTHORIZATION'] if string.lower(http_authorization[:6]) == 'basic ': try: decoded=base64.decodestring(http_authorization[6:]) except base64.binascii.Error: decoded='' t = string.split(decoded, ':', 1) if len(t) >= 2: user_name = t[0] if self.addr: self.server.logger.log ( self.addr[0], '%s - %s [%s] "%s %s" %d %d "%s" "%s"' % ( self.addr[1], user_name, time.strftime ( '%d/%b/%Y:%H:%M:%S ', time.localtime(time.time()) ) + tz_for_log, method, path, self.reply_code, bytes, referer, user_agent ) ) else: self.server.logger.log ( '127.0.0.1 ', '- %s [%s] "%s %s" %d %d "%s" "%s"' % ( user_name, time.strftime ( '%d/%b/%Y:%H:%M:%S ', time.localtime(time.time()) ) + tz_for_log, method, path, self.reply_code, bytes, referer, user_agent ) )
def handle_request(self,request): self.hits.increment() DebugLogger.log('B', id(request), '%s %s' % (request.command.upper(), request.uri)) size=get_header(CONTENT_LENGTH, request.header) if size and size != '0': size=int(size) zhttp_collector(self, request, size) else: sin=StringIO() self.continue_request(sin,request)
def continue_request(self, sin, request): "continue handling request now that we have the stdin" s=get_header(CONTENT_LENGTH, request.header) if s: s=int(s) else: s=0 DebugLogger.log('I', id(request), s) env=self.get_environment(request) zresponse=make_response(request,env) if self._force_connection_close: zresponse._http_connection = 'close' zrequest=HTTPRequest(sin, env, zresponse) request.channel.current_request=None request.channel.queue.append((self.module_name, zrequest, zresponse)) request.channel.work()
def close(self): if not self._channel.closed: data=self._data.getvalue() l=len(data) DebugLogger.log('A', id(self._channel), '%s %s' % (self._channel.reply_code, l)) self._channel.push('%010d%s%010d' % (l, data, 0), 0) self._channel.push(LoggingProducer(self._channel, l, 'log_request'), 0) self._channel.push(CallbackProducer( lambda t=('E', id(self._channel)): apply(DebugLogger.log,t)), 0) if self._shutdown: try: r=self._shutdown[0] except: r=0 ZServer.exit_code=r self._channel.push(ShutdownProducer(), 0) Wakeup(lambda: asyncore.close_all()) else: self._channel.push(None, 0) Wakeup() self._data=None self._channel=None
def continue_request(self, sin, request): "continue handling request now that we have the stdin" s=get_header(CONTENT_LENGTH, request.header) if s: s=int(s) else: s=0 DebugLogger.log('I', id(request), s) env=self.get_environment(request) version = request.version if version=='1.0' and is_proxying_match(request.request): # a request that was made as if this zope was an http 1.0 proxy. # that means we have to use some slightly different http # headers to manage persistent connections. connection_re = proxying_connection_re else: # a normal http request connection_re = CONNECTION env['http_connection'] = get_header(connection_re, request.header).lower() env['server_version']=request.channel.server.SERVER_IDENT env['wsgi.output'] = ChannelPipe(request) env['wsgi.input'] = sin env['wsgi.errors'] = sys.stderr env['wsgi.version'] = (1,0) env['wsgi.multithread'] = True env['wsgi.multiprocess'] = True env['wsgi.run_once'] = True env['wsgi.url_scheme'] = env['SERVER_PROTOCOL'].split('/')[0] request.channel.current_request=None request.channel.queue.append(('Zope2WSGI', env, env['wsgi.output'].start_response)) request.channel.work()
def found_terminator(self): if self.size is None: # read the next size header # and prepare to read env or stdin self.data.seek(0) self.size = string.atoi(self.data.read()) self.set_terminator(self.size) if self.size == 0: DebugLogger.log('I', id(self), 0) self.set_terminator('\r\n') self.data = StringIO() self.send_response() elif self.size > 1048576: self.data = TemporaryFile('w+b') else: self.data = StringIO() elif not self.env: # read env self.size = None self.data.seek(0) buff = self.data.read() for line in string.split(buff, '\000'): try: k, v = string.split(line, '=', 1) self.env[k] = v except: pass # Hack around broken IIS PATH_INFO # maybe, this should go in ZPublisher... if self.env.has_key('SERVER_SOFTWARE') and \ string.find(self.env['SERVER_SOFTWARE'], 'Microsoft-IIS') != -1: script = filter( None, string.split(string.strip(self.env['SCRIPT_NAME']), '/')) path = filter( None, string.split(string.strip(self.env['PATH_INFO']), '/')) self.env['PATH_INFO'] = '/' + string.join( path[len(script):], '/') self.data = StringIO() DebugLogger.log( 'B', id(self), '%s %s' % (self.env['REQUEST_METHOD'], self.env.get('PATH_INFO', '/'))) # now read the next size header self.set_terminator(10) else: DebugLogger.log('I', id(self), self.terminator) # we're done, we've got both env and stdin self.set_terminator('\r\n') self.data.seek(0) self.send_response()
def found_terminator(self): if self.size is None: # read the next size header # and prepare to read env or stdin self.data.seek(0) self.size=string.atoi(self.data.read()) self.set_terminator(self.size) if self.size==0: DebugLogger.log('I', id(self), 0) self.set_terminator('\r\n') self.data=StringIO() self.send_response() elif self.size > 1048576: self.data=TemporaryFile('w+b') else: self.data=StringIO() elif not self.env: # read env self.size=None self.data.seek(0) buff=self.data.read() for line in string.split(buff,'\000'): try: k,v = string.split(line,'=',1) self.env[k] = v except: pass # Hack around broken IIS PATH_INFO # maybe, this should go in ZPublisher... if self.env.has_key('SERVER_SOFTWARE') and \ string.find(self.env['SERVER_SOFTWARE'], 'Microsoft-IIS') != -1: script = filter(None,string.split( string.strip(self.env['SCRIPT_NAME']),'/')) path = filter(None,string.split( string.strip(self.env['PATH_INFO']),'/')) self.env['PATH_INFO'] = '/' + string.join(path[len(script):],'/') self.data=StringIO() DebugLogger.log('B', id(self), '%s %s' % (self.env['REQUEST_METHOD'], self.env.get('PATH_INFO' ,'/'))) # now read the next size header self.set_terminator(10) else: DebugLogger.log('I', id(self), self.terminator) # we're done, we've got both env and stdin self.set_terminator('\r\n') self.data.seek(0) self.send_response()
def found_terminator(self): # Are we starting a new record? If so, data is the header. if not self.curRec: self.curRec = FCGIRecord(self.data.getvalue()) if self.curRec.needMore(): self.set_terminator(self.curRec.needMore()) self.data = StringIO() return rec = self.curRec # If waiting for record content, give it to the record. if rec.needContent(): rec.parseContent(self.data.getvalue()) if rec.needMore(): self.set_terminator(rec.needMore()) self.data = StringIO() return if rec.needPadding(): rec.gotPadding() # If we get this far without returning, we've got the whole # record. Figure out what to do with it. if rec.recType in FCGI_ManagementTypes: # Apache mod_fastcgi doesn't send these, but others may self.handleManagementTypes(rec) elif rec.reqId == 0: # It's a management record of unknown type. # Complain about it... r2 = FCGIRecord() r2.recType = FCGI_UNKNOWN_TYPE r2.unknownType = rec.recType self.push(r2.getRecordAsString(), 0) # Since we don't actually have to do anything to ignore the # following conditions, they have been commented out and have # been left in the code for documentation purposes. # Ignore requests that aren't active # elif rec.reqId != self.requestId and rec.recType != FCGI_BEGIN_REQUEST: # pass # # If we're already doing a request, ignore further BEGIN_REQUESTs # elif rec.recType == FCGI_BEGIN_REQUEST and self.requestId != 0: # pass # Begin a new request elif rec.recType == FCGI_BEGIN_REQUEST and self.requestId == 0: self.requestId = rec.reqId if rec.role == FCGI_AUTHORIZER: self.remainingRecs = 1 elif rec.role == FCGI_RESPONDER: self.remainingRecs = 2 elif rec.role == FCGI_FILTER: self.remainingRecs = 3 # Read some name-value pairs (the CGI environment) elif rec.recType == FCGI_PARAMS: if rec.contentLength == 0: # end of the stream if self.env.has_key('REQUEST_METHOD'): method=self.env['REQUEST_METHOD'] else: method='GET' if self.env.has_key('PATH_INFO'): path=self.env['PATH_INFO'] else: path='' DebugLogger.log('B', id(self), '%s %s' % (method, path)) self.remainingRecs = self.remainingRecs - 1 self.content_length=string.atoi(self.env.get( 'CONTENT_LENGTH','0')) else: self.env.update(rec.values) # read some stdin data elif rec.recType == FCGI_STDIN: if rec.contentLength == 0: # end of the stream self.remainingRecs = self.remainingRecs - 1 else: # see if stdin is getting too big, and # replace it with a tempfile if necessary if len(rec.content) + self.stdin.tell() > 1048576 and \ not self.using_temp_stdin: t=TemporaryFile() t.write(self.stdin.getvalue()) self.stdin=t self.using_temp_stdin=1 self.stdin.write(rec.content) # read some filter data elif rec.recType == FCGI_DATA: if rec.contentLength == 0: # end of the stream self.remainingRecs = self.remainingRecs - 1 else: self.filterData.write(rec.content) # We've processed the record. Now what do we do? if self.remainingRecs > 0: # prepare to get the next record self.setInitialState() else: # We've got them all. Let ZPublisher do its thang. DebugLogger.log('I', id(self), self.stdin.tell()) # But first, fixup the auth header if using newest mod_fastcgi. if self.env.has_key('Authorization'): self.env['HTTP_AUTHORIZATION'] = self.env['Authorization'] del self.env['Authorization'] self.stdin.seek(0) self.send_response()