// ToolsListerFrame.java // $Id: ToolsListerFrame.java,v 1.10 1998/08/14 11:05:59 bmahe Exp $ // (c) COPYRIGHT MIT and INRIA, 1998. // Please first read the full copyright statement in file COPYRIGHT.html package org.w3c.jigsaw.cvs ; import java.io.* ; import java.util.* ; import org.w3c.tools.resources.*; import org.w3c.tools.sorter.*; import org.w3c.www.mime.*; import org.w3c.jigsaw.forms.*; import org.w3c.jigsaw.http.* ; import org.w3c.jigsaw.html.* ; import org.w3c.jigsaw.frames.* ; import org.w3c.www.http.* ; import org.w3c.tools.resources.event.*; /** * Emit the content of its parent directory. */ public class ToolsListerFrame extends PostableFrame implements StructureChangedListener { private boolean invalid = true; private ResourceReference dirResourceRef = null; protected ResourceReference getDirResourceRef() { if (invalid || (dirResourceRef == null)) { dirResourceRef = getResource().getParent(); } return dirResourceRef; } public void registerResource(FramedResource resource) { super.registerOtherResource(resource); dirResourceRef = resource.getParent(); try { FramedResource fres = (FramedResource)dirResourceRef.lock(); // register us as a listener fres.addStructureChangedListener(this); } catch(InvalidResourceException ex) { ex.printStackTrace(); } finally { dirResourceRef.unlock(); } invalid = false; } /** * Unused here. */ public void resourceModified(StructureChangedEvent evt) { } /** * Unused here. */ public void resourceCreated(StructureChangedEvent evt) { } public void resourceUnloaded(StructureChangedEvent evt){ } /** * A resource is about to be removed * This handles the RESOURCE_REMOVED kind of events. * @param evt The event describing the change. */ public void resourceRemoved(StructureChangedEvent evt) { invalid = true; } /** * Get the directory listing. * @param request the incomming request. * @exception ProtocolException if a protocol error occurs * @exception ResourceException if a server error occurs */ public synchronized Reply getDirectoryListing(Request request) throws ProtocolException, ResourceException { DirectoryResource dirResource = null; try { dirResource = (DirectoryResource) getDirResourceRef().lock(); if (dirResource == null) throw new ResourceException("parent is NOT a "+ "DirectoryResource. ("+ resource.getIdentifier()+")"); if (! dirResource.verify()) { // the directory was deleted, but we can't delete it here // (Multiple Locks) // Emit an error back: Reply error = request.makeReply(HTTP.NOT_FOUND) ; error.setContent ("

Document not found

"+ "

The document "+ request.getURL()+ " is indexed but not available."+ "

The server is misconfigured.") ; throw new HTTPException (error) ; } // Have we already an up-to-date computed a listing ? if ((listing == null) || (dirResource.getDirectory().lastModified() > listing_stamp) || (dirResource.getLastModified() > listing_stamp) || (getLastModified() > listing_stamp)) { Class httpClass = null; try { httpClass=Class.forName("org.w3c.jigsaw.frames.HTTPFrame"); } catch (ClassNotFoundException ex) { httpClass = null; } Enumeration enum = dirResource.enumerateResourceIdentifiers() ; Vector resources = Sorter.sortStringEnumeration(enum) ; HtmlGenerator g = new HtmlGenerator("Directory of "+ dirResource.getIdentifier()); // Add style link addStyleSheet(g); g.append("

"+dirResource.getIdentifier()+"

"); // Link to the parent, when possible: if ( dirResource.getParent() != null ) g.append("

Parent
"); g.append("\n

\n"); // List the children: for (int i = 0 ; i < resources.size() ; i++) { String name = (String) resources.elementAt(i); ResourceReference rr = null; rr = dirResource.lookup(name); FramedResource resource = null; try { resource = (FramedResource) rr.lock(); HTTPFrame itsframe = null; if (httpClass != null) itsframe = (HTTPFrame)resource.getFrame(httpClass); g.append(" "); if (itsframe != null) { // Icon first, if available String icon = itsframe.getIcon() ; if ( icon != null ) g.append(""); // Resource's name with link: g.append(""+name+""); // resource's title, if any: String title = itsframe.getTitle(); if ( title != null ) g.append(" "+title); g.append("
\n"); } else { // Resource's name with link: g.append(""+name+""+" No HTTP Frame!"); g.append("
\n"); } } catch (InvalidResourceException ex) { g.append(name + " cannot be loaded (server misconfigured)"); g.append("
"); continue; } finally { rr.unlock(); } } g.append("

\n"); g.close() ; listing_stamp = getLastModified() ; listing = g ; } else if ( checkIfModifiedSince(request) == COND_FAILED ) { // Is it an IMS request ? return createDefaultReply(request, HTTP.NOT_MODIFIED) ; } } catch (InvalidResourceException ex) { return createDefaultReply(request, HTTP.INTERNAL_SERVER_ERROR); } finally { getDirResourceRef().unlock(); } // New content or need update: Reply reply = createDefaultReply(request, HTTP.OK) ; reply.setLastModified(listing_stamp) ; reply.setStream(listing) ; return reply ; } /** * @exception org.w3c.tools.resources.ProtocolException * if a protocol error occurs * @exception org.w3c.tools.resources.ResourceException * if a server error occurs */ protected Reply getOtherResource (Request request) throws ProtocolException, ResourceException { return getDirectoryListing(request); } /** * Handle the form submission, after posted data parsing. *

This method ought to be abstract, but for reasonable reason, it * will just dump (parsed) the form content back to the client, so that it * can be used for debugging. * @param request The request proper. * @param data The parsed data content. * @exception ProtocolException If form data processing failed. * @see org.w3c.jigsaw.forms.URLDecoder */ public Reply handle (Request request, URLDecoder data) throws ProtocolException { Reply r; Enumeration e = data.keys() ; while ( e.hasMoreElements () ) { String name = (String) e.nextElement() ; if (name.equals("SUBMIT")) continue; // delete file now... avoit deleting CVS and lister // (should be in an attribute) synchronized (this) { DirectoryResource dr; Resource toDeleteRes; ResourceReference rr; File dir, toDeleteFile; try { dr = (DirectoryResource) getDirResourceRef().lock(); dir = dr.getDirectory(); System.out.println("Deleting " + name); rr = dr.lookup(name); if (rr != null) { try { toDeleteFile = new File(dir, name); toDeleteFile.delete(); } catch (Exception ex) { // fancy message. file not present // Or security manager forbiding deletion. } // and now, at least remove the resource try { toDeleteRes = (Resource) rr.lock(); toDeleteRes.delete(); } catch (Exception ex) { // some other locks... or pb with the resource } finally { rr.unlock(); } } } catch (Exception ex) { // some other locks... abort } finally { getDirResourceRef().unlock(); } } } try { r = getDirectoryListing(request); } catch (ResourceException ex) { r = createDefaultReply(request, HTTP.INTERNAL_SERVER_ERROR); } return r; } }