[Tomcat6.0源码]请求的处理二Request
2012-09-25 16:21
363 查看
Worker.run()取到socke后,往下执行handler.process(socket)。handler来源于Http11Protocol.init():
cHandler是在Http11Protocol的属性中直接new的:
Http11ConnectionHandler是Http11Protocol的内部类。handler.process(socket)即执行Http11ConnectionHandler.process(socket):
Http11ConnectionHandler.createProcessor():
processor.process(socket);即Http11Processor.process():
adapter.service(request, response);这个adapter是Http11Protocol.Http11ConnectionHandler.createProcessor()中创建Http11Processor对象时设置的:
而这个Http11ConnectionHandler的proto是在其构造函数中赋值的:
Http11ConnectionHandler对象是在Http11Protocol的属性中new出来的:
这个this就是Http11Protocol自身对象,那么proto.adapter既是Http11Protocol.adapter,是在Connector.initialize()中赋值的(Connector初始化的时候):
绕了一圈。也就是adapter.service(request, response);即CoyoteAdapter.service(request, response):
将org.apache.coyote.Request包装成org.apache.catalina.connector.Request,实现HttpServletRequest接口
将org.apache.coyote.Response包装成org.apache.catalina.connector.Response,实现HttpServletResponse接口
public void init() throws Exception { endpoint.setName(getName()); endpoint.setHandler(cHandler);
cHandler是在Http11Protocol的属性中直接new的:
protected Http11ConnectionHandler cHandler = new Http11ConnectionHandler(this);
Http11ConnectionHandler是Http11Protocol的内部类。handler.process(socket)即执行Http11ConnectionHandler.process(socket):
public boolean process(Socket socket) { Http11Processor processor = recycledProcessors.poll(); try { if (processor == null) { processor = createProcessor(); } if (processor instanceof ActionHook) { ((ActionHook) processor).action(ActionCode.ACTION_START, null); } if (proto.isSSLEnabled() && (proto.sslImplementation != null)) { processor.setSSLSupport (proto.sslImplementation.getSSLSupport(socket)); } else { processor.setSSLSupport(null); } processor.process(socket); return false; } catch(java.net.SocketException e) { // SocketExceptions are normal Http11Protocol.log.debug (sm.getString ("http11protocol.proto.socketexception.debug"), e); } catch (java.io.IOException e) { // IOExceptions are normal Http11Protocol.log.debug (sm.getString ("http11protocol.proto.ioexception.debug"), e); } // Future developers: if you discover any other // rare-but-nonfatal exceptions, catch them here, and log as // above. catch (Throwable e) { // any other exception or error is odd. Here we log it // with "ERROR" level, so it will show up even on // less-than-verbose logs. Http11Protocol.log.error (sm.getString("http11protocol.proto.error"), e); } finally { // if(proto.adapter != null) proto.adapter.recycle(); // processor.recycle(); if (processor instanceof ActionHook) { ((ActionHook) processor).action(ActionCode.ACTION_STOP, null); } recycledProcessors.offer(processor); } return false; }
Http11ConnectionHandler.createProcessor():
protected Http11Processor createProcessor() { Http11Processor processor = new Http11Processor(proto.maxHttpHeaderSize, proto.endpoint); processor.setAdapter(proto.adapter); processor.setMaxKeepAliveRequests(proto.maxKeepAliveRequests); processor.setKeepAliveTimeout(proto.keepAliveTimeout); processor.setTimeout(proto.timeout); processor.setDisableUploadTimeout(proto.disableUploadTimeout); processor.setCompressionMinSize(proto.compressionMinSize); processor.setCompression(proto.compression); processor.setNoCompressionUserAgents(proto.noCompressionUserAgents); processor.setCompressableMimeTypes(proto.compressableMimeTypes); processor.setRestrictedUserAgents(proto.restrictedUserAgents); processor.setSocketBuffer(proto.socketBuffer); processor.setMaxSavePostSize(proto.maxSavePostSize); processor.setServer(proto.server); register(processor); return processor; }
processor.process(socket);即Http11Processor.process():
public void process(Socket theSocket) throws IOException { RequestInfo rp = request.getRequestProcessor(); rp.setStage(org.apache.coyote.Constants.STAGE_PARSE); // Set the remote address remoteAddr = null; remoteHost = null; localAddr = null; localName = null; remotePort = -1; localPort = -1; // Setting up the I/O this.socket = theSocket; inputBuffer.setInputStream(socket.getInputStream()); outputBuffer.setOutputStream(socket.getOutputStream()); // Error flag error = false; keepAlive = true; int keepAliveLeft = maxKeepAliveRequests; int soTimeout = endpoint.getSoTimeout(); // When using an executor, these values may return non-positive values int curThreads = endpoint.getCurrentThreadsBusy(); int maxThreads = endpoint.getMaxThreads(); if (curThreads > 0 && maxThreads > 0) { // Only auto-disable keep-alive if the current thread usage % can be // calculated correctly if ((curThreads*100)/maxThreads > 75) { keepAliveLeft = 1; } } try { socket.setSoTimeout(soTimeout); } catch (Throwable t) { log.debug(sm.getString("http11processor.socket.timeout"), t); error = true; } boolean keptAlive = false; while (started && !error && keepAlive && !endpoint.isPaused()) { // Parsing the request header try { if (keptAlive) { if (keepAliveTimeout > 0) { socket.setSoTimeout(keepAliveTimeout); } else if (soTimeout > 0) { socket.setSoTimeout(soTimeout); } } inputBuffer.parseRequestLine(); request.setStartTime(System.currentTimeMillis()); keptAlive = true; if (disableUploadTimeout) { socket.setSoTimeout(soTimeout); } else { socket.setSoTimeout(timeout); } // Set this every time in case limit has been changed via JMX request.getMimeHeaders().setLimit(endpoint.getMaxHeaderCount()); inputBuffer.parseHeaders(); } catch (IOException e) { error = true; break; } catch (Throwable t) { if (log.isDebugEnabled()) { log.debug(sm.getString("http11processor.header.parse"), t); } // 400 - Bad Request response.setStatus(400); adapter.log(request, response, 0); error = true; } if (!error) { // Setting up filters, and parse some request headers rp.setStage(org.apache.coyote.Constants.STAGE_PREPARE); try { prepareRequest(); } catch (Throwable t) { if (log.isDebugEnabled()) { log.debug(sm.getString("http11processor.request.prepare"), t); } // 400 - Internal Server Error response.setStatus(400); adapter.log(request, response, 0); error = true; } } if (maxKeepAliveRequests > 0 && --keepAliveLeft == 0) keepAlive = false; // Process the request in the adapter if (!error) { try { rp.setStage(org.apache.coyote.Constants.STAGE_SERVICE); adapter.service(request, response); // Handle when the response was committed before a serious // error occurred. Throwing a ServletException should both // set the status to 500 and set the errorException. // If we fail here, then the response is likely already // committed, so we can't try and set headers. if(keepAlive && !error) { // Avoid checking twice. error = response.getErrorException() != null || statusDropsConnection(response.getStatus()); } } catch (InterruptedIOException e) { error = true; } catch (Throwable t) { log.error(sm.getString("http11processor.request.process"), t); // 500 - Internal Server Error response.setStatus(500); adapter.log(request, response, 0); error = true; } } // Finish the handling of the request try { rp.setStage(org.apache.coyote.Constants.STAGE_ENDINPUT); // If we know we are closing the connection, don't drain input. // This way uploading a 100GB file doesn't tie up the thread // if the servlet has rejected it. if(error) inputBuffer.setSwallowInput(false); inputBuffer.endRequest(); } catch (IOException e) { error = true; } catch (Throwable t) { log.error(sm.getString("http11processor.request.finish"), t); // 500 - Internal Server Error response.setStatus(500); // No access logging since after service method error = true; } try { rp.setStage(org.apache.coyote.Constants.STAGE_ENDOUTPUT); outputBuffer.endRequest(); } catch (IOException e) { error = true; } catch (Throwable t) { log.error(sm.getString("http11processor.response.finish"), t); error = true; } // If there was an error, make sure the request is counted as // and error, and update the statistics counter if (error) { response.setStatus(500); } request.updateCounters(); rp.setStage(org.apache.coyote.Constants.STAGE_KEEPALIVE); // Don't reset the param - we'll see it as ended. Next request // will reset it // thrA.setParam(null); // Next request inputBuffer.nextRequest(); outputBuffer.nextRequest(); } rp.setStage(org.apache.coyote.Constants.STAGE_ENDED); // Recycle inputBuffer.recycle(); outputBuffer.recycle(); this.socket = null; // Recycle ssl info sslSupport = null; }
adapter.service(request, response);这个adapter是Http11Protocol.Http11ConnectionHandler.createProcessor()中创建Http11Processor对象时设置的:
protected Http11Processor createProcessor() { Http11Processor processor = new Http11Processor(proto.maxHttpHeaderSize, proto.endpoint); processor.setAdapter(proto.adapter);
而这个Http11ConnectionHandler的proto是在其构造函数中赋值的:
Http11ConnectionHandler(Http11Protocol proto) { this.proto = proto; }
Http11ConnectionHandler对象是在Http11Protocol的属性中new出来的:
protected Http11ConnectionHandler cHandler = new Http11ConnectionHandler(this);
这个this就是Http11Protocol自身对象,那么proto.adapter既是Http11Protocol.adapter,是在Connector.initialize()中赋值的(Connector初始化的时候):
adapter = new CoyoteAdapter(this); protocolHandler.setAdapter(adapter);
绕了一圈。也就是adapter.service(request, response);即CoyoteAdapter.service(request, response):
public void service(org.apache.coyote.Request req, org.apache.coyote.Response res) throws Exception { Request request = (Request) req.getNote(ADAPTER_NOTES); Response response = (Response) res.getNote(ADAPTER_NOTES); if (request == null) { // Create objects request = (Request) connector.createRequest(); request.setCoyoteRequest(req); response = (Response) connector.createResponse(); response.setCoyoteResponse(res); // Link objects request.setResponse(response); response.setRequest(request); // Set as notes req.setNote(ADAPTER_NOTES, request); res.setNote(ADAPTER_NOTES, response); // Set query string encoding req.getParameters().setQueryStringEncoding (connector.getURIEncoding()); } if (connector.getXpoweredBy()) { response.addHeader("X-Powered-By", POWERED_BY); } boolean comet = false; try { // Parse and set Catalina and configuration specific // request parameters req.getRequestProcessor().setWorkerThreadName(Thread.currentThread().getName()); if (postParseRequest(req, request, res, response)) { // Calling the container connector.getContainer().getPipeline().getFirst().invoke(request, response); if (request.isComet()) { if (!response.isClosed() && !response.isError()) { if (request.getAvailable() || (request.getContentLength() > 0 && (!request.isParametersParsed()))) { // Invoke a read event right away if there are available bytes if (event(req, res, SocketStatus.OPEN)) { comet = true; res.action(ActionCode.ACTION_COMET_BEGIN, null); } } else { comet = true; res.action(ActionCode.ACTION_COMET_BEGIN, null); } } else { // Clear the filter chain, as otherwise it will not be reset elsewhere // since this is a Comet request request.setFilterChain(null); } } } if (!comet) { response.finishResponse(); req.action(ActionCode.ACTION_POST_REQUEST , null); } } catch (IOException e) { ; } finally { req.getRequestProcessor().setWorkerThreadName(null); // Recycle the wrapper request and response if (!comet) { request.recycle(); response.recycle(); } else { // Clear converters so that the minimum amount of memory // is used by this processor request.clearEncoders(); response.clearEncoders(); } } }
将org.apache.coyote.Request包装成org.apache.catalina.connector.Request,实现HttpServletRequest接口
将org.apache.coyote.Response包装成org.apache.catalina.connector.Response,实现HttpServletResponse接口
相关文章推荐
- [Tomcat6.0源码]请求的处理一Socket
- [Tomcat6.0源码]请求的处理三Mapper、JMX
- [Tomcat6.0源码]请求的处理四Pipeline、Valve、FilterChain
- Tomcat请求处理过程(Tomcat源码解析五)
- tomcat6源码分析三(请求处理过程)
- Tomcat请求处理过程(Tomcat源码解析五)
- Tomcat源码解读系列(三)——Tomcat对HTTP请求处理的整体流程
- Tomcat源码解读系列——Tomcat对HTTP请求处理的整体流程
- tomcat6源码分析三(请求处理过程)
- Tomcat源码阅读之处理请求
- 浅读Tomcat源码(三)---请求处理
- Tomcat6.0源码学习--接受并传递请求
- Tomcat6.0源码学习--接受并传递请求
- Tomcat源码解读系列三Tomcat对HTTP请求处理的整体流程
- Tomcat源码解读系列——Tomcat对HTTP请求处理的整体流程
- Tomcat源码解读系列(三)——Tomcat对HTTP请求处理的整体流程
- redis源码分析(3)——请求处理
- tomcat Server处理一个http请求的过程
- Spring MVC请求处理流程及源码分析
- Tomcat处理HTTP请求源码分析(上)