@rfc2822 Works! Thank you!
411 length error, DAVdroid 22.214.171.124, Owncloud
2016-06-14 13:39:58 2 [HttpClient$1] --> OPTIONS https://myDomain.de/owncloud/remote.php/carddav/principals/georg/ http/1.1 2016-06-14 13:39:58 2 [HttpClient$1] --> END OPTIONS 2016-06-14 13:39:58 2 [HttpClient$1] <-- 411 https://myDomain.de/owncloud/remote.php/carddav/principals/georg/ (28ms) 2016-06-14 13:39:58 2 [HttpClient$1] date: Tue, 14 Jun 2016 11:39:57 GMT 2016-06-14 13:39:58 2 [HttpClient$1] server: Apache 2016-06-14 13:39:58 2 [HttpClient$1] content-length: 242 2016-06-14 13:39:58 2 [HttpClient$1] content-type: text/html; charset=iso-8859-1 2016-06-14 13:39:58 2 [HttpClient$1] 2016-06-14 13:39:58 2 [HttpClient$1] <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html><head> <title>411 Length Required</title> </head><body> <h1>Length Required</h1> <p>A request of the requested method OPTIONS requires a valid Content-length.<br /> </p> </body></html> 2016-06-14 13:39:58 2 [HttpClient$1] <-- END HTTP (242-byte body)
In my opinion, this is quite creative server behavior because
OPTIONSrequests usually don’t have a body (in contrast to a well-defined, zero-length body like in
POST), as such a body is not even defined in current HTTP versions.
Are you server admin? Which server do you use? Are there any forwarding proxies?
Can you maybe provide a test account?
Small Provider with shared LAMP hosting.
PHP tells me:
PHP 5.6.22-pl0-gentoo (FPM)
How to send a PM with test account of my Owncloud installation?
Thanks for the credentials.
This is super-strange, I can reproduce the problem with DAVdroid, but not with curl …
Seems to work when disabling HTTP/2. So this seems to be another HTTP/2 problem … and I will have to debug that without being able to read/write the communications directly. Thanks, Google
In the meanwhile, you could ask your provider to disable HTTP/2. Maybe we will also provide a DAVdroid option to disable this … Would also be interesting to know their setup (which Apache version, how HTTP/2 is provided, if there are forwarding proxies etc.).
I was able to capture the failing request using mitmproxy:
OPTIONS /xxx/remote.php/carddav/principals/bitfire/ HTTP/2.0 :method: OPTIONS :path: /xxx/remote.php/carddav/principals/bitfire/ :authority: xxxdomain.de :scheme: https accept-encoding: identity cookie: oc_sessionPassphrase=CXlmDs1%2FwUpwtbMSuAw5h1F2XPIDgcL%2Fq3TNAHQGFI1StsXijz16fKwcxQFw1SGTGokq7cof%2Bupo1UBu9Ac%2F35a0VZ2Ib8qrqrFHg16Id9TeXlo6D2D6JG%2BwKiBA8F7z; occd3fe1ecae=rorto1rl5dioi4r8licjljvtj1 user-agent: DAVdroid/126.96.36.199 (2016/06/15; dav4android; okhttp3) Android/6.0.1 accept-language: en-US, en;q=0.7, *;q=0.5 authorization: Basic xxxxxxxxxx host: xxxdomain.de
HTTP/2.0 411 :status: 411 date: Wed, 15 Jun 2016 12:34:18 GMT server: Apache content-length: 242 content-type: text/html; charset=iso-8859-1 <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html><head> <title>411 Length Required</title> </head><body> <h1>Length Required</h1> <p>A request of the requested method OPTIONS requires a valid Content-length.<br /> </p> </body></html>
However, when replaying the same request with mitmproxy, the server replies with 200 OK. So I guess the problem must be somewhere in the deep stream handling details of okhttp/the server (although I don’t know how these details could cause a HTTP 411 error). And honestly, debugging becomes really awkward now …
My provider had now disabled HTTP/2.
And my Life is back:
my personal assistant could tell me again what to do on the next days and how to contact my friends ;-))
Same time when problems started with DAVdroid I had also problems with Thunderbird.
After deactivating http/2 in Thunderbird config:
everything was fine with Thunderbird again.
So - nevertheless my problems are solved by my current provider - but as a user of DAVdroid I would like to be enabled to disable HTTP/2 in DAVdroid ;-))
Many thanks for Your quick Response and debugging efforts - and identifying HTTP/2 as the big problem.
Sorry for digging out this old topic, but I have the same error…
I’m running sabre/katana 0.4.2 as DAV server (shipping with sabre/dav 3.0.5), did also test baikal in version 0.4.6 (using sabre/dav 3.1.4).
My provider upgraded a few months ago to Apache 2.4 and enabled http/2. Disabling http/2 in Thunderbird did the trick for the sync problems on my computer, DAVdroid continued to work as expected. A few days ago my phone broke, got a new one. Now I cannot create my account anymore, DAVdroid gives me the error message no DAV-Server found.
Android version: 6.0.1
Device: HTC One A9 (hiaeul)
Rom: Cyanogenmod 13, nightly 29161001
DAVdroid: 1.3.1-ose (from F-Droid)
Did also test this with my old Phone (Samsung Galaxy S4 Active GT-I9295 with cm12) and with my dad’s phone (Galaxy S4 mini, cm13), syncing with a existing account (account installed prior to Apache 2.4 migration) works, new account does not.
Disabling http/2 on server side is not an option, my provider does not support this.
Is there anything I can do about this (except changing my provider)? Happy to provide test accounts (baikal and katana).
@mic Thanks for the test accounts, I was now able to identify the problem:
It’s all about the
OPTIONSrequest. Basically, it can be sent with or without request body. Currently, an
OPTIONSrequest body has no defined semantic value and is not required for DAVdroid’s purposes, so we choose to send the request without request body.
With HTTP/1.1, it’s quite easy. The request is sent as
OPTIONS /path HTTP/1.1
Content-Lengthand request body, and everything works fine.
However, with HTTP/2, it becomes more difficult, because there are
DATAframes. If a request has no body, no
DATAframe should be sent. However, okhttp sends an empty
DATAframe with 0 bytes:
davdroid.DavResourceFinder: [HttpClient$1] --> OPTIONS https://yourserver/katana/public/server.php/principals/bitfire/ http/1.1 davdroid.DavResourceFinder: [HttpClient$1] --> END OPTIONS davdroid.dav4android: [dav4android.BasicDigestAuthHandler] Adding Basic authorization header for https://yourserver/katana/public/server.php/principals/bitfire/ okhttp3.internal.framed.Http2$FrameLogger: [okhttp3.internal.framed.Http2$Writer] >> 0x0000001f 218 HEADERS END_HEADERS [!!!] okhttp3.internal.framed.Http2$FrameLogger: [okhttp3.internal.framed.Http2$Writer] >> 0x0000001f 0 DATA END_STREAM okhttp3.internal.framed.Http2$FrameLogger: [okhttp3.internal.framed.Http2$Reader] << 0x0000001f 7 HEADERS END_HEADERS
although dav4android specifies a request without body (body is null). The Apache 2.4 server then rejects the request because there’s a request body (i.e. data frame), but no
So, it seems to be an okhttp problem. I have reported this to okhttp and I’m waiting for response.
The problem can be simulated with nghttp, too:
nghttp -v -H ':method:OPTIONS' -H 'Authorization: Basic ***' https://yourserver/baikal/html/dav.phpworks as expected, while a 0-byte data frame without
Content-Length, generated by
nghttp -v -d /dev/null --no-content-length -H ':method:OPTIONS' -H 'Authorization: Basic ***' https://yourserver/baikal/html/dav.phpcauses an error.
A workaround is to specify
Content-Length: 0in the
OPTIONSrequest (so the request has a body, but with specified length, which is OK for the server, too). We’ll implement this for the next DAVdroid version until okhttp is fixed.
Thanks for your support! I’d like to quote Georg:
And my Life is back:
my personal assistant could tell me again what to do on the next days and how to contact my friends )
I did apply your fix, works flawless! Adding accounts (tested on several devices) and syncing changes over different devices works perfect.
Many thanks for your quick response and your help.
The workaround has now been released with DAVdroid 188.8.131.52.
BTW, this has been fixed in okhttp now.