Roxen.git / server / modules / misc / webdav.pike

version» Context lines:

Roxen.git/server/modules/misc/webdav.pike:1:   // Protocol support for RFC 2518   // - // $Id: webdav.pike,v 1.39 2010/06/28 06:57:48 marty Exp $ + // $Id$   //   // 2003-09-17 Henrik Grubbström      inherit "module";      #include <module.h>   #include <request_trace.h>    - constant cvs_version = "$Id: webdav.pike,v 1.39 2010/06/28 06:57:48 marty Exp $"; + constant cvs_version = "$Id$";   constant thread_safe = 1;   constant module_name = "WebDAV: Protocol support";   constant module_type = MODULE_FIRST;   constant module_doc = "Adds support for various HTTP extensions defined "    "in <a href='http://rfc.roxen.com/2518'>RFC 2518 (WEBDAV)</a>, such as "    "<b>PROPFIND</b> and <b>PROPPATCH</b>.";      #ifdef DAV_DEBUG   #define DAV_WERROR(X...) werror(X)   #else /* !DAV_DEBUG */
Roxen.git/server/modules/misc/webdav.pike:478:    }    // Convert destination to module location relative.    destination = destination[sizeof(loc)..];    mapping(string:mixed) res =    ((id->method == "COPY")?    module->recurse_copy_files:    module->recurse_move_files)    (source, destination, behavior, overwrite, id);    if (res && ((res->error == 201) || (res->error == 204))) {    empty_result = res; +  if (id->method == "MOVE") { +  // RFC 4918 9.9: +  // The MOVE operation on a non-collection resource is +  // the logical equivalent of a copy (COPY), followed +  // by consistency maintenance processing, followed by +  // a delete of the source, where all three actions are +  // performed in a single operation. +  +  // The above seems to imply that RFC 4918 9.6 applies +  // to MOVE. We thus need to destroy any locks rooted +  // on the moved resource. +  multiset(DAVLock) sub_locks = +  module->find_locks(source, -1, 0, id); +  foreach(sub_locks||(<>);DAVLock lock;) { +  SIMPLE_TRACE_ENTER(module, +  "MOVE: Unlocking %O...", lock); +  mapping fail = +  id->conf->unlock_file(lock->path, lock, id); +  if (fail) { +  TRACE_LEAVE("MOVE: Unlock failed."); +  } else { +  TRACE_LEAVE("MOVE: Unlock ok."); +  } +  } +  }    return 0;    }    else if (!res && id->misc->error_code) {    empty_result = Roxen.http_status(id->misc->error_code);    }    return res;    };    empty_result = Roxen.http_status(404);    break;    case "DELETE":    recur_func = lambda(string path, string ignored, int d, RoxenModule module,    RequestID id) {    mapping res = module->recurse_delete_files(path, id);    if (res && res->error < 300) {    // Succeed in deleting some file(s).    empty_result = res; -  +  +  // RFC 4918 9.6: +  // A server processing a successful DELETE request: +  // +  // MUST destroy locks rooted on the deleted resource +  multiset(DAVLock) sub_locks = +  module->find_locks(path, -1, 0, id); +  foreach(sub_locks||(<>);DAVLock lock;) { +  SIMPLE_TRACE_ENTER(module, +  "DELETE: Unlocking %O...", lock); +  mapping fail = +  id->conf->unlock_file(lock->path, lock, id); +  if (fail) { +  TRACE_LEAVE("DELETE: Unlock failed."); +  } else { +  TRACE_LEAVE("DELETE: Unlock ok."); +  } +  }    return 0;    }    return res;    };    // The multi status will be empty if everything went well,    // or if the file didn't exist.    empty_result = Roxen.http_status(404);    break;    case "PROPFIND": // Get meta data.    if (xml_data) {