Subject: [hybi] -09: abstract and introduction

From: Peter Saint-Andre <[email-masked]>
Date: Wed, 15 Jun 2011 15:10:34 -0600

I've started reviewing -09. For several reasons (mostly because my
review time keeps getting interrupted), I'll provide feedback by
section. This set of comments is mostly editorial.

The abstract seems over-specific. I suggest deleting the parentheticals
and putting them in a slightly-longer first paragraph in the intro
(before Section 1.1).

Section 1.1 has always struck me as strange. It sounds as if we're
developing an IM protocol here! I suggest:

   Historically, creating Web applications that need bidirectional
   communication between a client and a server (e.g., instant messaging
   and gaming applications) has required an abuse of HTTP to poll the
   server for updates while sending upstream notifications as distinct
   HTTP calls. [RFC6202]

I think it would also be helpful to provide an additional paragraph at
the end of Section 1.1 with a bit of justification for why people who
want to write bidirectional Web applications can't simply use existing
application protocols such as IRC and XMPP. Yes, port 80 is the one true
port, and developers complain that it would be a pain to build protocols
like IRC and XMPP directly into a browser, but nothing says it's impossible.

BTW [I-D.ietf-httpstate-cookie] is now [RFC6265] (thanks, Adam!).

Section 1.3 says:

   If the
   server does not wish to accept connections from this origin, it can
   choose to reject the connection by sending an appropriate HTTP error
   code.

Which code?

Section 1.3 says:

   A JavaScript application cannot set a header starting with "Sec-" via
   XHR.

Why not? What is the nature of the restriction?

Section 1.3 says:

   If the |Sec-WebSocket-Accept|
   value does not match the expected value, or if the header is missing,
   or if the HTTP status code is not 101, the connection will not be
   established and WebSocket frames will not be sent.

Do we really mean the following?

   If the |Sec-WebSocket-Accept|
   value does not match the expected value, or if the header is missing,
   or if the HTTP status code is not 101, the browser MUST NOT
   establish the connection and MUST NOT send WebSocket frames.

Section 1.4 uses the term "man-in-the-middle proxies". The term "man in
the middle" might lead people to think of man-in-the-middle attacks as
in RFC 4949 (BTW, an informational reference to RFC 4949 would be good
in Section 2.1). I suggest "middlebox proxies" or "intermediate proxies"
or some more neutral term.

In Section 1.5, I suggest...

OLD:
   It is expected
   that metadata would be layered on top of WebSocket by the application
   layer, in the same way that metadata is layered on top of TCP by the
   application layer (HTTP).

NEW:
   It is expected
   that metadata would be layered on top of WebSocket by the application
   layer, in the same way that metadata is layered on top of TCP by the
   application layer (e.g., HTTP).

This paragraph is hard to read:

   Conceptually, WebSocket is really just a layer on top of TCP that
   adds a Web "origin"-based security model for browsers; adds an
   addressing and protocol naming mechanism to support multiple services
   on one port and multiple host names on one IP address; layers a
   framing mechanism on top of TCP to get back to the IP packet
   mechanism that TCP is built on, but without length limits; and
   includes an additional closing handshake in-band that is designed to
   work in the presence of proxies and other intermediaries.  Other than
   that, it adds nothing.  Basically it is intended to be as close to
   just exposing raw TCP to script as possible given the constraints of
   the Web. It's also designed in such a way that its servers can share
   a port with HTTP servers, by having its handshake be a valid HTTP
   Upgrade request mechanism also.

I suggest breaking it up into bullet points:

   Conceptually, WebSocket is really just a layer on top of TCP that
   does the following:

   * adds a Web "origin"-based security model for browsers

   * adds an addressing and protocol naming mechanism to support
   multiple services on one port and multiple host names on one IP
   address;

   * layers a framing mechanism on top of TCP to get back to the IP
   packet mechanism that TCP is built on, but without length limits

   * includes an additional closing handshake in-band that is designed
   to work in the presence of proxies and other intermediaries

   Other than that, WebSocket adds nothing.  Basically it is intended
   to be as close to just exposing raw TCP to script as possible given
   the constraints of the Web. It's also designed in such a way that
   its servers can share a port with HTTP servers, by having its
   handshake be a valid HTTP Upgrade request mechanism also.

Section 1.7 says:

   By default the WebSocket protocol uses port 80 for regular WebSocket
   connections and port 443 for WebSocket connections tunneled over TLS
   [RFC2818].

I know this has been discussed on the list, but how can an entity
discover if WebSocket is offered on ports other than 80/443? Would the
web server use a redirect to do that? Could it define SRV records?

Section 1.9 says:

   These subprotocol names should be registered as per Section 11.10.
   To avoid potential collisions, it is recommended to use names that
   contain the domain name of the subprotocol's originator.

Following the trail, we find this in Section 11.10:

   Subprotocol Identifier
      The identifier of the subprotocol, as will be used in the Sec-
      WebSocket-Protocol header registered in Section 11.9 of this
      specification.  The value must conform to the requirements given
      in Paragraph 10 of Paragraph 4 of Section 5.1 of this
      specification, namely the value must be a token as defined by RFC
      2616 [RFC2616].

In RFC 2616 we find:

       token          = 1*<any CHAR except CTLs or separators>

And in RFC 5234 we find:

         CHAR           =  %x01-7F
                                ; any 7-bit US-ASCII character,
                                ;  excluding NUL

So a Subprotocol Identifier is limited to 7-bit ASCII. Given that the
domain name of the subprotocol's originator might be an IDNA, how will
the originator be able to include their domain name in the identifier?
This needs to be specified.

More soon.

Peter

-- 
Peter Saint-Andre
https://stpeter.im/

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 00:53:02 +0200

2011/6/15 Peter Saint-Andre <[email-masked]>:
> application protocols such as IRC and XMPP.

Right, there is other protocols than HTTP (except for web developers) :)

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 01:03:01 +0200

2011/6/15 Peter Saint-Andre <[email-masked]>:
> discover if WebSocket is offered on ports other than 80/443?

I don't understand the question. The WebSocket URI is provided by the
webserver (most probably) and it can contain a port or not. If it does
not contain a port then default port should be used (80/443 depending
on URI schema). Do I miss something?

> Would the

I wrote a draft for including SRV records in WebSocket:

  http://tools.ietf.org/html/draft-ibc-websocket-dns-srv-02

...but got not too much interest, nothing in fact (I assume that since
HTTP just uses DNS A records, no more DNS stuff exists).

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: Peter Saint-Andre <[email-masked]>
Date: Wed, 15 Jun 2011 17:08:54 -0600

> on URI schema). Do I miss something?

Not if you wrote that SRV spec!

I want to point a client to the WebSocket service at example.com. I
can't assume that it's served on port 80 or port 443. How does my client
figure out which port to use?

Peter

-- 
Peter Saint-Andre
https://stpeter.im/

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 01:16:07 +0200

> figure out which port to use?

You have not enough data. A WebSocket service is not just identified
by a host and optional port, it also requires an URI schema (ws for
plain TCP or wss for TLS over TCP). So you need a WebSocket URI (like
"ws://1.2.3.4[:999]).

In your example above, if you want to point a client to the WebSocket
service at example.com, how do you know wheter to use TLS or not? you
need to know the URI schema for that.

Of course, in the case of using SRV records things change a bit (since
the server IP and port) must be determined by performing SRV
procedures and more than one valid destinations can be retrieved in
the DNS response.

PS: If I want to point a http client to the HTTP service at
example.com, how does my client figure out which port to use? Same
response as abobe, I need the URI scheme (http or https).  ;)

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 12:31:00 +0200

> procedures and more than one valid destinations can be retrieved in

However there is a way, at least in SIP protocol, for the client to
discover which transport (UDP, TCP, TLS over TCP) to use when
contacting a server: using DNS NAPTR records (RFC 2915).

For example, a SIP client wants to contact the server with domain
oversip.net so it performs a NAPTR DNS query:

  $ host -t NAPTR oversip.net
  oversip.net has NAPTR record 10 50 "S" "SIP+D2U" "" _sip._udp.oversip.net.
  oversip.net has NAPTR record 40 50 "S" "SIP+D2S" "" _sip._sctp.oversip.net.
  oversip.net has NAPTR record 50 50 "S" "SIPS+D2S" "" _sips._sctp.oversip.net.
  oversip.net has NAPTR record 5 50 "S" "SIPS+D2T" "" _sips._tcp.oversip.net.
  oversip.net has NAPTR record 10 50 "S" "SIP+D2T" "" _sip._tcp.oversip.net.

If the SIP client just supports SIP over UDP, TCP and TLS, it would
just take DNS records with service "SIP+D2U", "SIP+D2T" and
"SIPS+D2T".
It would then choose the resource with best 'order' (in this case
"SIPS+D2T") and perform a DNS SRV query for  _sips._tcp.oversip.net,
retrieving various SRV records (each one with a domain for which DNS A
must be queried, and a port). Then the client should try the SRV
record with best priority (taking into account the 'weight' field if
more than one record with same 'priority') and connect via TCP to the
resulting IP and port.

I see that NAPTR records don't exist in XMPP, so given a domain how
does a client know wheter it must use TCP or TLS??

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: "Simon Pieters" <[email-masked]>
Date: Thu, 16 Jun 2011 13:15:37 +0200

> Why not? What is the nature of the restriction?

"Header names starting with Sec- are not allowed to be set to allow new  
headers to be minted that are guaranteed not to come from XMLHttpRequest."

http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#dom-xmlhttprequest-setrequestheader

>    establish the connection and MUST NOT send WebSocket frames.

All of section 1 is non-normative so shouldn't contain any requirements.

>    handshake be a valid HTTP Upgrade request mechanism also.

I'm not sure this text is accurate anymore now that we have extensions and  
whatnot.

> web server use a redirect to do that? Could it define SRV records?

I don't think there's any discoverability. You can't know that WebSocket  
is offered on ports 80/443 either. I think the Web page that opens a  
WebSocket is supposed to know which port to use. (The WebSocket API  
doesn't allow redirects.)

-- 
Simon Pieters
Opera Software

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 13:18:38 +0200

2011/6/16 Simon Pieters <[email-masked]>:
> I don't think there's any discoverability. You can't know that WebSocket is
> offered on ports 80/443 either. I think the Web page that opens a WebSocket
> is supposed to know which port to use. (The WebSocket API doesn't allow
> redirects.)

Hummm, please, is it not clear that the WebSocket URI schema must be
provided in order to know which transport to use (TLS or TCP) and the
port to connect (80/443 depending the schema, in case no port is
explicitely given in the URI) ??

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: Iñaki Baz Castillo <[email-masked]>
Date: Thu, 16 Jun 2011 14:06:33 +0200

> All of section 1 is non-normative so shouldn't contain any requirements.

The question is: should such text be non-normative? WebSocket uses two
protocols:
1) HTTP for the handshake.
2) WebSocket "pure" protocol (masking, framing, WS messages, and so).

If this specification creates an extension for HTTP (as it does, point
1) it MUST specify certain HTTP response codes for certains
situations.

-- 
Iñaki Baz Castillo
<[email-masked]>

---

From: Greg Wilkins <[email-masked]>
Date: Mon, 20 Jun 2011 16:57:14 +1000

>   server for updates while sending upstream notifications as distinct

I don't think the usage of "abuse" can be justified.   There is
nothing abusive about long polling and it is entirely legal HTTP.
Besides that is too much of a subjective reason.

How about:

  Historically, creating Web applications that need bidirectional
  communication between a client and a server (e.g., instant messaging
  and gaming applications), has required the use of HTTP to poll or long
  poll the server for updates.  Such usage of HTTP is less efficient
and responsive
  that what is possible with a TCP/IP connection.

regards

---

From: Peter Saint-Andre <[email-masked]>
Date: Mon, 20 Jun 2011 21:43:16 -0600

>   that what is possible with a TCP/IP connection.

Sure. I tried to leave as much of the current text alone in my suggestion.

Peter

-- 
Peter Saint-Andre
https://stpeter.im/