@arkenv/core 1.0.0-alpha.2

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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Yam Borodetsky <https://yam.codes/>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,104 @@
1
+ <p align="center">
2
+ <a href="https://github.com/yamcodes/arkenv/blob/main/apps/www/public/assets/icon.svg"><img alt="ArkEnv Logo" src="https://arkenv.js.org/assets/icon.svg" width="160px" align="center"/></a>
3
+ <h1 align="center">ArkEnv</h1>
4
+ <div align="center">
5
+ <p align="center">
6
+ Environment variable validation from editor to runtime<br/> for <a href="https://nextjs.org/">Next.js</a>, <a href="https://nuxt.com/">Nuxt</a>, <a href="https://nodejs.org/">Node.js</a>, <a href="https://vite.dev/">Vite</a>, and <a href="https://bun.com/">Bun</a>
7
+ </p>
8
+ <a href="https://github.com/yamcodes/arkenv/actions/workflows/test.yml?query=branch%3Amain"><img alt="Test Status" src="https://github.com/yamcodes/arkenv/actions/workflows/tests-badge.yml/badge.svg?branch=main"></a>
9
+ <a href="https://bundlephobia.com/package/arkenv"><img alt="npm bundle size" src="https://img.shields.io/bundlephobia/minzip/arkenv"></a>
10
+ <a href="https://arktype.io/docs/ecosystem#arkenv"><img alt="ArkType Ecosystem" src="https://custom-icon-badges.demolab.com/badge/ArkType%20Ecosystem-0d1526?logo=arktype2&logoColor=e9eef9"></a>
11
+ <a href="https://pullfrog.com"><img alt="Pullfrog" src="https://custom-icon-badges.demolab.com/badge/Powered%20by%20Pullfrog-2f4032?logo=pullfrog-white"></a>
12
+ </div>
13
+ </p>
14
+
15
+ <div align="center">
16
+ <a href="https://arkenv.js.org/docs/arkenv">Docs</a>
17
+ <span>&nbsp;&nbsp;•&nbsp;&nbsp;</span>
18
+ <a href="https://arkenv.js.org/docs/arkenv/faq">FAQ</a>
19
+ <span>&nbsp;&nbsp;•&nbsp;&nbsp;</span>
20
+ <a href="https://stackblitz.com/github/yamcodes/arkenv/tree/main/examples/stackblitz?file=index.ts">Try on StackBlitz</a>
21
+ <br />
22
+ </div>
23
+
24
+ <br />
25
+ <br />
26
+
27
+ <p align="center">
28
+ <img alt="ArkEnv Demo" src="https://arkenv.js.org/assets/demo.gif" />
29
+ </p>
30
+
31
+ <br />
32
+
33
+
34
+
35
+ <details open>
36
+ <summary>npm</summary>
37
+
38
+ ```sh
39
+ npx arkenv@latest init
40
+ ```
41
+
42
+ </details>
43
+
44
+ <details>
45
+ <summary>pnpm</summary>
46
+
47
+ ```sh
48
+ pnx arkenv@latest init
49
+ ```
50
+
51
+ </details>
52
+
53
+ <details>
54
+ <summary>Yarn</summary>
55
+
56
+ ```sh
57
+ yarn dlx arkenv@latest init
58
+ ```
59
+
60
+ </details>
61
+
62
+ <details>
63
+ <summary>Bun</summary>
64
+
65
+ ```sh
66
+ bunx arkenv@latest init
67
+ ```
68
+
69
+ </details>
70
+
71
+ <br />
72
+
73
+ ### [Read the docs →](https://arkenv.js.org/docs/ArkEnv/quickstart)
74
+
75
+ <br />
76
+
77
+ ## Supporting ArkEnv
78
+
79
+ If you love ArkEnv, you can support the project by **starring it on GitHub**!
80
+
81
+ You are also welcome to [contribute to the project](https://github.com/yamcodes/arkenv/blob/main/docs/CONTRIBUTING.md) and join the wonderful people who have contributed:
82
+
83
+ <!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
84
+ <!-- prettier-ignore-start -->
85
+ <!-- markdownlint-disable -->
86
+ <table>
87
+ <tbody>
88
+ <tr>
89
+ <td align="center" valign="top" width="14.28%"><a href="https://yam.codes"><img src="https://avatars.githubusercontent.com/u/2014360?v=4?s=100" width="100px;" alt="Yam C Borodetsky"/><br /><sub><b>Yam C Borodetsky</b></sub></a><br /><a href="https://github.com/yamcodes/arkenv/commits?author=yamcodes" title="Code">💻</a> <a href="#question-yamcodes" title="Answering Questions">💬</a> <a href="#ideas-yamcodes" title="Ideas, Planning, & Feedback">🤔</a> <a href="#design-yamcodes" title="Design">🎨</a> <a href="https://github.com/yamcodes/arkenv/commits?author=yamcodes" title="Documentation">📖</a> <a href="https://github.com/yamcodes/arkenv/issues?q=author%3Ayamcodes" title="Bug reports">🐛</a> <a href="#example-yamcodes" title="Examples">💡</a> <a href="#infra-yamcodes" title="Infrastructure (Hosting, Build-Tools, etc)">🚇</a> <a href="https://github.com/yamcodes/arkenv/commits?author=yamcodes" title="Tests">⚠️</a></td>
90
+ <td align="center" valign="top" width="14.28%"><a href="https://github.com/aruaycodes"><img src="https://avatars.githubusercontent.com/u/57131628?v=4?s=100" width="100px;" alt="Aruay Berdikulova"/><br /><sub><b>Aruay Berdikulova</b></sub></a><br /><a href="https://github.com/yamcodes/arkenv/commits?author=aruaycodes" title="Code">💻</a> <a href="#ideas-aruaycodes" title="Ideas, Planning, & Feedback">🤔</a></td>
91
+ <td align="center" valign="top" width="14.28%"><a href="https://arktype.io"><img src="https://avatars.githubusercontent.com/u/10645823?v=4?s=100" width="100px;" alt="David Blass"/><br /><sub><b>David Blass</b></sub></a><br /><a href="#ideas-ssalbdivad" title="Ideas, Planning, & Feedback">🤔</a> <a href="#mentoring-ssalbdivad" title="Mentoring">🧑‍🏫</a> <a href="#question-ssalbdivad" title="Answering Questions">💬</a></td>
92
+ <td align="center" valign="top" width="14.28%"><a href="https://github.com/danciudev"><img src="https://avatars.githubusercontent.com/u/44430251?v=4?s=100" width="100px;" alt="Andrei Danciu"/><br /><sub><b>Andrei Danciu</b></sub></a><br /><a href="https://github.com/yamcodes/arkenv/commits?author=danciudev" title="Code">💻</a></td>
93
+ <td align="center" valign="top" width="14.28%"><a href="https://joakim.beng.se"><img src="https://avatars.githubusercontent.com/u/1427383?v=4?s=100" width="100px;" alt="Joakim Carlstein"/><br /><sub><b>Joakim Carlstein</b></sub></a><br /><a href="https://github.com/yamcodes/arkenv/commits?author=joakimbeng" title="Code">💻</a> <a href="https://github.com/yamcodes/arkenv/commits?author=joakimbeng" title="Documentation">📖</a></td>
94
+ <td align="center" valign="top" width="14.28%"><a href="https://fresh-accordion-06a.notion.site/Jiayi-Du-1817075e92978076b95cf9d90fb5eceb"><img src="https://avatars.githubusercontent.com/u/166608075?v=4?s=100" width="100px;" alt="RoomWithOutRoof"/><br /><sub><b>RoomWithOutRoof</b></sub></a><br /><a href="https://github.com/yamcodes/arkenv/commits?author=Jah-yee" title="Documentation">📖</a></td>
95
+ </tr>
96
+ </tbody>
97
+ </table>
98
+
99
+ <!-- markdownlint-restore -->
100
+ <!-- prettier-ignore-end -->
101
+
102
+ <!-- ALL-CONTRIBUTORS-LIST:END -->
103
+
104
+ We [acknowledge](https://github.com/yamcodes/arkenv/blob/main/docs/ACKNOWLEDGEMENTS.md) the various projects and people that inspired ArkEnv.
package/dist/index.cjs ADDED
@@ -0,0 +1,403 @@
1
+ Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: 'Module' } });
2
+ let arktype = require("arktype");
3
+
4
+ //#region ../internal/scope/dist/index.js
5
+ const n$1 = (0, arktype.type)(`0 <= number.integer <= 65535`), r$1 = (0, arktype.type)(`string.ip | 'localhost'`), i$1 = (0, arktype.scope)({
6
+ string: arktype.type.module({
7
+ ...arktype.type.keywords.string,
8
+ host: r$1
9
+ }),
10
+ number: arktype.type.module({
11
+ ...arktype.type.keywords.number,
12
+ port: n$1
13
+ })
14
+ });
15
+
16
+ //#endregion
17
+ //#region ../internal/utils/dist/index.js
18
+ const e = (e) => {
19
+ if (typeof e == `number` || typeof e != `string` || !e.trim()) return e;
20
+ if (e.trim() === `NaN`) return NaN;
21
+ let t = Number(e);
22
+ return Number.isNaN(t) ? e : t;
23
+ }, t = (e) => e === `true` ? !0 : e === `false` ? !1 : e, n = (e) => {
24
+ if (typeof e != `string`) return e;
25
+ let t = e.trim();
26
+ if (t[0] !== `{` && t[0] !== `[`) return e;
27
+ try {
28
+ return JSON.parse(t);
29
+ } catch {
30
+ return e;
31
+ }
32
+ }, r = (e) => {
33
+ if (e instanceof Date || typeof e != `string` || !e.trim()) return e;
34
+ let t = new Date(e);
35
+ return Number.isNaN(t.getTime()) ? e : t;
36
+ }, i = (e) => {
37
+ let t = {};
38
+ for (let n in e) {
39
+ let r = e[n];
40
+ r !== `` && (t[n] = r);
41
+ }
42
+ return t;
43
+ }, a = `*`, o = (e, t = []) => {
44
+ let n = [];
45
+ if (!e || typeof e != `object` || Array.isArray(e)) return n;
46
+ let r = e;
47
+ if (`const` in r) {
48
+ let e = typeof r.const;
49
+ (e === `number` || e === `boolean`) && n.push({
50
+ path: [...t],
51
+ type: `primitive`
52
+ });
53
+ }
54
+ `enum` in r && Array.isArray(r.enum) && r.enum.some((e) => typeof e == `number` || typeof e == `boolean`) && n.push({
55
+ path: [...t],
56
+ type: `primitive`
57
+ });
58
+ let i = r.type;
59
+ if (i === `number` || i === `integer` || i === `boolean`) n.push({
60
+ path: [...t],
61
+ type: `primitive`
62
+ });
63
+ else if (i === `string` && `format` in r && (r.format === `date-time` || r.format === `date`)) n.push({
64
+ path: [...t],
65
+ type: `date`
66
+ });
67
+ else if (i === `object`) {
68
+ if (r.properties && Object.keys(r.properties).length > 0) {
69
+ n.push({
70
+ path: [...t],
71
+ type: `object`
72
+ });
73
+ for (let e in r.properties) n.push(...o(r.properties[e], [...t, e]));
74
+ }
75
+ } else i === `array` && (n.push({
76
+ path: [...t],
77
+ type: `array`
78
+ }), r.items && (Array.isArray(r.items) ? r.items.forEach((e, r) => {
79
+ n.push(...o(e, [...t, String(r)]));
80
+ }) : n.push(...o(r.items, [...t, `*`]))));
81
+ for (let e of [
82
+ `anyOf`,
83
+ `allOf`,
84
+ `oneOf`
85
+ ]) if (r[e] && Array.isArray(r[e])) for (let i of r[e]) n.push(...o(i, t));
86
+ let a = /* @__PURE__ */ new Set();
87
+ return n.filter((e) => {
88
+ let t = e.path.join(`/`) + `:` + e.type;
89
+ return a.has(t) ? !1 : a.add(t);
90
+ });
91
+ }, s = (i, a, o = {}) => {
92
+ let { arrayFormat: s = `comma` } = o, c = (e) => {
93
+ if (s === `json`) try {
94
+ return JSON.parse(e);
95
+ } catch {
96
+ return e;
97
+ }
98
+ return e.trim() ? e.split(`,`).map((e) => e.trim()) : [];
99
+ }, l = (i, a) => {
100
+ if (a === `array` && typeof i == `string`) return c(i);
101
+ if (a === `object` && typeof i == `string`) return n(i);
102
+ if (a === `date` && typeof i == `string`) return r(i);
103
+ if (a === `primitive`) {
104
+ if (Array.isArray(i)) return i.map((n) => {
105
+ if (typeof n != `string`) return n;
106
+ let r = e(n);
107
+ return typeof r == `number` ? r : t(n);
108
+ });
109
+ if (typeof i != `string`) return i;
110
+ let n = e(i);
111
+ return typeof n == `number` ? n : t(i);
112
+ }
113
+ return i;
114
+ };
115
+ if (typeof i != `object` || !i) {
116
+ let e = a.find((e) => e.path.length === 0);
117
+ return e ? l(i, e.type) : i;
118
+ }
119
+ let u = [...a].sort((e, t) => e.path.length - t.path.length), d = (e, t, n) => {
120
+ if (t.length === 0) return n(e);
121
+ let [r, ...i] = t;
122
+ if (r === `*`) {
123
+ if (Array.isArray(e)) {
124
+ let t = !1, r = e.map((e) => {
125
+ let r = d(e, i, n);
126
+ return r !== e && (t = !0), r;
127
+ });
128
+ return t ? r : e;
129
+ }
130
+ return e;
131
+ }
132
+ if (!e || typeof e != `object`) return e;
133
+ if (Array.isArray(e)) {
134
+ let t = Number(r);
135
+ if (!Number.isNaN(t) && t >= 0 && t < e.length) {
136
+ let r = d(e[t], i, n);
137
+ if (r !== e[t]) {
138
+ let n = [...e];
139
+ return n[t] = r, n;
140
+ }
141
+ }
142
+ return e;
143
+ }
144
+ if (Object.hasOwn(e, r)) {
145
+ let t = d(e[r], i, n);
146
+ if (t !== e[r]) return {
147
+ ...e,
148
+ [r]: t
149
+ };
150
+ }
151
+ return e;
152
+ }, f = i;
153
+ for (let e of u) e.path.length > 0 && (f = d(f, e.path, (t) => l(t, e.type)));
154
+ return f;
155
+ };
156
+ function c(e, t, n, r) {
157
+ let a = t ? i(e) : e, c = { ...a }, l = [];
158
+ if (r) {
159
+ let e = r();
160
+ l.push(...e.missingKeys || []), e.hasSchema && (c = s(c, o(e.schema), { arrayFormat: n }));
161
+ }
162
+ return {
163
+ processedEnv: a,
164
+ coercedEnv: c,
165
+ missingKeys: l
166
+ };
167
+ }
168
+ const l = (e, t = 2, { dontDetectNewlines: n = !1 } = {}) => n ? `${` `.repeat(t)}${e}` : e.split(`
169
+ `).map((e) => `${` `.repeat(t)}${e}`).join(`
170
+ `), u = {
171
+ red: `\x1B[31m`,
172
+ yellow: `\x1B[33m`,
173
+ cyan: `\x1B[36m`,
174
+ reset: `\x1B[0m`
175
+ }, d = () => typeof process < `u` && process.versions != null && process.versions.node != null, f = () => !!(!d() || process.env.NO_COLOR !== void 0 || process.env.CI !== void 0 || process.stdout && !process.stdout.isTTY), p = (e, t) => d() && !f() ? `${u[e]}${t}${u.reset}` : t;
176
+ function m(e) {
177
+ return e.map((e) => `${p(`yellow`, e.path)} ${e.message.trimStart()}`).join(`
178
+ `);
179
+ }
180
+ var h = class extends Error {
181
+ constructor(e, t = `Errors found while validating environment variables`) {
182
+ let n = m(e);
183
+ super(`${p(`red`, t)}\n${l(n)}\n`), this.name = `ArkEnvError`, this.issues = e;
184
+ }
185
+ };
186
+ Object.defineProperty(h, `name`, { value: `ArkEnvError` });
187
+ const y = /secret|(_|^)key(_|$)|token|(_|^)password(_|$)|(_|^)pass(_|$)|(_|^)auth(_|$)|jwt|cert|credential|database_url|db_url/i;
188
+ function b(e) {
189
+ if (e !== void 0) return e;
190
+ if (typeof process > `u`) return !1;
191
+ let t = process.env.ARKENV_DEBUG_SECRETS;
192
+ return t === `true` || t === `1`;
193
+ }
194
+ function x(e) {
195
+ return y.test(e) && !/public/i.test(e);
196
+ }
197
+ function E(e) {
198
+ try {
199
+ return {
200
+ success: !0,
201
+ data: e()
202
+ };
203
+ } catch (e) {
204
+ if (e instanceof h) return {
205
+ success: !1,
206
+ issues: e.issues
207
+ };
208
+ throw e;
209
+ }
210
+ }
211
+ function D(e, t, n, r, i, a) {
212
+ let o = {
213
+ path: e,
214
+ message: t,
215
+ code: n,
216
+ meta: r ?? {}
217
+ };
218
+ return i && (o.expected = i), a !== void 0 && (o.received = a), o;
219
+ }
220
+ function P(e) {
221
+ if (!e || typeof e != `object` && typeof e != `function`) return [];
222
+ if (e.json && typeof e.json == `object` && e.json.domain === `object`) {
223
+ let t = [];
224
+ if (Array.isArray(e.json.required)) for (let n of e.json.required) n && typeof n == `object` && `key` in n && t.push(n.key);
225
+ if (Array.isArray(e.json.optional)) for (let n of e.json.optional) n && typeof n == `object` && `key` in n && t.push(n.key);
226
+ return t;
227
+ }
228
+ let t = e[`~standard`], n = typeof t?.jsonSchema?.input == `function` && t.jsonSchema.input || typeof e.jsonSchema?.input == `function` && e.jsonSchema.input;
229
+ if (n) try {
230
+ let e = n({ target: `draft-07` });
231
+ if (e && typeof e == `object` && e.properties) return Object.keys(e.properties);
232
+ } catch {}
233
+ if (typeof e.toJSONSchema == `function`) try {
234
+ let t = e.toJSONSchema();
235
+ if (t && typeof t == `object` && t.properties) return Object.keys(t.properties);
236
+ } catch {}
237
+ if (typeof e.toStandardJSONSchema?.v1 == `function`) try {
238
+ let t = e.toStandardJSONSchema.v1();
239
+ if (t && typeof t == `object` && t.properties) return Object.keys(t.properties);
240
+ } catch {}
241
+ return Object.keys(e);
242
+ }
243
+
244
+ //#endregion
245
+ //#region src/arktype/index.ts
246
+ const ARKTYPE_CODE_MAP = {
247
+ required: "MISSING_VARIABLE",
248
+ pattern: "PATTERN_MISMATCH",
249
+ min: "VALUE_TOO_SMALL",
250
+ minLength: "VALUE_TOO_SMALL",
251
+ max: "VALUE_TOO_LARGE",
252
+ maxLength: "VALUE_TOO_LARGE",
253
+ divisor: "INVALID_TYPE",
254
+ intersection: "INVALID_TYPE",
255
+ union: "INVALID_TYPE",
256
+ unit: "INVALID_TYPE",
257
+ proto: "INVALID_TYPE",
258
+ domain: "INVALID_TYPE",
259
+ exactLength: "INVALID_FORMAT",
260
+ before: "INVALID_FORMAT",
261
+ after: "INVALID_FORMAT",
262
+ predicate: "CUSTOM"
263
+ };
264
+ /**
265
+ * Map an ArkType error code to an ArkEnv issue code.
266
+ *
267
+ * @param engineCode The ArkType engine error code
268
+ * @returns The corresponding ArkEnv issue code
269
+ */
270
+ function mapArkTypeCode(engineCode) {
271
+ return engineCode in ARKTYPE_CODE_MAP ? ARKTYPE_CODE_MAP[engineCode] : "INVALID_FORMAT";
272
+ }
273
+ /**
274
+ * Extract numeric bounds from an ArkType error object.
275
+ *
276
+ * @param error The ArkType error object
277
+ * @returns An object containing optional min and max bounds
278
+ */
279
+ function getArkTypeMeta(error) {
280
+ const min = error.min ?? error.rule;
281
+ const max = error.max;
282
+ return {
283
+ ...typeof min === "number" ? { min } : {},
284
+ ...typeof max === "number" ? { max } : {}
285
+ };
286
+ }
287
+ /**
288
+ * Redact and colorize the value inside a "(was ...)" message fragment.
289
+ *
290
+ * @param message The validation error message
291
+ * @param path The environment variable key path
292
+ * @param debugSecrets Whether to display sensitive values in debug mode
293
+ * @returns The modified error message with styled or redacted value
294
+ */
295
+ function redactMessageWasValue(message, path, debugSecrets) {
296
+ const valueMatch = message.match(/\(was (.*)\)/);
297
+ if (!valueMatch?.[1]) return message;
298
+ const value = valueMatch[1];
299
+ const displayedValue = !b(debugSecrets) && x(path) ? "[REDACTED]" : value;
300
+ if (displayedValue.includes("\x1B[")) return message;
301
+ return message.replace(`(was ${value})`, `(was ${p("cyan", displayedValue)})`);
302
+ }
303
+ /**
304
+ * Convert ArkType's `ArkErrors` (keyed by path) into a flat `EnvIssue[]`
305
+ * suitable for `ArkEnvError`.
306
+ *
307
+ * @param errors The ArkType errors object to convert
308
+ * @param config Optional ArkEnvConfig to read debugSecrets options
309
+ * @returns An array of flattened validation issues
310
+ *
311
+ * @internal
312
+ */
313
+ function arkErrorsToIssues(errors, config) {
314
+ return Object.entries(errors.byPath).map(([path, error]) => {
315
+ let message = error.message;
316
+ let trimmed = message.trimStart();
317
+ if (trimmed.length > 0 && ":.-".includes(trimmed[0])) trimmed = trimmed.slice(1).trimStart();
318
+ if (trimmed.toLowerCase().startsWith(path.toLowerCase())) {
319
+ let rest = trimmed.slice(path.length).trimStart();
320
+ if (rest.length > 0 && ":.-".includes(rest[0])) rest = rest.slice(1);
321
+ message = rest.trimStart();
322
+ }
323
+ message = redactMessageWasValue(message, path, config?.debugSecrets);
324
+ const code = mapArkTypeCode(error.code);
325
+ const meta = { ...getArkTypeMeta(error) };
326
+ return D(path, message, code, meta, error.expected, error.code === "required" ? void 0 : error.data);
327
+ });
328
+ }
329
+ /**
330
+ * Parse and validate environment variables using ArkEnv's schema rules.
331
+ *
332
+ * This applies:
333
+ * - schema validation
334
+ * - optional coercion (strings → numbers, booleans, arrays)
335
+ * - undeclared key handling
336
+ *
337
+ * On success, returns the validated environment object.
338
+ * On failure, throws an {@link ArkEnvError}.
339
+ *
340
+ * This is a low-level utility used internally by ArkEnv.
341
+ * Most users should prefer the default `arkenv()` export.
342
+ *
343
+ * @param def The ArkType schema definition to validate against
344
+ * @param config The configuration object for parsing and coercion
345
+ * @returns The parsed and validated environment variables
346
+ * @throws {@link ArkEnvError} if validation fails
347
+ *
348
+ * @internal
349
+ */
350
+ function parse(def, config) {
351
+ const { env = process.env, coerce: shouldCoerce = true, onUndeclaredKey = "delete", arrayFormat = "comma", emptyAsUndefined = false } = config;
352
+ const schemaWithKeys = (typeof def === "function" && "assert" in def ? def : i$1.type.raw(def)).onUndeclaredKey(onUndeclaredKey);
353
+ const { coercedEnv } = c(env, emptyAsUndefined, arrayFormat, shouldCoerce ? () => {
354
+ return {
355
+ schema: schemaWithKeys.in.toJsonSchema({ fallback: (ctx) => ctx.base }),
356
+ hasSchema: true
357
+ };
358
+ } : void 0);
359
+ const validatedEnv = schemaWithKeys(coercedEnv);
360
+ if (validatedEnv instanceof arktype.ArkErrors) throw new h(arkErrorsToIssues(validatedEnv, config));
361
+ return validatedEnv;
362
+ }
363
+
364
+ //#endregion
365
+ //#region src/arkenv.ts
366
+ function arkenv(def, config = {}) {
367
+ if (config.safe) return E(() => parse(def, config));
368
+ return parse(def, config);
369
+ }
370
+
371
+ //#endregion
372
+ //#region src/index.ts
373
+ /**
374
+ * Like ArkType's `type`, but with ArkEnv's extra keywords, such as:
375
+ *
376
+ * - `string.host` – a hostname (e.g. `"localhost"`, `"127.0.0.1"`)
377
+ * - `number.port` – a port number (e.g. `8080`)
378
+ *
379
+ * See ArkType's docs for the full API:
380
+ * https://arktype.io/docs/type-api
381
+ */
382
+ const type = i$1.type;
383
+ /**
384
+ * ArkEnv's main export, an alias for {@link arkenv}
385
+ *
386
+ * {@link https://arkenv.js.org | ArkEnv} is a typesafe environment variables validator from editor to runtime.
387
+ */
388
+ var src_default = arkenv;
389
+
390
+ //#endregion
391
+ exports.ArkEnvError = h;
392
+ exports.arkenv = arkenv;
393
+ exports.default = src_default;
394
+ exports.formatIssues = m;
395
+ exports.getSchemaKeys = P;
396
+ exports.type = type;
397
+
398
+ // CJS Interop Shim
399
+ if (module.exports && module.exports.default) {
400
+ Object.assign(module.exports.default, module.exports);
401
+ module.exports = module.exports.default;
402
+ }
403
+