Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[http] request does not accept host encapsulated within square brackets #39738

Closed
trivikr opened this issue Aug 11, 2021 · 3 comments
Closed
Labels
http Issues or PRs related to the http subsystem.

Comments

@trivikr
Copy link
Member

trivikr commented Aug 11, 2021

Version

v14.17.5

Platform

Darwin <REDACTED> 20.5.0 Darwin Kernel Version 20.5.0: Sat May  8 05:10:33 PDT 2021; root:xnu-7195.121.3~9/RELEASE_X86_64 x86_64

Subsystem

http

What steps will reproduce the bug?

Note: This bug should ideally be Node.js version and platform independent.

To reproduce, run the following code:

Code
// test-node-http-ipv6.mjs
import { request } from "http";
import { lookup } from "dns";
import { promisify } from "util";

const lookupPromise = promisify(lookup);

// Get IPv6 address of example.com
const { address } = await lookupPromise("example.com", 6);

// Create URL from IPv6 address using square brackets.
const { protocol, host, port } = new URL(`http://[${address}]:80`);

// Throws Error: getaddrinfo ENOTFOUND [::ffff:5db8:d822]
// when host from IPv6 address is passed to request.
request({ protocol, host, port }).end();

// Does not throw error when square brackets are removed from host.
request({ protocol, host: host.replace(/^\[(.+)\]$/, "$1"), port }).end();
Output
events.js:377
      throw er; // Unhandled 'error' event
      ^

Error: getaddrinfo ENOTFOUND [::ffff:5db8:d822]
    at GetAddrInfoReqWrap.onlookup [as oncomplete] (dns.js:69:26)
Emitted 'error' event on ClientRequest instance at:
    at Socket.socketErrorListener (_http_client.js:475:9)
    at Socket.emit (events.js:400:28)
    at emitErrorNT (internal/streams/destroy.js:106:8)
    at emitErrorCloseNT (internal/streams/destroy.js:74:3)
    at processTicksAndRejections (internal/process/task_queues.js:82:21) {
  errno: -3008,
  code: 'ENOTFOUND',
  syscall: 'getaddrinfo',
  hostname: '[::ffff:5db8:d822]'
}

How often does it reproduce? Is there a required condition?

Always

What is the expected behavior?

The http.request should accept host encapsulated within square brackets.

What do you see instead?

The http.request internally calls getaddrinfo for host with square brackets, and gets ENOTFOUND error in return.

Additional information

This issue was noticed while testing IPv6 endpoints in AWS SDK for JavaScript in aws/aws-sdk-js-v3#2660

@trivikr trivikr changed the title http.request does not accept host encapsulated within square brackets [http] request does not accept host encapsulated within square brackets Aug 11, 2021
@trivikr trivikr added the http Issues or PRs related to the http subsystem. label Aug 11, 2021
@trivikr
Copy link
Member Author

trivikr commented Aug 11, 2021

From RFC 3986 section 3.2.2

The host subcomponent of authority is identified by an IP literal encapsulated within square brackets, an IPv4 address in dotted-decimal form, or a registered name.

The square bracket characters ([ and ]) are not part of IPv6 address specification outlined in RFC 4291 though.

trivikr added a commit to trivikr/aws-sdk-js-v3 that referenced this issue Aug 11, 2021
@lpinca
Copy link
Member

lpinca commented Aug 12, 2021

I don't think this is a bug. This is one of the reasons why urlToHttpOptions() exists.

@trivikr
Copy link
Member Author

trivikr commented Aug 12, 2021

I don't think this is a bug. This is one of the reasons why urlToHttpOptions() exists.

Verified that this issue was discussed in the past in #34349, and was resolved by exposing urlToHttpOptions utility in v15.7.0 in PR #35960

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
http Issues or PRs related to the http subsystem.
Projects
None yet
Development

No branches or pull requests

2 participants