Subject: [core] CoAP's handling of trailing slash in URI - to file erratum?

From: "Dijk, Esko" <[email-masked]>
Date: Tue, 20 Dec 2016 11:49:33 +0000

Dear CoRE WG,

while looking at the CoAP spec recently me and some colleagues found a potential wording issue in the handling of URIs with trailing slash (/) character in CoAP. The issue is as follows:
one would like to encode the below two CoAP URIs as separate CoAP requests because the two are in principle semantically different:
  Example #1:  coap://host.example.com/path
  Example #2:  coap://host.example.com/path/

(Although many CoAP servers will want to treat these requests in an identical way, similar to the way HTTP servers do, in the generic case these are different requests.)

The Example #1 URI will be encoded with a single Uri-Path option containing 4 bytes "path".
The #2 URI should be encoded with two Uri-Path options, one containing "path" and a second one of zero bytes.

However - RFC 7252 Section 6.4 step 8 mentions: " for each segment in the <path> component, include a Uri-Path Option and let that option's value be the segment (not including the delimiting slash characters)".
Now taking the above two examples, example #1 contains a single segment "path" which is encoded as one Uri-Path Option. Example #2 also contains a single segment "path", encoded as one Uri-Path Option, and the delimiting slash character is ignored just like the text says. So the problem is that both examples are encoded in exactly the same CoAP request, which the CoAP server. Furthermore it may be unclear to an implementer that the Example #2 path contains in fact two path segments, of which the 2nd is an empty segment. Because the text appears to say "don't include the delimiting slash character" this will easily go wrong.
For example, the often-used Eclipse Californium library (1.1.0) has this problem.

I'm planning to file an erratum on this item since clarification of RFC 7252 is clearly needed. This email is to check if others agree, or not, and whether I missed something.

best regards,
Esko Dijk

________________________________
The information contained in this message may be confidential and legally protected under applicable law. The message is intended solely for the addressee(s). If you are not the intended recipient, you are hereby notified that any use, forwarding, dissemination, or reproduction of this message is strictly prohibited and may be unlawful. If you are not the intended recipient, please contact the sender by return e-mail and destroy all copies of the original message.

---

From: Carsten Bormann <[email-masked]>
Date: Tue, 20 Dec 2016 13:33:25 +0100

Hi Esko,

RFC 3986 is a normative reference of RFC 7252.
While the defining parts of RFC 3986 (e.g., Section 3.3) are not very explicit about this (you have to read the ABNF to understand), Section 6.2.4 finally is.

>   Example #2:  coap://host.example.com/path/

Not just in principle — they definitely are different.

> (Although many CoAP servers will want to treat these requests in an identical way, similar to the way HTTP servers do, in the generic case these are different requests.)

They can’t do this in the same way HTTP servers do this, as that involves a redirect (which we deliberately don’t have in CoAP).

> The #2 URI should be encoded with two Uri-Path options, one containing "path" and a second one of zero bytes.

Yes.

> Now taking the above two examples, example #1 contains a single segment "path" which is encoded as one Uri-Path Option. Example #2 also contains a single segment "path”,

Segment is defined (Section 6 intro) to be a reference to the terminology defined by RFC 3986, and we clearly have two RFC 3986 segments in the second case.

We probably don’t have an example in RFC 7252 because that is not emphasizing collections (which is where these URIs typically occur).

> encoded as one Uri-Path Option, and the delimiting slash character is ignored just like the text says. So the problem is that both examples are encoded in exactly the same CoAP request, which the CoAP server. Furthermore it may be unclear to an implementer that the Example #2 path contains in fact two path segments, of which the 2nd is an empty segment. Because the text appears to say "don't include the delimiting slash character" this will easily go wrong.
> I'm planning to file an erratum on this item since clarification of RFC 7252 is clearly needed. 

Filing an erratum calling for making the fact more explicit that RFC 3986 works this way is good.
(It is not, however, an “erratum” in the Latin sense of the word; the text is unambiguous when properly consulting the references, and it is not wrong.)

Grüße, Carsten

---

From: Klaus Hartke <[email-masked]>
Date: Tue, 20 Dec 2016 13:44:23 +0100

Esko Dijk wrote:
> one would like to encode the below two CoAP URIs as separate CoAP requests
> because the two are in principle semantically different:
>
> [...]

This is the correct behavior.

Section 3.3 of RFC 3986 [1] defines the path component of a URI as a
sequence of (possibly empty) segments separated by a slash character:

      path-abempty  = *( "/" segment )
      path-absolute = "/" [ segment-nz *( "/" segment ) ]
      path-noscheme = segment-nz-nc *( "/" segment )
      path-rootless = segment-nz *( "/" segment )
      path-empty    = 0<pchar>

As the ABNF shows, there are two segments in Example #2 ("path" and
"") and segments do not include the slash character. RFC 7252 Section
6.4 step 8 tries to make that double clear by saying "let that
option's value be the segment (not including the delimiting slash
characters)".

So I don't think that RFC 7252 is wrong. Of course, there is always
room for improvement of the text.

Klaus

[1] https://tools.ietf.org/html/rfc3986#section-3.3