HttpServlet中的2种请求处理方式

HttpServlet继承于GenericServlet,,专门用于处理Http的请求:

  方法一:  HttpServlet复写了GenericServlet的service(ServletRequest rq,ServletResponse rp)并同时提供了了一个service(HttpServletRequest req,HttpServletRsponse rep),,,在service(ServletRequest rq,ServletResponse rp)方法内部调用了service(HttpServletRequest req,HttpServletRsponse rep),这样在服务器自动执行service(ServletRequest rq,ServletResponse rp)该生命周期方法时,也会同时调用到service(HttpServletRequest req,HttpServletRsponse rep)方法,而我们只需要子类中复写service(HttpServletRequest req,HttpServletRsponse rep)方法,在其中编写处理请求的代码,,[注]:在子类复写service(HttpServletRequest req,HttpServletRsponse rep)方法时,不能再该方法内写super.service(req,rep)调用该方法会输出一个错误信息.

  方法二:  HttpServlet复写了GenericServlet的service(ServletRequest rq,ServletResponse rp)并同时提供了了一个service(HttpServletRequest req,HttpServletRsponse rep),,,在service(ServletRequest rq,ServletResponse rp)方法内部调用了service(HttpServletRequest req,HttpServletRsponse rep),这样在服务器自动执行service(ServletRequest rq,ServletResponse rp)该生命周期方法时,也会同时调用到service(HttpServletRequest req,HttpServletRsponse rep)方法,,同时在service(HttpServletRequest req,HttpServletRsponse rep)方法内,还对请求类型进行了判断,如果根据不同的请求类型,在该方法内有调用了不同的方法对不同的请求类型进行处理,,,如针对get的doGet()方法,针对post的doPost()方法,,,,此时我们可以仅仅只在子类中分别复写针对不同请求类型的处理方法,如doGet()和doPost()等方法,,,这样即可在服务处理请求时根据service(ServletRequest rq,ServletResponse rp)------>service(HttpServletRequest req,HttpServletRsponse rep)的顺序自动找到相应的doGet()或doPost()方法进行对应的请求类型的处理...[注]:在子类中复写doGet()和doPost()等方法时不能在其方法内写super.doGet()或super.doPost()等方法,,,同样的,该调用同样是输出一个错误信息.

                          HttpServlet源代码

  1 /*
  2  * Licensed to the Apache Software Foundation (ASF) under one or more
  3  * contributor license agreements.  See the NOTICE file distributed with
  4  * this work for additional information regarding copyright ownership.
  5  * The ASF licenses this file to You under the Apache License, Version 2.0
  6  * (the "License"); you may not use this file except in compliance with
  7  * the License.  You may obtain a copy of the License at
  8  *
  9  *     http://www.apache.org/licenses/LICENSE-2.0
 10  *
 11  * Unless required by applicable law or agreed to in writing, software
 12  * distributed under the License is distributed on an "AS IS" BASIS,
 13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 14  * See the License for the specific language governing permissions and
 15  * limitations under the License.
 16  */
 17 package javax.servlet.http;
 18
 19 import java.io.IOException;
 20 import java.io.OutputStreamWriter;
 21 import java.io.PrintWriter;
 22 import java.io.UnsupportedEncodingException;
 23 import java.lang.reflect.Method;
 24 import java.text.MessageFormat;
 25 import java.util.Enumeration;
 26 import java.util.ResourceBundle;
 27
 28 import javax.servlet.GenericServlet;
 29 import javax.servlet.ServletException;
 30 import javax.servlet.ServletOutputStream;
 31 import javax.servlet.ServletRequest;
 32 import javax.servlet.ServletResponse;
 33
 34
 35 /**
 36  * Provides an abstract class to be subclassed to create
 37  * an HTTP servlet suitable for a Web site. A subclass of
 38  * <code>HttpServlet</code> must override at least
 39  * one method, usually one of these:
 40  *
 41  * <ul>
 42  * <li> <code>doGet</code>, if the servlet supports HTTP GET requests
 43  * <li> <code>doPost</code>, for HTTP POST requests
 44  * <li> <code>doPut</code>, for HTTP PUT requests
 45  * <li> <code>doDelete</code>, for HTTP DELETE requests
 46  * <li> <code>init</code> and <code>destroy</code>,
 47  * to manage resources that are held for the life of the servlet
 48  * <li> <code>getServletInfo</code>, which the servlet uses to
 49  * provide information about itself
 50  * </ul>
 51  *
 52  * <p>There‘s almost no reason to override the <code>service</code>
 53  * method. <code>service</code> handles standard HTTP
 54  * requests by dispatching them to the handler methods
 55  * for each HTTP request type (the <code>do</code><i>Method</i>
 56  * methods listed above).
 57  *
 58  * <p>Likewise, there‘s almost no reason to override the
 59  * <code>doOptions</code> and <code>doTrace</code> methods.
 60  *
 61  * <p>Servlets typically run on multithreaded servers,
 62  * so be aware that a servlet must handle concurrent
 63  * requests and be careful to synchronize access to shared resources.
 64  * Shared resources include in-memory data such as
 65  * instance or class variables and external objects
 66  * such as files, database connections, and network
 67  * connections.
 68  * See the
 69  * <a href="http://java.sun.com/Series/Tutorial/java/threads/multithreaded.html">
 70  * Java Tutorial on Multithreaded Programming</a> for more
 71  * information on handling multiple threads in a Java program.
 72  *
 73  * @author  Various
 74  */
 75 public abstract class HttpServlet extends GenericServlet {
 76
 77     private static final long serialVersionUID = 1L;
 78
 79     private static final String METHOD_DELETE = "DELETE";
 80     private static final String METHOD_HEAD = "HEAD";
 81     private static final String METHOD_GET = "GET";
 82     private static final String METHOD_OPTIONS = "OPTIONS";
 83     private static final String METHOD_POST = "POST";
 84     private static final String METHOD_PUT = "PUT";
 85     private static final String METHOD_TRACE = "TRACE";
 86
 87     private static final String HEADER_IFMODSINCE = "If-Modified-Since";
 88     private static final String HEADER_LASTMOD = "Last-Modified";
 89
 90     private static final String LSTRING_FILE =
 91         "javax.servlet.http.LocalStrings";
 92     private static ResourceBundle lStrings =
 93         ResourceBundle.getBundle(LSTRING_FILE);
 94
 95
 96     /**
 97      * Does nothing, because this is an abstract class.
 98      */
 99     public HttpServlet() {
100         // NOOP
101     }
102
103
104     /**
105      * Called by the server (via the <code>service</code> method) to
106      * allow a servlet to handle a GET request.
107      *
108      * <p>Overriding this method to support a GET request also
109      * automatically supports an HTTP HEAD request. A HEAD
110      * request is a GET request that returns no body in the
111      * response, only the request header fields.
112      *
113      * <p>When overriding this method, read the request data,
114      * write the response headers, get the response‘s writer or
115      * output stream object, and finally, write the response data.
116      * It‘s best to include content type and encoding. When using
117      * a <code>PrintWriter</code> object to return the response,
118      * set the content type before accessing the
119      * <code>PrintWriter</code> object.
120      *
121      * <p>The servlet container must write the headers before
122      * committing the response, because in HTTP the headers must be sent
123      * before the response body.
124      *
125      * <p>Where possible, set the Content-Length header (with the
126      * {@link javax.servlet.ServletResponse#setContentLength} method),
127      * to allow the servlet container to use a persistent connection
128      * to return its response to the client, improving performance.
129      * The content length is automatically set if the entire response fits
130      * inside the response buffer.
131      *
132      * <p>When using HTTP 1.1 chunked encoding (which means that the response
133      * has a Transfer-Encoding header), do not set the Content-Length header.
134      *
135      * <p>The GET method should be safe, that is, without
136      * any side effects for which users are held responsible.
137      * For example, most form queries have no side effects.
138      * If a client request is intended to change stored data,
139      * the request should use some other HTTP method.
140      *
141      * <p>The GET method should also be idempotent, meaning
142      * that it can be safely repeated. Sometimes making a
143      * method safe also makes it idempotent. For example,
144      * repeating queries is both safe and idempotent, but
145      * buying a product online or modifying data is neither
146      * safe nor idempotent.
147      *
148      * <p>If the request is incorrectly formatted, <code>doGet</code>
149      * returns an HTTP "Bad Request" message.
150      *
151      * @param req   an {@link HttpServletRequest} object that
152      *                  contains the request the client has made
153      *                  of the servlet
154      *
155      * @param resp  an {@link HttpServletResponse} object that
156      *                  contains the response the servlet sends
157      *                  to the client
158      *
159      * @exception IOException   if an input or output error is
160      *                              detected when the servlet handles
161      *                              the GET request
162      *
163      * @exception ServletException  if the request for the GET
164      *                                  could not be handled
165      *
166      * @see javax.servlet.ServletResponse#setContentType
167      */
168     protected void doGet(HttpServletRequest req, HttpServletResponse resp)
169         throws ServletException, IOException
170     {
171         String protocol = req.getProtocol();
172         String msg = lStrings.getString("http.method_get_not_supported");
173         if (protocol.endsWith("1.1")) {
174             resp.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, msg);
175         } else {
176             resp.sendError(HttpServletResponse.SC_BAD_REQUEST, msg);
177         }
178     }
179
180
181     /**
182      * Returns the time the <code>HttpServletRequest</code>
183      * object was last modified,
184      * in milliseconds since midnight January 1, 1970 GMT.
185      * If the time is unknown, this method returns a negative
186      * number (the default).
187      *
188      * <p>Servlets that support HTTP GET requests and can quickly determine
189      * their last modification time should override this method.
190      * This makes browser and proxy caches work more effectively,
191      * reducing the load on server and network resources.
192      *
193      * @param req   the <code>HttpServletRequest</code>
194      *                  object that is sent to the servlet
195      *
196      * @return  a <code>long</code> integer specifying
197      *              the time the <code>HttpServletRequest</code>
198      *              object was last modified, in milliseconds
199      *              since midnight, January 1, 1970 GMT, or
200      *              -1 if the time is not known
201      */
202     protected long getLastModified(HttpServletRequest req) {
203         return -1;
204     }
205
206
207     /**
208      * <p>Receives an HTTP HEAD request from the protected
209      * <code>service</code> method and handles the
210      * request.
211      * The client sends a HEAD request when it wants
212      * to see only the headers of a response, such as
213      * Content-Type or Content-Length. The HTTP HEAD
214      * method counts the output bytes in the response
215      * to set the Content-Length header accurately.
216      *
217      * <p>If you override this method, you can avoid computing
218      * the response body and just set the response headers
219      * directly to improve performance. Make sure that the
220      * <code>doHead</code> method you write is both safe
221      * and idempotent (that is, protects itself from being
222      * called multiple times for one HTTP HEAD request).
223      *
224      * <p>If the HTTP HEAD request is incorrectly formatted,
225      * <code>doHead</code> returns an HTTP "Bad Request"
226      * message.
227      *
228      * @param req   the request object that is passed to the servlet
229      *
230      * @param resp  the response object that the servlet
231      *                  uses to return the headers to the client
232      *
233      * @exception IOException   if an input or output error occurs
234      *
235      * @exception ServletException  if the request for the HEAD
236      *                                  could not be handled
237      */
238     protected void doHead(HttpServletRequest req, HttpServletResponse resp)
239         throws ServletException, IOException {
240
241         NoBodyResponse response = new NoBodyResponse(resp);
242
243         doGet(req, response);
244         response.setContentLength();
245     }
246
247
248     /**
249      * Called by the server (via the <code>service</code> method)
250      * to allow a servlet to handle a POST request.
251      *
252      * The HTTP POST method allows the client to send
253      * data of unlimited length to the Web server a single time
254      * and is useful when posting information such as
255      * credit card numbers.
256      *
257      * <p>When overriding this method, read the request data,
258      * write the response headers, get the response‘s writer or output
259      * stream object, and finally, write the response data. It‘s best
260      * to include content type and encoding. When using a
261      * <code>PrintWriter</code> object to return the response, set the
262      * content type before accessing the <code>PrintWriter</code> object.
263      *
264      * <p>The servlet container must write the headers before committing the
265      * response, because in HTTP the headers must be sent before the
266      * response body.
267      *
268      * <p>Where possible, set the Content-Length header (with the
269      * {@link javax.servlet.ServletResponse#setContentLength} method),
270      * to allow the servlet container to use a persistent connection
271      * to return its response to the client, improving performance.
272      * The content length is automatically set if the entire response fits
273      * inside the response buffer.
274      *
275      * <p>When using HTTP 1.1 chunked encoding (which means that the response
276      * has a Transfer-Encoding header), do not set the Content-Length header.
277      *
278      * <p>This method does not need to be either safe or idempotent.
279      * Operations requested through POST can have side effects for
280      * which the user can be held accountable, for example,
281      * updating stored data or buying items online.
282      *
283      * <p>If the HTTP POST request is incorrectly formatted,
284      * <code>doPost</code> returns an HTTP "Bad Request" message.
285      *
286      *
287      * @param req   an {@link HttpServletRequest} object that
288      *                  contains the request the client has made
289      *                  of the servlet
290      *
291      * @param resp  an {@link HttpServletResponse} object that
292      *                  contains the response the servlet sends
293      *                  to the client
294      *
295      * @exception IOException   if an input or output error is
296      *                              detected when the servlet handles
297      *                              the request
298      *
299      * @exception ServletException  if the request for the POST
300      *                                  could not be handled
301      *
302      * @see javax.servlet.ServletOutputStream
303      * @see javax.servlet.ServletResponse#setContentType
304      */
305     protected void doPost(HttpServletRequest req, HttpServletResponse resp)
306         throws ServletException, IOException {
307
308         String protocol = req.getProtocol();
309         String msg = lStrings.getString("http.method_post_not_supported");
310         if (protocol.endsWith("1.1")) {
311             resp.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, msg);
312         } else {
313             resp.sendError(HttpServletResponse.SC_BAD_REQUEST, msg);
314         }
315     }
316
317
318     /**
319      * Called by the server (via the <code>service</code> method)
320      * to allow a servlet to handle a PUT request.
321      *
322      * The PUT operation allows a client to
323      * place a file on the server and is similar to
324      * sending a file by FTP.
325      *
326      * <p>When overriding this method, leave intact
327      * any content headers sent with the request (including
328      * Content-Length, Content-Type, Content-Transfer-Encoding,
329      * Content-Encoding, Content-Base, Content-Language, Content-Location,
330      * Content-MD5, and Content-Range). If your method cannot
331      * handle a content header, it must issue an error message
332      * (HTTP 501 - Not Implemented) and discard the request.
333      * For more information on HTTP 1.1, see RFC 2616
334      * <a href="http://www.ietf.org/rfc/rfc2616.txt"></a>.
335      *
336      * <p>This method does not need to be either safe or idempotent.
337      * Operations that <code>doPut</code> performs can have side
338      * effects for which the user can be held accountable. When using
339      * this method, it may be useful to save a copy of the
340      * affected URL in temporary storage.
341      *
342      * <p>If the HTTP PUT request is incorrectly formatted,
343      * <code>doPut</code> returns an HTTP "Bad Request" message.
344      *
345      * @param req   the {@link HttpServletRequest} object that
346      *                  contains the request the client made of
347      *                  the servlet
348      *
349      * @param resp  the {@link HttpServletResponse} object that
350      *                  contains the response the servlet returns
351      *                  to the client
352      *
353      * @exception IOException   if an input or output error occurs
354      *                              while the servlet is handling the
355      *                              PUT request
356      *
357      * @exception ServletException  if the request for the PUT
358      *                                  cannot be handled
359      */
360     protected void doPut(HttpServletRequest req, HttpServletResponse resp)
361         throws ServletException, IOException {
362
363         String protocol = req.getProtocol();
364         String msg = lStrings.getString("http.method_put_not_supported");
365         if (protocol.endsWith("1.1")) {
366             resp.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, msg);
367         } else {
368             resp.sendError(HttpServletResponse.SC_BAD_REQUEST, msg);
369         }
370     }
371
372
373     /**
374      * Called by the server (via the <code>service</code> method)
375      * to allow a servlet to handle a DELETE request.
376      *
377      * The DELETE operation allows a client to remove a document
378      * or Web page from the server.
379      *
380      * <p>This method does not need to be either safe
381      * or idempotent. Operations requested through
382      * DELETE can have side effects for which users
383      * can be held accountable. When using
384      * this method, it may be useful to save a copy of the
385      * affected URL in temporary storage.
386      *
387      * <p>If the HTTP DELETE request is incorrectly formatted,
388      * <code>doDelete</code> returns an HTTP "Bad Request"
389      * message.
390      *
391      * @param req   the {@link HttpServletRequest} object that
392      *                  contains the request the client made of
393      *                  the servlet
394      *
395      *
396      * @param resp  the {@link HttpServletResponse} object that
397      *                  contains the response the servlet returns
398      *                  to the client
399      *
400      * @exception IOException   if an input or output error occurs
401      *                              while the servlet is handling the
402      *                              DELETE request
403      *
404      * @exception ServletException  if the request for the
405      *                                  DELETE cannot be handled
406      */
407     protected void doDelete(HttpServletRequest req,
408                             HttpServletResponse resp)
409         throws ServletException, IOException {
410
411         String protocol = req.getProtocol();
412         String msg = lStrings.getString("http.method_delete_not_supported");
413         if (protocol.endsWith("1.1")) {
414             resp.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, msg);
415         } else {
416             resp.sendError(HttpServletResponse.SC_BAD_REQUEST, msg);
417         }
418     }
419
420
421     private static Method[] getAllDeclaredMethods(Class<?> c) {
422
423         if (c.equals(javax.servlet.http.HttpServlet.class)) {
424             return null;
425         }
426
427         Method[] parentMethods = getAllDeclaredMethods(c.getSuperclass());
428         Method[] thisMethods = c.getDeclaredMethods();
429
430         if ((parentMethods != null) && (parentMethods.length > 0)) {
431             Method[] allMethods =
432                 new Method[parentMethods.length + thisMethods.length];
433             System.arraycopy(parentMethods, 0, allMethods, 0,
434                              parentMethods.length);
435             System.arraycopy(thisMethods, 0, allMethods, parentMethods.length,
436                              thisMethods.length);
437
438             thisMethods = allMethods;
439         }
440
441         return thisMethods;
442     }
443
444
445     /**
446      * Called by the server (via the <code>service</code> method)
447      * to allow a servlet to handle a OPTIONS request.
448      *
449      * The OPTIONS request determines which HTTP methods
450      * the server supports and
451      * returns an appropriate header. For example, if a servlet
452      * overrides <code>doGet</code>, this method returns the
453      * following header:
454      *
455      * <p><code>Allow: GET, HEAD, TRACE, OPTIONS</code>
456      *
457      * <p>There‘s no need to override this method unless the
458      * servlet implements new HTTP methods, beyond those
459      * implemented by HTTP 1.1.
460      *
461      * @param req   the {@link HttpServletRequest} object that
462      *                  contains the request the client made of
463      *                  the servlet
464      *
465      * @param resp  the {@link HttpServletResponse} object that
466      *                  contains the response the servlet returns
467      *                  to the client
468      *
469      * @exception IOException   if an input or output error occurs
470      *                              while the servlet is handling the
471      *                              OPTIONS request
472      *
473      * @exception ServletException  if the request for the
474      *                                  OPTIONS cannot be handled
475      */
476     protected void doOptions(HttpServletRequest req,
477             HttpServletResponse resp)
478         throws ServletException, IOException {
479
480         Method[] methods = getAllDeclaredMethods(this.getClass());
481
482         boolean ALLOW_GET = false;
483         boolean ALLOW_HEAD = false;
484         boolean ALLOW_POST = false;
485         boolean ALLOW_PUT = false;
486         boolean ALLOW_DELETE = false;
487         boolean ALLOW_TRACE = true;
488         boolean ALLOW_OPTIONS = true;
489
490         for (int i=0; i<methods.length; i++) {
491             Method m = methods[i];
492
493             if (m.getName().equals("doGet")) {
494                 ALLOW_GET = true;
495                 ALLOW_HEAD = true;
496             }
497             if (m.getName().equals("doPost"))
498                 ALLOW_POST = true;
499             if (m.getName().equals("doPut"))
500                 ALLOW_PUT = true;
501             if (m.getName().equals("doDelete"))
502                 ALLOW_DELETE = true;
503         }
504
505         String allow = null;
506         if (ALLOW_GET)
507             allow=METHOD_GET;
508         if (ALLOW_HEAD)
509             if (allow==null) allow=METHOD_HEAD;
510             else allow += ", " + METHOD_HEAD;
511         if (ALLOW_POST)
512             if (allow==null) allow=METHOD_POST;
513             else allow += ", " + METHOD_POST;
514         if (ALLOW_PUT)
515             if (allow==null) allow=METHOD_PUT;
516             else allow += ", " + METHOD_PUT;
517         if (ALLOW_DELETE)
518             if (allow==null) allow=METHOD_DELETE;
519             else allow += ", " + METHOD_DELETE;
520         if (ALLOW_TRACE)
521             if (allow==null) allow=METHOD_TRACE;
522             else allow += ", " + METHOD_TRACE;
523         if (ALLOW_OPTIONS)
524             if (allow==null) allow=METHOD_OPTIONS;
525             else allow += ", " + METHOD_OPTIONS;
526
527         resp.setHeader("Allow", allow);
528     }
529
530
531     /**
532      * Called by the server (via the <code>service</code> method)
533      * to allow a servlet to handle a TRACE request.
534      *
535      * A TRACE returns the headers sent with the TRACE
536      * request to the client, so that they can be used in
537      * debugging. There‘s no need to override this method.
538      *
539      * @param req   the {@link HttpServletRequest} object that
540      *                  contains the request the client made of
541      *                  the servlet
542      *
543      * @param resp  the {@link HttpServletResponse} object that
544      *                  contains the response the servlet returns
545      *                  to the client
546      *
547      * @exception IOException   if an input or output error occurs
548      *                              while the servlet is handling the
549      *                              TRACE request
550      *
551      * @exception ServletException  if the request for the
552      *                                  TRACE cannot be handled
553      */
554     protected void doTrace(HttpServletRequest req, HttpServletResponse resp)
555         throws ServletException, IOException
556     {
557
558         int responseLength;
559
560         String CRLF = "\r\n";
561         StringBuilder buffer = new StringBuilder("TRACE ").append(req.getRequestURI())
562             .append(" ").append(req.getProtocol());
563
564         Enumeration<String> reqHeaderEnum = req.getHeaderNames();
565
566         while( reqHeaderEnum.hasMoreElements() ) {
567             String headerName = reqHeaderEnum.nextElement();
568             buffer.append(CRLF).append(headerName).append(": ")
569                 .append(req.getHeader(headerName));
570         }
571
572         buffer.append(CRLF);
573
574         responseLength = buffer.length();
575
576         resp.setContentType("message/http");
577         resp.setContentLength(responseLength);
578         ServletOutputStream out = resp.getOutputStream();
579         out.print(buffer.toString());
580         out.close();
581         return;
582     }
583
584
585     /**
586      * Receives standard HTTP requests from the public
587      * <code>service</code> method and dispatches
588      * them to the <code>do</code><i>Method</i> methods defined in
589      * this class. This method is an HTTP-specific version of the
590      * {@link javax.servlet.Servlet#service} method. There‘s no
591      * need to override this method.
592      *
593      * @param req   the {@link HttpServletRequest} object that
594      *                  contains the request the client made of
595      *                  the servlet
596      *
597      * @param resp  the {@link HttpServletResponse} object that
598      *                  contains the response the servlet returns
599      *                  to the client
600      *
601      * @exception IOException   if an input or output error occurs
602      *                              while the servlet is handling the
603      *                              HTTP request
604      *
605      * @exception ServletException  if the HTTP request
606      *                                  cannot be handled
607      *
608      * @see javax.servlet.Servlet#service
609      */
610     protected void service(HttpServletRequest req, HttpServletResponse resp)
611         throws ServletException, IOException {
612
613         String method = req.getMethod();
614
615         if (method.equals(METHOD_GET)) {
616             long lastModified = getLastModified(req);
617             if (lastModified == -1) {
618                 // servlet doesn‘t support if-modified-since, no reason
619                 // to go through further expensive logic
620                 doGet(req, resp);
621             } else {
622                 long ifModifiedSince;
623                 try {
624                     ifModifiedSince = req.getDateHeader(HEADER_IFMODSINCE);
625                 } catch (IllegalArgumentException iae) {
626                     // Invalid date header - proceed as if none was set
627                     ifModifiedSince = -1;
628                 }
629                 if (ifModifiedSince < (lastModified / 1000 * 1000)) {
630                     // If the servlet mod time is later, call doGet()
631                     // Round down to the nearest second for a proper compare
632                     // A ifModifiedSince of -1 will always be less
633                     maybeSetLastModified(resp, lastModified);
634                     doGet(req, resp);
635                 } else {
636                     resp.setStatus(HttpServletResponse.SC_NOT_MODIFIED);
637                 }
638             }
639
640         } else if (method.equals(METHOD_HEAD)) {
641             long lastModified = getLastModified(req);
642             maybeSetLastModified(resp, lastModified);
643             doHead(req, resp);
644
645         } else if (method.equals(METHOD_POST)) {
646             doPost(req, resp);
647
648         } else if (method.equals(METHOD_PUT)) {
649             doPut(req, resp);
650
651         } else if (method.equals(METHOD_DELETE)) {
652             doDelete(req, resp);
653
654         } else if (method.equals(METHOD_OPTIONS)) {
655             doOptions(req,resp);
656
657         } else if (method.equals(METHOD_TRACE)) {
658             doTrace(req,resp);
659
660         } else {
661             //
662             // Note that this means NO servlet supports whatever
663             // method was requested, anywhere on this server.
664             //
665
666             String errMsg = lStrings.getString("http.method_not_implemented");
667             Object[] errArgs = new Object[1];
668             errArgs[0] = method;
669             errMsg = MessageFormat.format(errMsg, errArgs);
670
671             resp.sendError(HttpServletResponse.SC_NOT_IMPLEMENTED, errMsg);
672         }
673     }
674
675
676     /*
677      * Sets the Last-Modified entity header field, if it has not
678      * already been set and if the value is meaningful.  Called before
679      * doGet, to ensure that headers are set before response data is
680      * written.  A subclass might have set this header already, so we
681      * check.
682      */
683     private void maybeSetLastModified(HttpServletResponse resp,
684                                       long lastModified) {
685         if (resp.containsHeader(HEADER_LASTMOD))
686             return;
687         if (lastModified >= 0)
688             resp.setDateHeader(HEADER_LASTMOD, lastModified);
689     }
690
691
692     /**
693      * Dispatches client requests to the protected
694      * <code>service</code> method. There‘s no need to
695      * override this method.
696      *
697      * @param req   the {@link HttpServletRequest} object that
698      *                  contains the request the client made of
699      *                  the servlet
700      *
701      * @param res   the {@link HttpServletResponse} object that
702      *                  contains the response the servlet returns
703      *                  to the client
704      *
705      * @exception IOException   if an input or output error occurs
706      *                              while the servlet is handling the
707      *                              HTTP request
708      *
709      * @exception ServletException  if the HTTP request cannot
710      *                                  be handled
711      *
712      * @see javax.servlet.Servlet#service
713      */
714     @Override
715     public void service(ServletRequest req, ServletResponse res)
716         throws ServletException, IOException {
717
718         HttpServletRequest  request;
719         HttpServletResponse response;
720
721         try {
722             request = (HttpServletRequest) req;
723             response = (HttpServletResponse) res;
724         } catch (ClassCastException e) {
725             throw new ServletException("non-HTTP request or response");
726         }
727         service(request, response);
728     }
729 }
730
731
732 /*
733  * A response wrapper for use in (dumb) "HEAD" support.
734  * This just swallows that body, counting the bytes in order to set
735  * the content length appropriately.  All other methods delegate to the
736  * wrapped HTTP Servlet Response object.
737  */
738 // file private
739 class NoBodyResponse extends HttpServletResponseWrapper {
740     private NoBodyOutputStream                noBody;
741     private PrintWriter                        writer;
742     private boolean                        didSetContentLength;
743
744     // file private
745     NoBodyResponse(HttpServletResponse r) {
746         super(r);
747         noBody = new NoBodyOutputStream();
748     }
749
750     // file private
751     void setContentLength() {
752         if (!didSetContentLength) {
753             if (writer != null) {
754                 writer.flush();
755             }
756             super.setContentLength(noBody.getContentLength());
757         }
758     }
759
760
761     // SERVLET RESPONSE interface methods
762
763     @Override
764     public void setContentLength(int len) {
765         super.setContentLength(len);
766         didSetContentLength = true;
767     }
768
769     @Override
770     public void setHeader(String name, String value) {
771         super.setHeader(name, value);
772         checkHeader(name);
773     }
774
775     @Override
776     public void addHeader(String name, String value) {
777         super.addHeader(name, value);
778         checkHeader(name);
779     }
780
781     @Override
782     public void setIntHeader(String name, int value) {
783         super.setIntHeader(name, value);
784         checkHeader(name);
785     }
786
787     @Override
788     public void addIntHeader(String name, int value) {
789         super.addIntHeader(name, value);
790         checkHeader(name);
791     }
792
793     private void checkHeader(String name) {
794         if ("content-length".equalsIgnoreCase(name)) {
795             didSetContentLength = true;
796         }
797     }
798
799     @Override
800     public ServletOutputStream getOutputStream() throws IOException {
801         return noBody;
802     }
803
804     @Override
805     public PrintWriter getWriter() throws UnsupportedEncodingException {
806
807         if (writer == null) {
808             OutputStreamWriter w;
809
810             w = new OutputStreamWriter(noBody, getCharacterEncoding());
811             writer = new PrintWriter(w);
812         }
813         return writer;
814     }
815 }
816
817
818 /*
819  * Servlet output stream that gobbles up all its data.
820  */
821
822 // file private
823 class NoBodyOutputStream extends ServletOutputStream {
824
825     private static final String LSTRING_FILE =
826         "javax.servlet.http.LocalStrings";
827     private static ResourceBundle lStrings =
828         ResourceBundle.getBundle(LSTRING_FILE);
829
830     private int                contentLength = 0;
831
832     // file private
833     NoBodyOutputStream() {
834         // NOOP
835     }
836
837     // file private
838     int getContentLength() {
839         return contentLength;
840     }
841
842     @Override
843     public void write(int b) {
844         contentLength++;
845     }
846
847     @Override
848     public void write(byte buf[], int offset, int len) throws IOException {
849         if (buf == null) {
850             throw new NullPointerException(
851                     lStrings.getString("err.io.nullArray"));
852         }
853
854         if (offset < 0 || len < 0 || offset+len > buf.length) {
855             String msg = lStrings.getString("err.io.indexOutOfBounds");
856             Object[] msgArgs = new Object[3];
857             msgArgs[0] = Integer.valueOf(offset);
858             msgArgs[1] = Integer.valueOf(len);
859             msgArgs[2] = Integer.valueOf(buf.length);
860             msg = MessageFormat.format(msg, msgArgs);
861             throw new IndexOutOfBoundsException(msg);
862         }
863
864         contentLength += len;
865     }
866 }
时间: 2024-11-09 01:56:39

HttpServlet中的2种请求处理方式的相关文章

SQL Server 中的三种分页方式

USE tempdb GO SET NOCOUNT ON --创建表结构 IF OBJECT_ID(N'ClassB', N'U') IS NOT NULL DROP TABLE ClassB GO CREATE TABLE ClassB(ID INT PRIMARY KEY, Name VARCHAR(16), CreateDate DATETIME, AID INT, Status INT) CREATE INDEX IDX_CreateDate ON ClassB(CreateDate)

Linux中的两种link方式

Linux系统中包括两种链接方式:硬链接(hard link)和符号链接(symbolic link),其中符合链接就是所谓的软链接(soft link),那么两者之间到底有什么区别呢? inode 在Linux系统中,内核为每一个新创建的文件分配一个inode,每个文件都有一个惟一的inode,这里将inode简单理解成一个指针,它永远指向本文件的具体存储位置同时,文件属性保存在inode里,比如owner等.在访问文件时,inode被复制到内存,从而实现文件的快速访问.系统是通过inode来

Oracle中的三种Join 方式

基本概念 Nested loop join: Outer table中的每一行与inner table中的相应记录join,类似一个嵌套的循环. Sort merge join: 将两个表排序,然后再进行join. Hash join: 将两个表中较小的一个在内存中构造一个Hash 表(对Join Key),扫描另一个表,同样对Join Key进行Hash后探测是否可以join,找出与之匹配的行. 一张小表被hash在内存中.因为数据量小,所以这张小表的大多数数据已经驻入在内存中,剩下的少量数据

Selenium中的几种等待方式,需特别注意implicitlyWait的用法(转)

最近在项目过程中使用selenium 判断元素是否存在的时候 遇到一个很坑爹的问题, 用以下方法执行的时候每次都会等待很长一段时间,原因是因为对selenium实现方法了解不足导致一直找不到解决方法. private boolean isElementPresent(By by) {     try { driver.findElement(by);       return true;     } catch (NoSuchElementException e) {       return

Hibeernate中的两种分页方式

1. return getHibernateTemplate().executeFind(new HibernateCallback() { public Object doInHibernate(Session s) throws HibernateException { Criteria c = s.createCriteria(AskOnline.class); c.add(Restrictions.eq("boardid", new Long(bid))); c.setFirs

转:Selenium中的几种等待方式,需特别注意implicitlyWait的用法

最近在项目过程中使用selenium 判断元素是否存在的时候 遇到一个很坑爹的问题, 用以下方法执行的时候每次都会等待很长一段时间,原因是因为对selenium实现方法了解不足导致一直找不到解决方法. private boolean isElementPresent(By by) {     try { driver.findElement(by);       return true;     } catch (NoSuchElementException e) {       return

PHP在apache中的三种工作方式

cgi是什么? CGI是外部应用程序(CGI程序)与Web服务器之间的接口标准,是在CGI程序和Web服务器之间传递信息的规程.CGI规范允许Web服务器执行外部程序,并将它们的输出发送给Web浏览器,CGI将Web的一组简单的静态超媒体文档变成一个完整的新的交互式媒体. 以下分别比较:1. CGI模式与模块模式比较:PHP在apache中两种工作方式的区别(CGI模式.Apache 模块DLL)这两种工作方式的安装:PHP 在 Apache 2.0 中的 CGI 方式ScriptAlias /

C++中的三种继承方式

1,被忽略的细节: 1,冒号( :)表示继承关系,Parent 表示被继承的类,public 的意义是什么? 1 class Parent 2 { 3 4 }; 5 6 class Child : public Parent 7 { 8 9 }; 2,有趣的问题: 1,是否可以将继承语句中的 public 换成 protected 或者 private?如果可以,与 public 继承有什么区别? 3,有趣的尝试编程实验: 1 #include <iostream> 2 #include &l

【协议分析】HTTP响应头中的2种编码方式介绍

HTTP 1.1中有两个实体头(Entity-Header)直接与编码相关,分别为Content-Encoding和Transfer-Encoding.    先说Content-Encoding, 该头表示实体已经采用了的编码方式.Content-Encoding是请求URL对应实体(Entity)本身的一部分.比如请求URL为 http://host/image.png.gz时,可能会得到的Content-Encoding为gzip.Content-Encoding的值是不区分大小写的,目前