Fix WebDAV ACL validation in multiget reports (fixes #1768)

This commit is contained in:
mdecimus
2025-07-14 13:16:47 +02:00
parent 1035183ec7
commit fb5a7ec144
3 changed files with 57 additions and 20 deletions

View File

@@ -1480,7 +1480,7 @@ async fn multiget(
if !resource.is_container() {
if document_ids
.as_ref()
.is_none_or(|docs| docs.contains(resource.document_id()))
.is_none_or(|docs| docs.contains(resource.parent_id().unwrap()))
{
paths.push(PropFindItem::new(
resources.format_resource(resource),

View File

@@ -120,6 +120,25 @@ pub async fn test(test: &WebDavTest) {
.await
.with_status(StatusCode::OK)
.with_body(&owner_file_content);
match resource_type {
DavResourceName::Cal => {
sharee_client
.multiget_calendar(&owner_folder, &[&owner_file])
.await
.properties(&owner_file)
.with_status(StatusCode::OK)
.is_defined(DavProperty::WebDav(WebDavProperty::GetETag));
}
DavResourceName::Card => {
sharee_client
.multiget_addressbook(&owner_folder, &[&owner_file])
.await
.properties(&owner_file)
.with_status(StatusCode::OK)
.is_defined(DavProperty::WebDav(WebDavProperty::GetETag));
}
_ => {}
}
// Test 5: Read ACL as owner
let response = owner_client

View File

@@ -5,7 +5,7 @@
*/
use super::WebDavTest;
use crate::webdav::GenerateTestDavResource;
use crate::webdav::{DummyWebDavClient, GenerateTestDavResource, prop::DavMultiStatus};
use dav_proto::schema::property::{CalDavProperty, CardDavProperty, DavProperty, WebDavProperty};
use groupware::DavResourceName;
use hyper::StatusCode;
@@ -16,8 +16,7 @@ const MULTIGET_CALENDAR: &str = r#"<?xml version="1.0" encoding="utf-8" ?>
<D:getetag/>
<C:calendar-data/>
</D:prop>
<D:href>$PATH_1</D:href>
<D:href>$PATH_2</D:href>
$PATH
</C:calendar-multiget>
"#;
const MULTIGET_ADDRESSBOOK: &str = r#"<?xml version="1.0" encoding="utf-8" ?>
@@ -27,8 +26,7 @@ const MULTIGET_ADDRESSBOOK: &str = r#"<?xml version="1.0" encoding="utf-8" ?>
<D:getetag/>
<C:address-data/>
</D:prop>
<D:href>$PATH_1</D:href>
<D:href>$PATH_2</D:href>
$PATH
</C:addressbook-multiget>
"#;
@@ -56,14 +54,9 @@ pub async fn test(test: &WebDavTest) {
if resource_type == DavResourceName::Cal {
let path = format!("{}/john", resource_type.base_path());
let body = MULTIGET_CALENDAR
.replace("$PATH_1", &paths[0].0)
.replace("$PATH_2", &paths[1].0);
let response = client
.request("REPORT", &path, &body)
.await
.with_status(StatusCode::MULTI_STATUS)
.into_propfind_response(None);
.multiget_calendar(&path, &[&paths[0].0, &paths[1].0])
.await;
for (path, etag, contents) in paths {
let props = response.properties(&path);
props
@@ -77,14 +70,9 @@ pub async fn test(test: &WebDavTest) {
}
} else {
let path = format!("{}/john", resource_type.base_path());
let body = MULTIGET_ADDRESSBOOK
.replace("$PATH_1", &paths[0].0)
.replace("$PATH_2", &paths[1].0);
let response = client
.request("REPORT", &path, &body)
.await
.with_status(StatusCode::MULTI_STATUS)
.into_propfind_response(None);
.multiget_addressbook(&path, &[&paths[0].0, &paths[1].0])
.await;
for (path, etag, contents) in paths {
let props = response.properties(&path);
props
@@ -102,3 +90,33 @@ pub async fn test(test: &WebDavTest) {
client.delete_default_containers().await;
test.assert_is_empty().await;
}
impl DummyWebDavClient {
pub async fn multiget_calendar(&self, path: &str, uris: &[&str]) -> DavMultiStatus {
let mut paths = String::new();
for uri in uris {
paths.push_str(&format!("<D:href>{}</D:href>", uri));
}
self.request("REPORT", path, &MULTIGET_CALENDAR.replace("$PATH", &paths))
.await
.with_status(StatusCode::MULTI_STATUS)
.into_propfind_response(None)
}
pub async fn multiget_addressbook(&self, path: &str, uris: &[&str]) -> DavMultiStatus {
let mut paths = String::new();
for uri in uris {
paths.push_str(&format!("<D:href>{}</D:href>", uri));
}
self.request(
"REPORT",
path,
&MULTIGET_ADDRESSBOOK.replace("$PATH", &paths),
)
.await
.with_status(StatusCode::MULTI_STATUS)
.into_propfind_response(None)
}
}