001: /*
002: * DirectoryComponent.java February 2001
003: *
004: * Copyright (C) 2001, Niall Gallagher <niallg@users.sf.net>
005: *
006: * This library is free software; you can redistribute it and/or
007: * modify it under the terms of the GNU Lesser General Public
008: * License as published by the Free Software Foundation.
009: *
010: * This library is distributed in the hope that it will be useful,
011: * but WITHOUT ANY WARRANTY; without even the implied warranty of
012: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
013: * GNU Lesser General Public License for more details.
014: *
015: * You should have received a copy of the GNU Lesser General
016: * Public License along with this library; if not, write to the
017: * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
018: * Boston, MA 02111-1307 USA
019: */
020:
021: package simple.http.serve;
022:
023: import simple.http.Response;
024: import simple.http.Request;
025:
026: /**
027: * This is used to display the contents of a directory when that
028: * directory is referenced. This will generate a HTML response
029: * that will reference every file in that directory using the
030: * <code>File.list</code> method. This creates the HTML contents
031: * of the directory referenced
032: * <p>
033: * This must be given a URI style path, that is a path in the
034: * form of a URI path, UNIX style, for example /a/b. This allows
035: * the <code>Component</code> more flexibility across platforms.
036: * The path given MUST be relative to the current directory. So
037: * if the path is ./path/ then the path given must be /path/.
038: * Backward references are not permitted so a path like ../
039: * is illegal.
040: *
041: * @author Niall Gallagher
042: */
043: final class DirectoryComponent extends IndexedComponent {
044:
045: /**
046: * Constructs a HTML <code>Component</code> to represent the path
047: * specified. The <code>handle</code> method will generate a HTML
048: * listing of all the files in the directory with hyperlinks to
049: * them.
050: *
051: * @param target this is the HTTP request URI for this resource
052: * @param context the root context of this directory resource
053: */
054: public DirectoryComponent(Context context, String target) {
055: super (context, target);
056: }
057:
058: /**
059: * This will generate the HTML listing of the contents of the
060: * referenced directory. Because this listing may be for a
061: * directory that is some directories in depth there may be a
062: * need to give paths relative to the current path. For example
063: * if the URI path "/pub/bin" were the directory "/pub/bin/"
064: * then if the relative URL "README.txt" was clicked on the
065: * page "/pub/bin" the browser would think that it would have
066: * to look for that using the path "/usr/README.txt" because
067: * the browser thinks that "/pub/bin" is not a directory but
068: * rather a resource in "/pub". For a browser to realize that
069: * the URL path it is looking at is a directory and thus look
070: * for relative URLs in it, it needs a "/" ending for this.
071: * <p>
072: * If the method used is HEAD then this will write only the
073: * headers and will subsequently close the pipeline. However
074: * this will not handle POST, OPTIONS, TRACE, DELETE or PUT
075: * requests and will generate a "501 Not Implemented" message
076: * if attempted, see RFC 2616 sec 5.1.1.
077: *
078: * @param req the <code>Request</code> to be processed
079: * @param resp the <code>Response</code> to be processed
080: *
081: * @exception Exception this is thrown if an uncaptured
082: * <code>Exception</code> propagates
083: */
084: protected void process(Request req, Response resp) throws Exception {
085: if (req.getDate("If-Modified-Since") < getLastModified()) {
086: Format format = context.getFormat();
087: byte[] text = format.getContents(context, target);
088:
089: resp.setDate("Date", System.currentTimeMillis());
090: resp.setDate("Last-Modified", getLastModified());
091: resp.set("Content-Type", format.getContentType());
092: resp.setContentLength(text.length);
093:
094: if (req.getMethod().equals("HEAD")) {
095: resp.commit();
096: } else if (req.getMethod().equals("GET")) {
097: resp.getOutputStream().write(text);
098: resp.getOutputStream().close();
099: } else {
100: handle(req, resp, 501);
101: }
102: } else {
103: handle(req, resp, 304);
104: }
105: }
106: }
|