garycourt/uri-js

Support ws and wss protocols

Closed this issue · 4 comments

I am not an expert on these protocols, but I believe that the websocket protocol's URIs are basically the same as HTTP URIs but with the protocol switched. (see "Encoding considerations" here: https://tools.ietf.org/id/draft-ietf-hybi-thewebsocketprotocol-17.html)

However, it seems like uri-js doesn't speak ws right now and urlencodes the hostname, which I think is wrong. I haven't fully comprehended RFC3987 yet, but I don't think you're
supposed to URLencode hostnames?

> URI.serialize({scheme: "http", host: "www.中华人民.com", path: "cats[]"})
'http://www.xn--fiq4m90jru6a.com/cats%5B%5D'
> URI.serialize({scheme: "ws", host: "www.中华人民.com", path: "cats[]"})
'ws://www.%E4%B8%AD%E5%8D%8E%E4%BA%BA%E6%B0%91.com/cats%5B%5D'

A workaround is to override the scheme in the options parameter:

> URI.serialize({scheme: "ws", host: "www.中华人民.com", path: "cats[]"}, {scheme: "http"})
'ws://www.xn--fiq4m90jru6a.com/cats%5B%5D'

It would be nice to have this library support it properly. It ought to be easy, if I understand things right, to just reuse the HTTP definition.

Have you tried setting domainHost: true in the options parameter?

Hrm, no, I haven't. Looking at https://github.com/garycourt/uri-js/blob/master/src/schemes/http.ts#L6, it seems to be a more direct way of accomplishing what {scheme: "http"} does, without any other baggage.

Considering that you don't need to set that to get the same behavior for HTTP, would you still consider this a workaround?

Yes. In essence, the URI spec does not assume that the host field contains a domain. And thus, will encode the value like any other component. In HTTP, the host most definitely can be a domain, and the library treats the HTTP scheme as such.

I'll leave this job open as implementing the ws/wss scheme is a legitimate feature. But for what you are trying to accomplish, the above solution should work.

Closing this job since, as of uri-js@4.4.0, official support for the ws/wss schemes have been implemented.