skazantsev / WebDavClient

Asynchronous cross-platform WebDAV client for .NET Core
MIT License
155 stars 30 forks source link

Using PROPPATCH with custom Properties (Nextcloud/owncloud) #47

Closed CSchmidtDD closed 4 years ago

CSchmidtDD commented 4 years ago

Hi.

I could not find documentation to PROPPATCH and looked up your tests to determine how to place custom properties into the propfind Dictionary with a certain schema.

Here is the code I am using:

var _space = "http://example.com";
var _spaceNs = "{" + _space + "}";
// Construct properties
var propDict = new Dictionary<XName, string>
{
    { _spaceNs + "uploader", "chrakker" },
    { _spaceNs + "vertragstyp", item.Get_Property("Type") },
    { _spaceNs + "loeschdatum", item.Get_Property("ReminderDate02") }
};
// Construct Namespaces
var ns = new[]
{
    new NamespaceAttr("oc", "http://owncloud.org/ns"),
    new NamespaceAttr("nc", "http://nextcloud.org/ns"),
    new NamespaceAttr("te", _space)
};
// Construct the parameters
var propParam = new ProppatchParameters {
PropertiesToSet = propDict,
Namespaces = ns
};

// Call the Response
var response = _client.Proppatch(ncPath, propParam).Result;

I expect something like this:

<?xml version=""1.0"" encoding=""utf-8""?>
<D:propertyupdate xmlns:D=""DAV:"" xmlns:te=""http://example.com/"" xmlns:oc=""http://owncloud.org/ns"" xmlns:nc=""http://nextcloud.org/ns"">
    <D:set>
        <D:prop>
            <te:uploader>chrakker</X:prop1>
            <te:vertragstyp>XYZ</X:prop1>
            <te:loeschdatum>01012044</X:prop1>
        </D:prop>
    </D:set>
</D:propertyupdate>;

Sadly, it only takes the last Property from the Dict (here "loeschdatum") and sets it, not the other Properties, disregarding the length of the Dictionary completely.

Can you help me out there?

skazantsev commented 4 years ago

Hi @Chrakker,

Thank you for clear description of the issue.

Unfortunately, it's a bug in the library.

When multiple properties are passed it generates multiple prop elements, which is incorrect:

<?xml version="1.0" encoding="utf-8"?>
<D:propertyupdate xmlns:D="DAV:" xmlns:te="http://example.com/" xmlns:oc="http://owncloud.org/ns" xmlns:nc="http://nextcloud.org/ns">
    <D:set>
        <D:prop>
            <te:uploader>chrakker</te:uploader>
        </D:prop>
        <D:prop>
            <te:vertragstyp>XYZ</te:vertragstyp>
        </D:prop>
        <D:prop>
            <te:loeschdatum>01012044</te:loeschdatum>
        </D:prop>
    </D:set>
</D:propertyupdate>

Looks like some WebDAV servers can handle it and set all properties but a correct request should look like:

<?xml version="1.0" encoding="utf-8"?>
<D:propertyupdate xmlns:D="DAV:" xmlns:te="http://example.com/" xmlns:oc="http://owncloud.org/ns" xmlns:nc="http://nextcloud.org/ns">
    <D:set>
        <D:prop>
            <te:uploader>chrakker</te:uploader>
            <te:vertragstyp>XYZ</te:vertragstyp>
            <te:loeschdatum>01012044</te:loeschdatum>
        </D:prop>
    </D:set>
</D:propertyupdate>

I'll release a new version with a fix.

skazantsev commented 4 years ago

A new version with a fix is available in NuGet.

CSchmidtDD commented 4 years ago

Hi @skazantsev ,

thank you for your fast fix. Am currently working with owncloud/nextcloud and this behaviour is a major QOL change for me and probably others as well that included your NuGet. Very much appreciated, indeed!