Skip to content

Commit 0d8b53a

Browse files
committed
url: fix url spec compliance issues
1 parent bed28f2 commit 0d8b53a

File tree

4 files changed

+20
-3
lines changed

4 files changed

+20
-3
lines changed

lib/internal/url.js

+8-1
Original file line numberDiff line numberDiff line change
@@ -153,6 +153,7 @@ class URLContext {
153153
hash = '';
154154
hasHost = false;
155155
hasOpaquePath = false;
156+
hasHash = false;
156157
}
157158

158159
function isURLSearchParams(self) {
@@ -628,7 +629,7 @@ class URL {
628629

629630
#onParseComplete = (href, origin, protocol, host, hostname, pathname,
630631
search, username, password, port, hash, hasHost,
631-
hasOpaquePath) => {
632+
hasOpaquePath, hasHash) => {
632633
const ctx = this[context];
633634
ctx.href = href;
634635
ctx.origin = origin;
@@ -644,6 +645,7 @@ class URL {
644645
// TODO(@anonrig): Remove hasHost and hasOpaquePath when kFormat is removed.
645646
ctx.hasHost = hasHost;
646647
ctx.hasOpaquePath = hasOpaquePath;
648+
ctx.hasHash = hasHash;
647649
if (!this[searchParams]) { // Invoked from URL constructor
648650
this[searchParams] = new URLSearchParams();
649651
this[searchParams][context] = this;
@@ -864,6 +866,11 @@ function update(url, params) {
864866
ctx.search = '?' + serializedParams;
865867
} else {
866868
ctx.search = '';
869+
870+
// Potentially strip trailing spaces from an opaque path
871+
if (ctx.hasOpaquePath && !ctx.hasHash) {
872+
ctx.pathname = ctx.pathname.trimEnd();
873+
}
867874
}
868875
ctx.href = constructHref(ctx);
869876
}

src/node_url.cc

+3
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@ void SetArgs(Environment* env, Local<Value> argv[12], const ada::result& url) {
6262
argv[10] = Utf8String(isolate, url->get_hash());
6363
argv[11] = Boolean::New(isolate, url->host.has_value());
6464
argv[12] = Boolean::New(isolate, url->has_opaque_path);
65+
argv[13] = Boolean::New(isolate, url->fragment.has_value());
6566
}
6667

6768
void Parse(const FunctionCallbackInfo<Value>& args) {
@@ -109,6 +110,7 @@ void Parse(const FunctionCallbackInfo<Value>& args) {
109110
undef,
110111
undef,
111112
undef,
113+
undef,
112114
};
113115
SetArgs(env, argv, out);
114116
USE(success_callback_->Call(
@@ -260,6 +262,7 @@ void UpdateUrl(const FunctionCallbackInfo<Value>& args) {
260262
undef,
261263
undef,
262264
undef,
265+
undef,
263266
};
264267
SetArgs(env, argv, out);
265268
USE(success_callback_->Call(

test/parallel/test-whatwg-url-custom-inspect.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,8 @@ assert.strictEqual(
5858
port: '8080',
5959
hash: '#hash',
6060
hasHost: true,
61-
hasOpaquePath: false
61+
hasOpaquePath: false,
62+
hasHash: true
6263
}
6364
}`);
6465

test/wpt/status/url.json

+7-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,13 @@
77
"skip": "TODO: port from .window.js"
88
},
99
"historical.any.js": {
10-
"requires": ["small-icu"]
10+
"requires": ["small-icu"],
11+
"fail": {
12+
"expected": [
13+
"URL: no structured serialize/deserialize support",
14+
"URLSearchParams: no structured serialize/deserialize support"
15+
]
16+
}
1117
},
1218
"urlencoded-parser.any.js": {
1319
"requires": ["small-icu"]

0 commit comments

Comments
 (0)