]> git.ipfire.org Git - thirdparty/apache/httpd.git/commitdiff
Merge r1911651, r1911906 from trunk:
authorJoe Orton <jorton@apache.org>
Mon, 4 Sep 2023 12:00:01 +0000 (12:00 +0000)
committerJoe Orton <jorton@apache.org>
Mon, 4 Sep 2023 12:00:01 +0000 (12:00 +0000)
Add DAVBasePath directive to allow users to configure the real repos
root path, useful where the DAV repos is configured with a regex match.

* modules/dav/main/mod_dav.c
  (dav_get_resource): If available, pass the configured base path
  as the repos root to repos provider.
  On the error path for fetching a resource, detect and warn
  specifically when the location is configured via a regex.
  (dav_cmd_davbasepath): New function.

PR: 35077
Github: closes #377
Reviewed by: jorton, minfrin, rpluem

Merge r1911715, r1911907 from trunk:

Add docs for DavBasePath
Fix documented default for DavBasePath to match code.

git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1912081 13f79535-47bb-0310-9956-ffa450edef68

CHANGES
docs/manual/mod/mod_dav.xml
modules/dav/main/mod_dav.c

diff --git a/CHANGES b/CHANGES
index 9fea3219bd2230f566c599bcdc43d60592f14036..1fd6daace7e5e894c282943fe37b809683f98a0f 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,6 +1,9 @@
                                                          -*- coding: utf-8 -*-
 Changes with Apache 2.4.58
 
+  *) mod_dav: Add DavBasePath directive to configure the repository root
+     path.  PR 35077.  [Joe Orton]
+
   *) mod_alias: Add RedirectRelative to allow relative redirect targets to be
      issued as-is. [Eric Covener, Graham Leggett]
 
index c4eb0bb4dae246cde1c101ec896a16563bedd544..cac5c9cf8801b73510b169fccfe78c524eaa98ec 100644 (file)
@@ -194,6 +194,36 @@ Alias "/php-source" "/home/gstein/php_files"
 </usage>
 </directivesynopsis>
 
+<directivesynopsis>
+<name>DavBasePath</name>
+<description>Configure repository root path</description>
+<syntax>DavBasePath <var>root-path</var></syntax>
+<default>None</default>
+<contextlist><context>directory</context></contextlist>
+<compatibility>Available in version 2.5.1 and later</compatibility>
+
+<usage>
+  <p>If a DAV repository is configured using a regular expression
+  match (such as <directive module="core">LocationMatch</directive>)
+  then <module>mod_dav</module> will not be able to find the root of
+  the repository from the pathname alone. Third-party providers (for
+  example, Subversion's <a
+  href="https://svnbook.red-bean.com/en/1.7/svn.ref.mod_dav_svn.conf.html">mod_dav_svn</a>)
+  may fail to handle requests without the correct repository root.</p>
+
+  <p>To allow providers to work correctly in such a configuration,
+  <directive>DavBasePath</directive> must be used.</p>
+
+    <highlight language="config">
+&lt;LocationMatch "^/repos/"&gt;
+    Dav svn
+    DavBasePath /repos
+    SVNParentPath /var/svn
+&lt;/LocationMatch&gt;
+    </highlight>
+</usage>
+</directivesynopsis>
+
 <directivesynopsis>
 <name>DavMinTimeout</name>
 <description>Minimum amount of time the server holds a lock on
index d16ab4a1b2729c9f844cffcd532d308b021a77be..a035f254f4d78eaccd4319b406f6f8a6ae5ed34c 100644 (file)
@@ -81,6 +81,7 @@ typedef struct {
     const char *provider_name;
     const dav_provider *provider;
     const char *dir;
+    const char *base;
     int locktimeout;
     int allow_depthinfinity;
     int allow_lockdiscovery;
@@ -196,6 +197,7 @@ static void *dav_merge_dir_config(apr_pool_t *p, void *base, void *overrides)
 
     newconf->locktimeout = DAV_INHERIT_VALUE(parent, child, locktimeout);
     newconf->dir = DAV_INHERIT_VALUE(parent, child, dir);
+    newconf->base = DAV_INHERIT_VALUE(parent, child, base);
     newconf->allow_depthinfinity = DAV_INHERIT_VALUE(parent, child,
                                                      allow_depthinfinity);
     newconf->allow_lockdiscovery = DAV_INHERIT_VALUE(parent, child,
@@ -282,6 +284,18 @@ static const char *dav_cmd_dav(cmd_parms *cmd, void *config, const char *arg1)
     return NULL;
 }
 
+/*
+ * Command handler for the DAVBasePath directive, which is TAKE1
+ */
+static const char *dav_cmd_davbasepath(cmd_parms *cmd, void *config, const char *arg1)
+{
+    dav_dir_conf *conf = config;
+
+    conf->base = arg1;
+
+    return NULL;
+}
+
 /*
  * Command handler for the DAVDepthInfinity directive, which is FLAG.
  */
@@ -748,7 +762,7 @@ DAV_DECLARE(dav_error *) dav_get_resource(request_rec *r, int label_allowed,
                                    int use_checked_in, dav_resource **res_p)
 {
     dav_dir_conf *conf;
-    const char *label = NULL;
+    const char *label = NULL, *base;
     dav_error *err;
 
     /* if the request target can be overridden, get any target selector */
@@ -765,11 +779,27 @@ DAV_DECLARE(dav_error *) dav_get_resource(request_rec *r, int label_allowed,
                              ap_escape_html(r->pool, r->uri)));
     }
 
+    /* Take the repos root from DAVBasePath if configured, else the
+     * path of the enclosing section. */
+    base = conf->base ? conf->base : conf->dir;
+
     /* resolve the resource */
-    err = (*conf->provider->repos->get_resource)(r, conf->dir,
+    err = (*conf->provider->repos->get_resource)(r, base,
                                                  label, use_checked_in,
                                                  res_p);
     if (err != NULL) {
+        /* In the error path, give a hint that DavBasePath needs to be
+         * used if the location was configured via a regex match. */
+        if (!conf->base) {
+            core_dir_config *cdc = ap_get_core_module_config(r->per_dir_config);
+
+            if (cdc->r) {
+                ap_log_error(APLOG_MARK, APLOG_ERR, 0, NULL, APLOGNO(10484)
+                             "failed to find repository for location configured "
+                             "via regex match - missing DAVBasePath?");
+            }
+        }
+
         err = dav_push_error(r->pool, err->status, 0,
                              "Could not fetch resource information.", err);
         return err;
@@ -5164,6 +5194,10 @@ static const command_rec dav_cmds[] =
     AP_INIT_TAKE1("DAV", dav_cmd_dav, NULL, ACCESS_CONF,
                   "specify the DAV provider for a directory or location"),
 
+    /* per directory/location */
+    AP_INIT_TAKE1("DAVBasePath", dav_cmd_davbasepath, NULL, ACCESS_CONF,
+                  "specify the DAV repository base URL"),
+
     /* per directory/location, or per server */
     AP_INIT_TAKE1("DAVMinTimeout", dav_cmd_davmintimeout, NULL,
                   ACCESS_CONF|RSRC_CONF,