@arcblock/did-connect-service 4.0.4 → 4.0.6

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.
Files changed (190) hide show
  1. package/assets/fonts/noto-sans-sc-regular.otf +0 -0
  2. package/dist/embedded.d.ts +32 -0
  3. package/dist/embedded.d.ts.map +1 -1
  4. package/dist/embedded.js +3 -0
  5. package/dist/embedded.js.map +1 -1
  6. package/dist/handlers/auth-handler.d.ts +5 -0
  7. package/dist/handlers/auth-handler.d.ts.map +1 -1
  8. package/dist/handlers/auth-handler.js +33 -0
  9. package/dist/handlers/auth-handler.js.map +1 -1
  10. package/dist/handlers/branding-handler.d.ts +17 -0
  11. package/dist/handlers/branding-handler.d.ts.map +1 -1
  12. package/dist/handlers/branding-handler.js +107 -5
  13. package/dist/handlers/branding-handler.js.map +1 -1
  14. package/dist/identity/csrf.d.ts +17 -0
  15. package/dist/identity/csrf.d.ts.map +1 -0
  16. package/dist/identity/csrf.js +56 -0
  17. package/dist/identity/csrf.js.map +1 -0
  18. package/dist/og/emoji.d.ts +12 -0
  19. package/dist/og/emoji.d.ts.map +1 -0
  20. package/dist/og/emoji.js +71 -0
  21. package/dist/og/emoji.js.map +1 -0
  22. package/dist/og/generator.d.ts +3 -0
  23. package/dist/og/generator.d.ts.map +1 -0
  24. package/dist/og/generator.js +338 -0
  25. package/dist/og/generator.js.map +1 -0
  26. package/dist/og/index.d.ts +6 -0
  27. package/dist/og/index.d.ts.map +1 -0
  28. package/dist/og/index.js +4 -0
  29. package/dist/og/index.js.map +1 -0
  30. package/dist/og/passport-svg.d.ts +52 -0
  31. package/dist/og/passport-svg.d.ts.map +1 -0
  32. package/dist/og/passport-svg.js +157 -0
  33. package/dist/og/passport-svg.js.map +1 -0
  34. package/dist/og/ssrf-guard.d.ts +38 -0
  35. package/dist/og/ssrf-guard.d.ts.map +1 -0
  36. package/dist/og/ssrf-guard.js +188 -0
  37. package/dist/og/ssrf-guard.js.map +1 -0
  38. package/dist/og/templates.d.ts +26 -0
  39. package/dist/og/templates.d.ts.map +1 -0
  40. package/dist/og/templates.js +302 -0
  41. package/dist/og/templates.js.map +1 -0
  42. package/dist/og/types.d.ts +74 -0
  43. package/dist/og/types.d.ts.map +1 -0
  44. package/dist/og/types.js +14 -0
  45. package/dist/og/types.js.map +1 -0
  46. package/package.json +18 -4
  47. package/dist/access-key-handler.d.ts +0 -37
  48. package/dist/access-key-handler.d.ts.map +0 -1
  49. package/dist/access-key-handler.js +0 -316
  50. package/dist/access-key-handler.js.map +0 -1
  51. package/dist/access-key-util.d.ts +0 -19
  52. package/dist/access-key-util.d.ts.map +0 -1
  53. package/dist/access-key-util.js +0 -45
  54. package/dist/access-key-util.js.map +0 -1
  55. package/dist/access-policy.d.ts +0 -53
  56. package/dist/access-policy.d.ts.map +0 -1
  57. package/dist/access-policy.js +0 -153
  58. package/dist/access-policy.js.map +0 -1
  59. package/dist/auth-client.d.ts +0 -20
  60. package/dist/auth-client.d.ts.map +0 -1
  61. package/dist/auth-client.js +0 -42
  62. package/dist/auth-client.js.map +0 -1
  63. package/dist/auth-entrypoint.d.ts +0 -45
  64. package/dist/auth-entrypoint.d.ts.map +0 -1
  65. package/dist/auth-entrypoint.js +0 -31
  66. package/dist/auth-entrypoint.js.map +0 -1
  67. package/dist/auth-handler.d.ts +0 -136
  68. package/dist/auth-handler.d.ts.map +0 -1
  69. package/dist/auth-handler.js +0 -408
  70. package/dist/auth-handler.js.map +0 -1
  71. package/dist/auth-rpc-types.d.ts +0 -139
  72. package/dist/auth-rpc-types.d.ts.map +0 -1
  73. package/dist/auth-rpc-types.js +0 -11
  74. package/dist/auth-rpc-types.js.map +0 -1
  75. package/dist/auth-rpc.d.ts +0 -80
  76. package/dist/auth-rpc.d.ts.map +0 -1
  77. package/dist/auth-rpc.js +0 -257
  78. package/dist/auth-rpc.js.map +0 -1
  79. package/dist/auth-worker.d.ts +0 -42
  80. package/dist/auth-worker.d.ts.map +0 -1
  81. package/dist/auth-worker.js +0 -120
  82. package/dist/auth-worker.js.map +0 -1
  83. package/dist/blocklet-js-handler.d.ts +0 -22
  84. package/dist/blocklet-js-handler.d.ts.map +0 -1
  85. package/dist/blocklet-js-handler.js +0 -205
  86. package/dist/blocklet-js-handler.js.map +0 -1
  87. package/dist/branding-handler.d.ts +0 -42
  88. package/dist/branding-handler.d.ts.map +0 -1
  89. package/dist/branding-handler.js +0 -326
  90. package/dist/branding-handler.js.map +0 -1
  91. package/dist/d1-token-storage.d.ts +0 -31
  92. package/dist/d1-token-storage.d.ts.map +0 -1
  93. package/dist/d1-token-storage.js +0 -83
  94. package/dist/d1-token-storage.js.map +0 -1
  95. package/dist/did-connect-handler.d.ts +0 -57
  96. package/dist/did-connect-handler.d.ts.map +0 -1
  97. package/dist/did-connect-handler.js +0 -182
  98. package/dist/did-connect-handler.js.map +0 -1
  99. package/dist/did.d.ts +0 -14
  100. package/dist/did.d.ts.map +0 -1
  101. package/dist/did.js +0 -17
  102. package/dist/did.js.map +0 -1
  103. package/dist/email-login-handler.d.ts +0 -50
  104. package/dist/email-login-handler.d.ts.map +0 -1
  105. package/dist/email-login-handler.js +0 -238
  106. package/dist/email-login-handler.js.map +0 -1
  107. package/dist/federation-utils.d.ts +0 -23
  108. package/dist/federation-utils.d.ts.map +0 -1
  109. package/dist/federation-utils.js +0 -25
  110. package/dist/federation-utils.js.map +0 -1
  111. package/dist/handler.d.ts +0 -90
  112. package/dist/handler.d.ts.map +0 -1
  113. package/dist/handler.js +0 -591
  114. package/dist/handler.js.map +0 -1
  115. package/dist/identity/invitation-util.d.ts +0 -7
  116. package/dist/identity/invitation-util.d.ts.map +0 -1
  117. package/dist/identity/invitation-util.js +0 -66
  118. package/dist/identity/invitation-util.js.map +0 -1
  119. package/dist/instance-role.d.ts +0 -10
  120. package/dist/instance-role.d.ts.map +0 -1
  121. package/dist/instance-role.js +0 -20
  122. package/dist/instance-role.js.map +0 -1
  123. package/dist/jwt.d.ts +0 -7
  124. package/dist/jwt.d.ts.map +0 -1
  125. package/dist/jwt.js +0 -72
  126. package/dist/jwt.js.map +0 -1
  127. package/dist/login-entry.d.ts +0 -9
  128. package/dist/login-entry.d.ts.map +0 -1
  129. package/dist/login-entry.js +0 -9
  130. package/dist/login-entry.js.map +0 -1
  131. package/dist/membership-handler.d.ts +0 -27
  132. package/dist/membership-handler.d.ts.map +0 -1
  133. package/dist/membership-handler.js +0 -111
  134. package/dist/membership-handler.js.map +0 -1
  135. package/dist/oauth-callback-page.d.ts +0 -9
  136. package/dist/oauth-callback-page.d.ts.map +0 -1
  137. package/dist/oauth-callback-page.js +0 -31
  138. package/dist/oauth-callback-page.js.map +0 -1
  139. package/dist/oauth-handler.d.ts +0 -72
  140. package/dist/oauth-handler.d.ts.map +0 -1
  141. package/dist/oauth-handler.js +0 -423
  142. package/dist/oauth-handler.js.map +0 -1
  143. package/dist/page.d.ts +0 -33
  144. package/dist/page.d.ts.map +0 -1
  145. package/dist/page.js +0 -59
  146. package/dist/page.js.map +0 -1
  147. package/dist/pages/auth-script.d.ts +0 -18
  148. package/dist/pages/auth-script.d.ts.map +0 -1
  149. package/dist/pages/auth-script.js +0 -185
  150. package/dist/pages/auth-script.js.map +0 -1
  151. package/dist/pages/design-tokens.d.ts +0 -86
  152. package/dist/pages/design-tokens.d.ts.map +0 -1
  153. package/dist/pages/design-tokens.js +0 -159
  154. package/dist/pages/design-tokens.js.map +0 -1
  155. package/dist/pages/did-connect-script.d.ts +0 -16
  156. package/dist/pages/did-connect-script.d.ts.map +0 -1
  157. package/dist/pages/did-connect-script.js +0 -105
  158. package/dist/pages/did-connect-script.js.map +0 -1
  159. package/dist/pages/shared-styles.d.ts +0 -6
  160. package/dist/pages/shared-styles.d.ts.map +0 -1
  161. package/dist/pages/shared-styles.js +0 -109
  162. package/dist/pages/shared-styles.js.map +0 -1
  163. package/dist/rbac.d.ts +0 -19
  164. package/dist/rbac.d.ts.map +0 -1
  165. package/dist/rbac.js +0 -76
  166. package/dist/rbac.js.map +0 -1
  167. package/dist/session-context.d.ts +0 -35
  168. package/dist/session-context.d.ts.map +0 -1
  169. package/dist/session-context.js +0 -39
  170. package/dist/session-context.js.map +0 -1
  171. package/dist/store.d.ts +0 -222
  172. package/dist/store.d.ts.map +0 -1
  173. package/dist/store.js +0 -1366
  174. package/dist/store.js.map +0 -1
  175. package/dist/team-handler.d.ts +0 -90
  176. package/dist/team-handler.d.ts.map +0 -1
  177. package/dist/team-handler.js +0 -1225
  178. package/dist/team-handler.js.map +0 -1
  179. package/dist/ticket-handler.d.ts +0 -28
  180. package/dist/ticket-handler.d.ts.map +0 -1
  181. package/dist/ticket-handler.js +0 -74
  182. package/dist/ticket-handler.js.map +0 -1
  183. package/dist/wallet-identity.d.ts +0 -32
  184. package/dist/wallet-identity.d.ts.map +0 -1
  185. package/dist/wallet-identity.js +0 -43
  186. package/dist/wallet-identity.js.map +0 -1
  187. package/dist/webauthn.d.ts +0 -65
  188. package/dist/webauthn.d.ts.map +0 -1
  189. package/dist/webauthn.js +0 -112
  190. package/dist/webauthn.js.map +0 -1
@@ -0,0 +1,157 @@
1
+ import { Hasher } from "@ocap/mcrypto";
2
+ import { toHex } from "@ocap/util";
3
+ export const DEFAULT_COLORS = {
4
+ "did-space": { start: "#7D3AC5", end: "#9761D1" },
5
+ "app-space": { start: "#6CC68D", end: "#47B871" },
6
+ "app-purchase": { start: "#DE7021", end: "#E48D4E" },
7
+ "app-passport": { start: "#3882C7", end: "#7AB2F6" },
8
+ "app-kyc": { start: "#3882C7", end: "#7AB2F6" },
9
+ };
10
+ /**
11
+ * Convert RGB color to HSL color.
12
+ * @param rgbString - The RGB color value (e.g. "#FF0000").
13
+ * @returns A [h, s, l] tuple with values in [0, 1].
14
+ */
15
+ export function rgbToHsl(rgbString) {
16
+ const color = rgbString.replace("#", "");
17
+ const r = parseInt(color.slice(0, 2), 16) / 255;
18
+ const g = parseInt(color.slice(2, 4), 16) / 255;
19
+ const b = parseInt(color.slice(4, 6), 16) / 255;
20
+ const max = Math.max(r, g, b);
21
+ const min = Math.min(r, g, b);
22
+ let h = 0;
23
+ let s = 0;
24
+ const l = (max + min) / 2;
25
+ if (max === min) {
26
+ h = 0;
27
+ s = 0;
28
+ }
29
+ else {
30
+ const d = max - min;
31
+ s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
32
+ switch (max) {
33
+ case r:
34
+ h = (g - b) / d + (g < b ? 6 : 0);
35
+ break;
36
+ case g:
37
+ h = (b - r) / d + 2;
38
+ break;
39
+ case b:
40
+ h = (r - g) / d + 4;
41
+ break;
42
+ default:
43
+ break;
44
+ }
45
+ h /= 6;
46
+ }
47
+ return [h, s, l];
48
+ }
49
+ /**
50
+ * Convert HSL color value to an RGB hex string.
51
+ * @param h - Hue in [0, 1].
52
+ * @param s - Saturation in [0, 1].
53
+ * @param l - Lightness in [0, 1].
54
+ * @returns A hex color string like "#rrggbb".
55
+ */
56
+ export function hslToRgb(h, s, l) {
57
+ let r;
58
+ let g;
59
+ let b;
60
+ if (s === 0) {
61
+ r = l;
62
+ g = l;
63
+ b = l;
64
+ }
65
+ else {
66
+ const hue2rgb = (p, q, t2) => {
67
+ let t = t2;
68
+ if (t < 0)
69
+ t += 1;
70
+ if (t > 1)
71
+ t -= 1;
72
+ if (t < 1 / 6)
73
+ return p + (q - p) * 6 * t;
74
+ if (t < 1 / 2)
75
+ return q;
76
+ if (t < 2 / 3)
77
+ return p + (q - p) * (2 / 3 - t) * 6;
78
+ return p;
79
+ };
80
+ const q = l < 0.5 ? l * (1 + s) : l + s - l * s;
81
+ const p = 2 * l - q;
82
+ r = hue2rgb(p, q, h + 1 / 3);
83
+ g = hue2rgb(p, q, h);
84
+ b = hue2rgb(p, q, h - 1 / 3);
85
+ }
86
+ return `#${[Math.round(r * 255), Math.round(g * 255), Math.round(b * 255)]
87
+ .map((e) => e.toString(16).padStart(2, "0"))
88
+ .join("")}`;
89
+ }
90
+ /**
91
+ * Convert a single color to usable NFT gradient background colors.
92
+ * Clamps saturation to ≤0.7 and lightness to [0.3, 0.6].
93
+ * @param rgbString - The background color in RGB hex format.
94
+ * @returns An NFTColor with clamped start and end gradient colors.
95
+ */
96
+ export function getNftBGColor(rgbString) {
97
+ if (rgbString) {
98
+ const data = rgbToHsl(rgbString);
99
+ // Hue h can be arbitrary
100
+ // Saturation s should not exceed 0.7
101
+ // Lightness l should not exceed 0.6 and should be above 0.3
102
+ const h = data[0];
103
+ const s = data[1] > 0.7 ? 0.7 : data[1];
104
+ const l = data[2] > 0.6 ? 0.6 : data[2] < 0.3 ? 0.3 : data[2];
105
+ const newColor = hslToRgb(h, s, l);
106
+ const newRepeatColor = hslToRgb(h, s, l - 0.1);
107
+ return {
108
+ start: newRepeatColor,
109
+ end: newColor,
110
+ };
111
+ }
112
+ return DEFAULT_COLORS["app-passport"];
113
+ }
114
+ /**
115
+ * Derive a deterministic passport color hex string from a DID.
116
+ * @param did - The DID string.
117
+ * @returns A 7-character hex color string like "#rrggbb".
118
+ */
119
+ export function getPassportColorFromDid(did) {
120
+ return `#${toHex(Hasher.SHA3.hash224(did)).slice(-6)}`;
121
+ }
122
+ /**
123
+ * Get NFT background color derived from a DID.
124
+ * @param did - The DID string.
125
+ * @returns An NFTColor with start and end gradient colors.
126
+ */
127
+ export function getNftBGColorFromDid(did) {
128
+ return getNftBGColor(getPassportColorFromDid(did));
129
+ }
130
+ /**
131
+ * Get the passport gradient color for display.
132
+ * @param preferredColor - "default" | "auto" | a hex color string | undefined
133
+ * @param did - The DID string (used when preferredColor is "auto").
134
+ * @returns An NFTColor with start and end gradient colors.
135
+ */
136
+ export function getPassportColor(preferredColor, did) {
137
+ if (preferredColor === "default" || !preferredColor) {
138
+ return DEFAULT_COLORS["app-passport"];
139
+ }
140
+ if (preferredColor === "auto") {
141
+ return getNftBGColorFromDid(did);
142
+ }
143
+ return getNftBGColor(preferredColor);
144
+ }
145
+ /**
146
+ * Choose readable text color based on background luminance.
147
+ * @param background - A hex color string like "#rrggbb".
148
+ * @returns "#111" for light backgrounds, "#EEE" for dark backgrounds.
149
+ */
150
+ export function getTextColor(background) {
151
+ const r = parseInt(background.slice(1, 3), 16);
152
+ const g = parseInt(background.slice(3, 5), 16);
153
+ const b = parseInt(background.slice(5, 7), 16);
154
+ const luminance = (0.299 * r + 0.587 * g + 0.114 * b) / 255;
155
+ return luminance > 0.5 ? "#111" : "#EEE";
156
+ }
157
+ //# sourceMappingURL=passport-svg.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"passport-svg.js","sourceRoot":"","sources":["../../src/og/passport-svg.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,38 @@
1
+ /**
2
+ * SSRF guard for server-side image fetches.
3
+ *
4
+ * The OG generator fetches caller-supplied `cover`/`logo` URLs from a public
5
+ * endpoint. Without a guard, an attacker could probe internal HTTPS hosts
6
+ * (cloud metadata, private services). This module:
7
+ * - enforces https
8
+ * - rejects private / loopback / link-local / unique-local / metadata
9
+ * targets, checked against the resolved IPs (not just the hostname) so a
10
+ * public domain pointing at a private address is still blocked
11
+ * - exposes a streaming reader that hard-caps the byte count instead of
12
+ * trusting the (forgeable) Content-Length header
13
+ *
14
+ * Residual risk: a narrow DNS-rebinding window between the resolve check and
15
+ * the fetch. Mitigated in practice by the short-lived fetch and the literal-IP
16
+ * checks; full pinning would require a custom connect-time hook.
17
+ */
18
+ /** DNS resolver shape — overridable in tests to avoid real network lookups. */
19
+ export type LookupImpl = (host: string) => Promise<Array<{
20
+ address: string;
21
+ }>>;
22
+ export declare class SsrfBlockedError extends Error {
23
+ statusCode: number;
24
+ constructor(message: string);
25
+ }
26
+ /** True if an IPv4/IPv6 literal is private, loopback, link-local, etc. */
27
+ export declare function isPrivateAddress(ip: string): boolean;
28
+ /**
29
+ * Reject a URL that isn't safe to fetch server-side. Throws SsrfBlockedError
30
+ * (400) on https violation or a private/blocked resolved address.
31
+ */
32
+ export declare function assertFetchableUrl(rawUrl: string, lookupImpl?: LookupImpl): Promise<void>;
33
+ /**
34
+ * Read a fetch Response body into a Buffer, aborting once `maxBytes` is
35
+ * exceeded. Does not trust Content-Length.
36
+ */
37
+ export declare function readBodyCapped(res: Response, maxBytes: number): Promise<Buffer>;
38
+ //# sourceMappingURL=ssrf-guard.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ssrf-guard.d.ts","sourceRoot":"","sources":["../../src/og/ssrf-guard.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAKH,+EAA+E;AAC/E,MAAM,MAAM,UAAU,GAAG,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC,KAAK,CAAC;IAAE,OAAO,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC,CAAC;AAI/E,qBAAa,gBAAiB,SAAQ,KAAK;IACzC,UAAU,SAAO;gBACL,OAAO,EAAE,MAAM;CAI5B;AAED,0EAA0E;AAC1E,wBAAgB,gBAAgB,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAKpD;AA4ED;;;GAGG;AACH,wBAAsB,kBAAkB,CAAC,MAAM,EAAE,MAAM,EAAE,UAAU,GAAE,UAA0B,GAAG,OAAO,CAAC,IAAI,CAAC,CA+B9G;AAED;;;GAGG;AACH,wBAAsB,cAAc,CAAC,GAAG,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAoBrF"}
@@ -0,0 +1,188 @@
1
+ /**
2
+ * SSRF guard for server-side image fetches.
3
+ *
4
+ * The OG generator fetches caller-supplied `cover`/`logo` URLs from a public
5
+ * endpoint. Without a guard, an attacker could probe internal HTTPS hosts
6
+ * (cloud metadata, private services). This module:
7
+ * - enforces https
8
+ * - rejects private / loopback / link-local / unique-local / metadata
9
+ * targets, checked against the resolved IPs (not just the hostname) so a
10
+ * public domain pointing at a private address is still blocked
11
+ * - exposes a streaming reader that hard-caps the byte count instead of
12
+ * trusting the (forgeable) Content-Length header
13
+ *
14
+ * Residual risk: a narrow DNS-rebinding window between the resolve check and
15
+ * the fetch. Mitigated in practice by the short-lived fetch and the literal-IP
16
+ * checks; full pinning would require a custom connect-time hook.
17
+ */
18
+ import { lookup as dnsLookup } from "node:dns/promises";
19
+ import { isIP } from "node:net";
20
+ const defaultLookup = (host) => dnsLookup(host, { all: true });
21
+ export class SsrfBlockedError extends Error {
22
+ statusCode = 400;
23
+ constructor(message) {
24
+ super(message);
25
+ this.name = "SsrfBlockedError";
26
+ }
27
+ }
28
+ /** True if an IPv4/IPv6 literal is private, loopback, link-local, etc. */
29
+ export function isPrivateAddress(ip) {
30
+ const kind = isIP(ip);
31
+ if (kind === 4)
32
+ return isPrivateIPv4(ip);
33
+ if (kind === 6)
34
+ return isPrivateIPv6(ip.toLowerCase());
35
+ return true; // not a parseable IP → treat as unsafe
36
+ }
37
+ function isPrivateIPv4(ip) {
38
+ const o = ip.split(".").map(Number);
39
+ if (o.length !== 4 || o.some((n) => Number.isNaN(n) || n < 0 || n > 255))
40
+ return true;
41
+ const [a, b] = o;
42
+ if (a === 0)
43
+ return true; // 0.0.0.0/8
44
+ if (a === 10)
45
+ return true; // 10/8 private
46
+ if (a === 127)
47
+ return true; // loopback
48
+ if (a === 169 && b === 254)
49
+ return true; // link-local + cloud metadata 169.254.169.254
50
+ if (a === 172 && b >= 16 && b <= 31)
51
+ return true; // 172.16/12 private
52
+ if (a === 192 && b === 168)
53
+ return true; // 192.168/16 private
54
+ if (a === 100 && b >= 64 && b <= 127)
55
+ return true; // 100.64/10 CGNAT
56
+ if (a >= 224)
57
+ return true; // multicast + reserved
58
+ return false;
59
+ }
60
+ /**
61
+ * Expand an IPv6 string (with `::` compression and/or a trailing dotted IPv4)
62
+ * into its 8 16-bit hextet values. Returns null if it can't be parsed.
63
+ */
64
+ function expandIPv6(ip) {
65
+ const parts = ip.split("::");
66
+ if (parts.length > 2)
67
+ return null;
68
+ const toHextets = (segment) => {
69
+ if (segment === "")
70
+ return [];
71
+ const out = [];
72
+ for (const piece of segment.split(":")) {
73
+ if (piece.includes(".")) {
74
+ // Embedded dotted IPv4 → two hextets.
75
+ const o = piece.split(".").map(Number);
76
+ if (o.length !== 4 || o.some((n) => Number.isNaN(n) || n < 0 || n > 255))
77
+ return null;
78
+ out.push((o[0] << 8) | o[1], (o[2] << 8) | o[3]);
79
+ }
80
+ else {
81
+ if (!/^[0-9a-fA-F]{1,4}$/.test(piece))
82
+ return null;
83
+ out.push(parseInt(piece, 16));
84
+ }
85
+ }
86
+ return out;
87
+ };
88
+ const head = toHextets(parts[0]);
89
+ const tail = parts.length === 2 ? toHextets(parts[1]) : [];
90
+ if (head === null || tail === null)
91
+ return null;
92
+ if (parts.length === 2) {
93
+ const gap = 8 - head.length - tail.length;
94
+ if (gap < 0)
95
+ return null;
96
+ return [...head, ...Array(gap).fill(0), ...tail];
97
+ }
98
+ return head.length === 8 ? head : null;
99
+ }
100
+ function isPrivateIPv6(ip) {
101
+ const h = expandIPv6(ip);
102
+ if (!h)
103
+ return true; // unparseable → unsafe
104
+ // Loopback (::1) and unspecified (::)
105
+ if (h.every((x, i) => (i < 7 ? x === 0 : x === 0 || x === 1)))
106
+ return true;
107
+ // IPv4-mapped (::ffff:a.b.c.d, any notation) and deprecated IPv4-compatible
108
+ // (::a.b.c.d): first 5 hextets zero, optional ffff marker → check embedded v4.
109
+ const firstFiveZero = h.slice(0, 5).every((x) => x === 0);
110
+ if (firstFiveZero && (h[5] === 0xffff || h[5] === 0)) {
111
+ const v4 = `${h[6] >> 8}.${h[6] & 0xff}.${h[7] >> 8}.${h[7] & 0xff}`;
112
+ return isPrivateIPv4(v4);
113
+ }
114
+ const first = h[0];
115
+ if ((first & 0xff00) === 0xff00)
116
+ return true; // multicast ff00::/8
117
+ if ((first & 0xffc0) === 0xfe80)
118
+ return true; // link-local fe80::/10
119
+ if ((first & 0xfe00) === 0xfc00)
120
+ return true; // unique local fc00::/7
121
+ return false;
122
+ }
123
+ /**
124
+ * Reject a URL that isn't safe to fetch server-side. Throws SsrfBlockedError
125
+ * (400) on https violation or a private/blocked resolved address.
126
+ */
127
+ export async function assertFetchableUrl(rawUrl, lookupImpl = defaultLookup) {
128
+ let url;
129
+ try {
130
+ url = new URL(rawUrl);
131
+ }
132
+ catch {
133
+ throw new SsrfBlockedError(`invalid url: ${rawUrl}`);
134
+ }
135
+ if (url.protocol !== "https:") {
136
+ throw new SsrfBlockedError(`only https image URLs are allowed: ${rawUrl}`);
137
+ }
138
+ const host = url.hostname;
139
+ // Literal IP in the host → check directly (no DNS).
140
+ if (isIP(host)) {
141
+ if (isPrivateAddress(host))
142
+ throw new SsrfBlockedError(`blocked private address: ${host}`);
143
+ return;
144
+ }
145
+ // Hostname → resolve and ensure EVERY address is public.
146
+ let addrs;
147
+ try {
148
+ addrs = await lookupImpl(host);
149
+ }
150
+ catch {
151
+ throw new SsrfBlockedError(`dns resolution failed: ${host}`);
152
+ }
153
+ if (addrs.length === 0)
154
+ throw new SsrfBlockedError(`no addresses for host: ${host}`);
155
+ for (const { address } of addrs) {
156
+ if (isPrivateAddress(address)) {
157
+ throw new SsrfBlockedError(`host ${host} resolves to blocked address ${address}`);
158
+ }
159
+ }
160
+ }
161
+ /**
162
+ * Read a fetch Response body into a Buffer, aborting once `maxBytes` is
163
+ * exceeded. Does not trust Content-Length.
164
+ */
165
+ export async function readBodyCapped(res, maxBytes) {
166
+ if (!res.body) {
167
+ const buf = Buffer.from(await res.arrayBuffer());
168
+ if (buf.byteLength > maxBytes)
169
+ throw new SsrfBlockedError(`response too large (> ${maxBytes} bytes)`);
170
+ return buf;
171
+ }
172
+ const chunks = [];
173
+ let total = 0;
174
+ const reader = res.body.getReader();
175
+ for (;;) {
176
+ const { done, value } = await reader.read();
177
+ if (done)
178
+ break;
179
+ total += value.byteLength;
180
+ if (total > maxBytes) {
181
+ await reader.cancel().catch(() => { });
182
+ throw new SsrfBlockedError(`response too large (> ${maxBytes} bytes)`);
183
+ }
184
+ chunks.push(Buffer.from(value));
185
+ }
186
+ return Buffer.concat(chunks);
187
+ }
188
+ //# sourceMappingURL=ssrf-guard.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ssrf-guard.js","sourceRoot":"","sources":["../../src/og/ssrf-guard.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ import type { NFTColor } from "./passport-svg.js";
2
+ export type OgTemplate = "default" | "section" | "cover" | "banner";
3
+ export type OgFormat = "png" | "svg" | "html";
4
+ export interface OgTemplateParams {
5
+ width: number;
6
+ height: number;
7
+ logo: string;
8
+ background: string;
9
+ logoRounded: boolean;
10
+ color: NFTColor;
11
+ title: string;
12
+ description: string;
13
+ section: string;
14
+ cover: string;
15
+ template: OgTemplate;
16
+ format: OgFormat;
17
+ }
18
+ /**
19
+ * Public brand-logo SVG helper. Returns an inline SVG string with the given
20
+ * stroke color. Not used by any of the 4 OG templates in this file — it's
21
+ * exported for external callers (e.g., admin UI, embed previews) that want
22
+ * the same brand mark with a custom stroke.
23
+ */
24
+ export declare const getLogoSvg: (color: string) => string;
25
+ export declare const getTemplate: (params: OgTemplateParams) => Promise<unknown>;
26
+ //# sourceMappingURL=templates.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"templates.d.ts","sourceRoot":"","sources":["../../src/og/templates.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGlD,MAAM,MAAM,UAAU,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,GAAG,QAAQ,CAAC;AACpE,MAAM,MAAM,QAAQ,GAAG,KAAK,GAAG,KAAK,GAAG,MAAM,CAAC;AAE9C,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,OAAO,CAAC;IACrB,KAAK,EAAE,QAAQ,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,UAAU,CAAC;IACrB,MAAM,EAAE,QAAQ,CAAC;CAClB;AAWD;;;;;GAKG;AACH,eAAO,MAAM,UAAU,GAAI,OAAO,MAAM,KAAG,MAe1C,CAAC;AA+TF,eAAO,MAAM,WAAW,GAAU,QAAQ,gBAAgB,KAAG,OAAO,CAAC,OAAO,CAiB3E,CAAC"}