@fedify/vocab-runtime 2.2.0 → 2.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/deno.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fedify/vocab-runtime",
3
- "version": "2.2.0",
3
+ "version": "2.2.1",
4
4
  "license": "MIT",
5
5
  "exports": {
6
6
  ".": "./src/mod.ts",
package/dist/mod.cjs CHANGED
@@ -4383,7 +4383,7 @@ const preloadedContexts = {
4383
4383
  //#endregion
4384
4384
  //#region deno.json
4385
4385
  var name = "@fedify/vocab-runtime";
4386
- var version = "2.2.0";
4386
+ var version = "2.2.1";
4387
4387
  //#endregion
4388
4388
  //#region src/link.ts
4389
4389
  const parametersNeedLowerCase = ["rel", "type"];
@@ -4650,8 +4650,13 @@ async function validatePublicUrl(url) {
4650
4650
  const parsed = new URL(url);
4651
4651
  if (parsed.protocol !== "http:" && parsed.protocol !== "https:") throw new UrlError(`Unsupported protocol: ${parsed.protocol}`);
4652
4652
  let hostname = parsed.hostname;
4653
- if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.substring(1, hostname.length - 2);
4653
+ if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.slice(1, -1);
4654
4654
  if (hostname === "localhost") throw new UrlError("Localhost is not allowed");
4655
+ const hostnameFamily = (0, node_net.isIP)(hostname);
4656
+ if (hostnameFamily !== 0) {
4657
+ validatePublicIpAddress(hostname, hostnameFamily);
4658
+ return;
4659
+ }
4655
4660
  if ("Deno" in globalThis && !(0, node_net.isIP)(hostname)) {
4656
4661
  if ((await Deno.permissions.query({ name: "net" })).state !== "granted") return;
4657
4662
  }
@@ -4665,7 +4670,11 @@ async function validatePublicUrl(url) {
4665
4670
  } catch {
4666
4671
  addresses = [];
4667
4672
  }
4668
- for (const { address, family } of addresses) if (family === 4 && !isValidPublicIPv4Address(address) || family === 6 && !isValidPublicIPv6Address(address) || family < 4 || family === 5 || family > 6) throw new UrlError(`Invalid or private address: ${address}`);
4673
+ for (const { address, family } of addresses) validatePublicIpAddress(address, family);
4674
+ }
4675
+ function validatePublicIpAddress(address, family) {
4676
+ if (family === 4 && isValidPublicIPv4Address(address) || family === 6 && isValidPublicIPv6Address(address)) return;
4677
+ throw new UrlError(`Invalid or private address: ${address}`);
4669
4678
  }
4670
4679
  function isValidPublicIPv4Address(address) {
4671
4680
  const parts = address.split(".");
package/dist/mod.js CHANGED
@@ -4379,7 +4379,7 @@ const preloadedContexts = {
4379
4379
  //#endregion
4380
4380
  //#region deno.json
4381
4381
  var name = "@fedify/vocab-runtime";
4382
- var version = "2.2.0";
4382
+ var version = "2.2.1";
4383
4383
  //#endregion
4384
4384
  //#region src/link.ts
4385
4385
  const parametersNeedLowerCase = ["rel", "type"];
@@ -4646,8 +4646,13 @@ async function validatePublicUrl(url) {
4646
4646
  const parsed = new URL(url);
4647
4647
  if (parsed.protocol !== "http:" && parsed.protocol !== "https:") throw new UrlError(`Unsupported protocol: ${parsed.protocol}`);
4648
4648
  let hostname = parsed.hostname;
4649
- if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.substring(1, hostname.length - 2);
4649
+ if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.slice(1, -1);
4650
4650
  if (hostname === "localhost") throw new UrlError("Localhost is not allowed");
4651
+ const hostnameFamily = isIP(hostname);
4652
+ if (hostnameFamily !== 0) {
4653
+ validatePublicIpAddress(hostname, hostnameFamily);
4654
+ return;
4655
+ }
4651
4656
  if ("Deno" in globalThis && !isIP(hostname)) {
4652
4657
  if ((await Deno.permissions.query({ name: "net" })).state !== "granted") return;
4653
4658
  }
@@ -4661,7 +4666,11 @@ async function validatePublicUrl(url) {
4661
4666
  } catch {
4662
4667
  addresses = [];
4663
4668
  }
4664
- for (const { address, family } of addresses) if (family === 4 && !isValidPublicIPv4Address(address) || family === 6 && !isValidPublicIPv6Address(address) || family < 4 || family === 5 || family > 6) throw new UrlError(`Invalid or private address: ${address}`);
4669
+ for (const { address, family } of addresses) validatePublicIpAddress(address, family);
4670
+ }
4671
+ function validatePublicIpAddress(address, family) {
4672
+ if (family === 4 && isValidPublicIPv4Address(address) || family === 6 && isValidPublicIPv6Address(address)) return;
4673
+ throw new UrlError(`Invalid or private address: ${address}`);
4665
4674
  }
4666
4675
  function isValidPublicIPv4Address(address) {
4667
4676
  const parts = address.split(".");
@@ -1,5 +1,5 @@
1
1
  require("./chunk-Do9eywBl.cjs");
2
- require("./docloader-Cm8MkfmU.cjs");
2
+ require("./docloader-ptXlCCN2.cjs");
3
3
  require("./key-DTTIntwb.cjs");
4
4
  require("./multibase-F7LtMMsK.cjs");
5
5
  require("./langstr-CbAxaeEZ.cjs");
@@ -1,4 +1,4 @@
1
- import "./docloader-0xxbBwa9.mjs";
1
+ import "./docloader-BmzhZFCE.mjs";
2
2
  import "./key-BeTHFQJK.mjs";
3
3
  import "./multibase-BgU9XRf7.mjs";
4
4
  import "./langstr-Di5AvKpB.mjs";
@@ -1,6 +1,6 @@
1
- import { a as name, i as logRequest, n as createActivityPubRequest, o as version, t as FetchError } from "./request-peBUF_HC.mjs";
1
+ import { a as name, i as logRequest, n as createActivityPubRequest, o as version, t as FetchError } from "./request-DXYl4T3q.mjs";
2
2
  import { t as HttpHeaderLink } from "./link-NUUWCdnK.mjs";
3
- import { a as validatePublicUrl, t as UrlError } from "./url-BQ_kgmCk.mjs";
3
+ import { a as validatePublicUrl, t as UrlError } from "./url-BzGwIxB4.mjs";
4
4
  import { getLogger } from "@logtape/logtape";
5
5
  import { SpanKind, SpanStatusCode, trace } from "@opentelemetry/api";
6
6
  //#region src/contexts/activitystreams.json
@@ -1,7 +1,7 @@
1
1
  require("./chunk-Do9eywBl.cjs");
2
- const require_request = require("./request-DLk6MHw1.cjs");
2
+ const require_request = require("./request-CaVQlMm8.cjs");
3
3
  const require_link = require("./link-FguCydMA.cjs");
4
- const require_url = require("./url-pFuSds44.cjs");
4
+ const require_url = require("./url-Cj9-Ycue.cjs");
5
5
  let _logtape_logtape = require("@logtape/logtape");
6
6
  let _opentelemetry_api = require("@opentelemetry/api");
7
7
  //#region src/contexts/activitystreams.json
@@ -1,7 +1,7 @@
1
1
  const require_chunk = require("./chunk-Do9eywBl.cjs");
2
- const require_docloader = require("./docloader-Cm8MkfmU.cjs");
3
- const require_request = require("./request-DLk6MHw1.cjs");
4
- const require_url = require("./url-pFuSds44.cjs");
2
+ const require_docloader = require("./docloader-ptXlCCN2.cjs");
3
+ const require_request = require("./request-CaVQlMm8.cjs");
4
+ const require_url = require("./url-Cj9-Ycue.cjs");
5
5
  let node_assert = require("node:assert");
6
6
  let node_test = require("node:test");
7
7
  //#region ../../node_modules/.pnpm/glob-to-regexp@0.4.1/node_modules/glob-to-regexp/index.js
@@ -1,6 +1,6 @@
1
- import { n as preloadedContexts, t as getDocumentLoader } from "./docloader-0xxbBwa9.mjs";
2
- import { t as FetchError } from "./request-peBUF_HC.mjs";
3
- import { t as UrlError } from "./url-BQ_kgmCk.mjs";
1
+ import { n as preloadedContexts, t as getDocumentLoader } from "./docloader-BmzhZFCE.mjs";
2
+ import { t as FetchError } from "./request-DXYl4T3q.mjs";
3
+ import { t as UrlError } from "./url-BzGwIxB4.mjs";
4
4
  import { deepStrictEqual, ok, rejects } from "node:assert";
5
5
  import { test } from "node:test";
6
6
  //#region \0rolldown/runtime.js
@@ -3,7 +3,7 @@ let node_process = require("node:process");
3
3
  node_process = require_chunk.__toESM(node_process);
4
4
  //#region deno.json
5
5
  var name = "@fedify/vocab-runtime";
6
- var version = "2.2.0";
6
+ var version = "2.2.1";
7
7
  //#endregion
8
8
  //#region src/request.ts
9
9
  /**
@@ -1,7 +1,7 @@
1
1
  import process from "node:process";
2
2
  //#region deno.json
3
3
  var name = "@fedify/vocab-runtime";
4
- var version = "2.2.0";
4
+ var version = "2.2.1";
5
5
  //#endregion
6
6
  //#region src/request.ts
7
7
  /**
@@ -1,5 +1,5 @@
1
1
  const require_chunk = require("./chunk-Do9eywBl.cjs");
2
- const require_request = require("./request-DLk6MHw1.cjs");
2
+ const require_request = require("./request-CaVQlMm8.cjs");
3
3
  let node_assert = require("node:assert");
4
4
  let node_test = require("node:test");
5
5
  let node_process = require("node:process");
@@ -1,4 +1,4 @@
1
- import { o as version, r as getUserAgent } from "./request-peBUF_HC.mjs";
1
+ import { o as version, r as getUserAgent } from "./request-DXYl4T3q.mjs";
2
2
  import { deepStrictEqual } from "node:assert";
3
3
  import { test } from "node:test";
4
4
  import process from "node:process";
@@ -14,8 +14,13 @@ async function validatePublicUrl(url) {
14
14
  const parsed = new URL(url);
15
15
  if (parsed.protocol !== "http:" && parsed.protocol !== "https:") throw new UrlError(`Unsupported protocol: ${parsed.protocol}`);
16
16
  let hostname = parsed.hostname;
17
- if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.substring(1, hostname.length - 2);
17
+ if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.slice(1, -1);
18
18
  if (hostname === "localhost") throw new UrlError("Localhost is not allowed");
19
+ const hostnameFamily = isIP(hostname);
20
+ if (hostnameFamily !== 0) {
21
+ validatePublicIpAddress(hostname, hostnameFamily);
22
+ return;
23
+ }
19
24
  if ("Deno" in globalThis && !isIP(hostname)) {
20
25
  if ((await Deno.permissions.query({ name: "net" })).state !== "granted") return;
21
26
  }
@@ -29,7 +34,11 @@ async function validatePublicUrl(url) {
29
34
  } catch {
30
35
  addresses = [];
31
36
  }
32
- for (const { address, family } of addresses) if (family === 4 && !isValidPublicIPv4Address(address) || family === 6 && !isValidPublicIPv6Address(address) || family < 4 || family === 5 || family > 6) throw new UrlError(`Invalid or private address: ${address}`);
37
+ for (const { address, family } of addresses) validatePublicIpAddress(address, family);
38
+ }
39
+ function validatePublicIpAddress(address, family) {
40
+ if (family === 4 && isValidPublicIPv4Address(address) || family === 6 && isValidPublicIPv6Address(address)) return;
41
+ throw new UrlError(`Invalid or private address: ${address}`);
33
42
  }
34
43
  function isValidPublicIPv4Address(address) {
35
44
  const parts = address.split(".");
@@ -15,8 +15,13 @@ async function validatePublicUrl(url) {
15
15
  const parsed = new URL(url);
16
16
  if (parsed.protocol !== "http:" && parsed.protocol !== "https:") throw new UrlError(`Unsupported protocol: ${parsed.protocol}`);
17
17
  let hostname = parsed.hostname;
18
- if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.substring(1, hostname.length - 2);
18
+ if (hostname.startsWith("[") && hostname.endsWith("]")) hostname = hostname.slice(1, -1);
19
19
  if (hostname === "localhost") throw new UrlError("Localhost is not allowed");
20
+ const hostnameFamily = (0, node_net.isIP)(hostname);
21
+ if (hostnameFamily !== 0) {
22
+ validatePublicIpAddress(hostname, hostnameFamily);
23
+ return;
24
+ }
20
25
  if ("Deno" in globalThis && !(0, node_net.isIP)(hostname)) {
21
26
  if ((await Deno.permissions.query({ name: "net" })).state !== "granted") return;
22
27
  }
@@ -30,7 +35,11 @@ async function validatePublicUrl(url) {
30
35
  } catch {
31
36
  addresses = [];
32
37
  }
33
- for (const { address, family } of addresses) if (family === 4 && !isValidPublicIPv4Address(address) || family === 6 && !isValidPublicIPv6Address(address) || family < 4 || family === 5 || family > 6) throw new UrlError(`Invalid or private address: ${address}`);
38
+ for (const { address, family } of addresses) validatePublicIpAddress(address, family);
39
+ }
40
+ function validatePublicIpAddress(address, family) {
41
+ if (family === 4 && isValidPublicIPv4Address(address) || family === 6 && isValidPublicIPv6Address(address)) return;
42
+ throw new UrlError(`Invalid or private address: ${address}`);
34
43
  }
35
44
  function isValidPublicIPv4Address(address) {
36
45
  const parts = address.split(".");
@@ -1,5 +1,5 @@
1
1
  require("./chunk-Do9eywBl.cjs");
2
- const require_url = require("./url-pFuSds44.cjs");
2
+ const require_url = require("./url-Cj9-Ycue.cjs");
3
3
  let node_assert = require("node:assert");
4
4
  let node_test = require("node:test");
5
5
  //#region src/url.test.ts
@@ -9,6 +9,8 @@ let node_test = require("node:test");
9
9
  await (0, node_assert.rejects)(() => require_url.validatePublicUrl("https://localhost"), require_url.UrlError);
10
10
  await (0, node_assert.rejects)(() => require_url.validatePublicUrl("https://127.0.0.1"), require_url.UrlError);
11
11
  await (0, node_assert.rejects)(() => require_url.validatePublicUrl("https://[::1]"), require_url.UrlError);
12
+ await (0, node_assert.rejects)(() => require_url.validatePublicUrl("http://[::ffff:7f00:1]/"), require_url.UrlError);
13
+ await require_url.validatePublicUrl("https://[2001:db8::1]");
12
14
  });
13
15
  (0, node_test.test)("isValidPublicIPv4Address()", () => {
14
16
  (0, node_assert.ok)(require_url.isValidPublicIPv4Address("8.8.8.8"));
@@ -25,6 +27,7 @@ let node_test = require("node:test");
25
27
  (0, node_assert.ok)(!require_url.isValidPublicIPv6Address("fe80::1"));
26
28
  (0, node_assert.ok)(!require_url.isValidPublicIPv6Address("ff00::1"));
27
29
  (0, node_assert.ok)(!require_url.isValidPublicIPv6Address("::"));
30
+ (0, node_assert.ok)(!require_url.isValidPublicIPv6Address("::ffff:7f00:1"));
28
31
  });
29
32
  (0, node_test.test)("expandIPv6Address()", () => {
30
33
  (0, node_assert.deepStrictEqual)(require_url.expandIPv6Address("::"), "0000:0000:0000:0000:0000:0000:0000:0000");
@@ -1,4 +1,4 @@
1
- import { a as validatePublicUrl, i as isValidPublicIPv6Address, n as expandIPv6Address, r as isValidPublicIPv4Address, t as UrlError } from "./url-BQ_kgmCk.mjs";
1
+ import { a as validatePublicUrl, i as isValidPublicIPv6Address, n as expandIPv6Address, r as isValidPublicIPv4Address, t as UrlError } from "./url-BzGwIxB4.mjs";
2
2
  import { deepStrictEqual, ok, rejects } from "node:assert";
3
3
  import { test } from "node:test";
4
4
  //#region src/url.test.ts
@@ -8,6 +8,8 @@ test("validatePublicUrl()", async () => {
8
8
  await rejects(() => validatePublicUrl("https://localhost"), UrlError);
9
9
  await rejects(() => validatePublicUrl("https://127.0.0.1"), UrlError);
10
10
  await rejects(() => validatePublicUrl("https://[::1]"), UrlError);
11
+ await rejects(() => validatePublicUrl("http://[::ffff:7f00:1]/"), UrlError);
12
+ await validatePublicUrl("https://[2001:db8::1]");
11
13
  });
12
14
  test("isValidPublicIPv4Address()", () => {
13
15
  ok(isValidPublicIPv4Address("8.8.8.8"));
@@ -24,6 +26,7 @@ test("isValidPublicIPv6Address()", () => {
24
26
  ok(!isValidPublicIPv6Address("fe80::1"));
25
27
  ok(!isValidPublicIPv6Address("ff00::1"));
26
28
  ok(!isValidPublicIPv6Address("::"));
29
+ ok(!isValidPublicIPv6Address("::ffff:7f00:1"));
27
30
  });
28
31
  test("expandIPv6Address()", () => {
29
32
  deepStrictEqual(expandIPv6Address("::"), "0000:0000:0000:0000:0000:0000:0000:0000");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fedify/vocab-runtime",
3
- "version": "2.2.0",
3
+ "version": "2.2.1",
4
4
  "homepage": "https://fedify.dev/",
5
5
  "repository": {
6
6
  "type": "git",
package/src/url.test.ts CHANGED
@@ -19,6 +19,11 @@ test("validatePublicUrl()", async () => {
19
19
  await rejects(() => validatePublicUrl("https://localhost"), UrlError);
20
20
  await rejects(() => validatePublicUrl("https://127.0.0.1"), UrlError);
21
21
  await rejects(() => validatePublicUrl("https://[::1]"), UrlError);
22
+ await rejects(
23
+ () => validatePublicUrl("http://[::ffff:7f00:1]/"),
24
+ UrlError,
25
+ );
26
+ await validatePublicUrl("https://[2001:db8::1]");
22
27
  });
23
28
 
24
29
  test("isValidPublicIPv4Address()", () => {
@@ -37,6 +42,7 @@ test("isValidPublicIPv6Address()", () => {
37
42
  ok(!isValidPublicIPv6Address("fe80::1")); // link-local
38
43
  ok(!isValidPublicIPv6Address("ff00::1")); // multicast
39
44
  ok(!isValidPublicIPv6Address("::")); // unspecified
45
+ ok(!isValidPublicIPv6Address("::ffff:7f00:1")); // IPv4-mapped
40
46
  });
41
47
 
42
48
  test("expandIPv6Address()", () => {
package/src/url.ts CHANGED
@@ -19,11 +19,16 @@ export async function validatePublicUrl(url: string): Promise<void> {
19
19
  }
20
20
  let hostname = parsed.hostname;
21
21
  if (hostname.startsWith("[") && hostname.endsWith("]")) {
22
- hostname = hostname.substring(1, hostname.length - 2);
22
+ hostname = hostname.slice(1, -1);
23
23
  }
24
24
  if (hostname === "localhost") {
25
25
  throw new UrlError("Localhost is not allowed");
26
26
  }
27
+ const hostnameFamily = isIP(hostname);
28
+ if (hostnameFamily !== 0) {
29
+ validatePublicIpAddress(hostname, hostnameFamily);
30
+ return;
31
+ }
27
32
  if ("Deno" in globalThis && !isIP(hostname)) {
28
33
  // If the `net` permission is not granted, we can't resolve the hostname.
29
34
  // However, we can safely assume that it cannot gain access to private
@@ -50,14 +55,18 @@ export async function validatePublicUrl(url: string): Promise<void> {
50
55
  addresses = [];
51
56
  }
52
57
  for (const { address, family } of addresses) {
53
- if (
54
- family === 4 && !isValidPublicIPv4Address(address) ||
55
- family === 6 && !isValidPublicIPv6Address(address) ||
56
- family < 4 || family === 5 || family > 6
57
- ) {
58
- throw new UrlError(`Invalid or private address: ${address}`);
59
- }
58
+ validatePublicIpAddress(address, family);
59
+ }
60
+ }
61
+
62
+ function validatePublicIpAddress(address: string, family: number): void {
63
+ if (
64
+ family === 4 && isValidPublicIPv4Address(address) ||
65
+ family === 6 && isValidPublicIPv6Address(address)
66
+ ) {
67
+ return;
60
68
  }
69
+ throw new UrlError(`Invalid or private address: ${address}`);
61
70
  }
62
71
 
63
72
  export function isValidPublicIPv4Address(address: string): boolean {