From 53f8d96a1faf3b0f97e793b2e4ea86c64c12cbfa Mon Sep 17 00:00:00 2001 From: Oron Sharabi Date: Mon, 29 Jun 2020 17:39:17 +0300 Subject: fix(std/http): Support ipv6 parsing (#5263) --- std/http/server.ts | 31 +++++++++++++++++++++++++++++-- std/http/server_test.ts | 49 ++++++++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 77 insertions(+), 3 deletions(-) (limited to 'std/http') diff --git a/std/http/server.ts b/std/http/server.ts index effa7b4b9..82e5f8169 100644 --- a/std/http/server.ts +++ b/std/http/server.ts @@ -237,6 +237,34 @@ export class Server implements AsyncIterable { /** Options for creating an HTTP server. */ export type HTTPOptions = Omit; +/** + * Parse addr from string + * + * const addr = "::1:8000"; + * parseAddrFromString(addr); + * + * @param addr Address string + */ +export function _parseAddrFromStr(addr: string): HTTPOptions { + let url: URL; + try { + url = new URL(`http://${addr}`); + } catch { + throw new TypeError("Invalid address."); + } + if ( + url.username || + url.password || + url.pathname != "/" || + url.search || + url.hash + ) { + throw new TypeError("Invalid address."); + } + + return { hostname: url.hostname, port: Number(url.port) }; +} + /** * Create a HTTP server * @@ -249,8 +277,7 @@ export type HTTPOptions = Omit; */ export function serve(addr: string | HTTPOptions): Server { if (typeof addr === "string") { - const [hostname, port] = addr.split(":"); - addr = { hostname, port: Number(port) }; + addr = _parseAddrFromStr(addr); } const listener = Deno.listen(addr); diff --git a/std/http/server_test.ts b/std/http/server_test.ts index 340d9fa73..5a4a48932 100644 --- a/std/http/server_test.ts +++ b/std/http/server_test.ts @@ -13,7 +13,14 @@ import { assertStringContains, assertThrowsAsync, } from "../testing/asserts.ts"; -import { Response, ServerRequest, Server, serve, serveTLS } from "./server.ts"; +import { + Response, + ServerRequest, + Server, + serve, + serveTLS, + _parseAddrFromStr, +} from "./server.ts"; import { BufReader, BufWriter } from "../io/bufio.ts"; import { delay } from "../async/delay.ts"; import { encode, decode } from "../encoding/utf8.ts"; @@ -612,3 +619,43 @@ Deno.test({ } }, }); + +Deno.test({ + name: "server.serve() should be able to parse IPV4 address", + fn: (): void => { + const server = serve("127.0.0.1:8124"); + const expected = { + hostname: "127.0.0.1", + port: 8124, + transport: "tcp", + }; + assertEquals(expected, server.listener.addr); + server.close(); + }, +}); + +Deno.test({ + name: "server.parseAddrFromStr() should be able to parse IPV6 address", + fn: (): void => { + const addr = _parseAddrFromStr("[::1]:8124"); + const expected = { + hostname: "[::1]", + port: 8124, + }; + assertEquals(expected, addr); + }, +}); + +Deno.test({ + name: "server.serve() should be able to parse IPV6 address", + fn: (): void => { + const server = serve("[::1]:8124"); + const expected = { + hostname: "::1", + port: 8124, + transport: "tcp", + }; + assertEquals(expected, server.listener.addr); + server.close(); + }, +}); -- cgit v1.2.3