Skip to content

Commit 6901c46

Browse files
authored
Generate dynamic env types (#6413)
* use descriptions in generated env types * generate dynamic env types * remove references to PublicEnv and PrivateEnv * generate dynamic env types - closes #6202
1 parent 8c4cb0a commit 6901c46

File tree

16 files changed

+79
-77
lines changed

16 files changed

+79
-77
lines changed

.changeset/dull-cheetahs-clean.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@sveltejs/kit': patch
3+
---
4+
5+
[breaking] remove App.PrivateEnv and App.PublicEnv in favour of generated types

.changeset/lovely-otters-lie.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'create-svelte': patch
3+
---
4+
5+
Remove App.PrivateEnv and App.PublicEnv placeholders

packages/create-svelte/templates/default/src/app.d.ts

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,4 @@ declare namespace App {
99
// interface PageData {}
1010

1111
// interface Platform {}
12-
13-
// interface PrivateEnv {}
14-
15-
// interface PublicEnv {}
1612
}

packages/create-svelte/templates/libskeleton/src/app.d.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,4 @@ declare namespace App {
77
// interface Locals {}
88
// interface PageData {}
99
// interface Platform {}
10-
// interface PrivateEnv {}
11-
// interface PublicEnv {}
1210
}

packages/create-svelte/templates/skeleton/src/app.d.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,4 @@ declare namespace App {
55
// interface Locals {}
66
// interface PageData {}
77
// interface Platform {}
8-
// interface PrivateEnv {}
9-
// interface PublicEnv {}
108
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
This module provides access to runtime environment variables, as defined by the platform you're running on. For example if you're using [`adapter-node`](https://github.com/sveltejs/kit/tree/master/packages/adapter-node) (or running [`vite preview`](https://kit.svelte.dev/docs/cli)), this is equivalent to `process.env`. This module only includes variables that _do not_ begin with [`config.kit.env.publicPrefix`](https://kit.svelte.dev/docs/configuration#kit-env-publicprefix).
2+
3+
This module cannot be imported into client-side code.
4+
5+
```ts
6+
import { env } from '$env/dynamic/private';
7+
console.log(env.DEPLOYMENT_SPECIFIC_VARIABLE);
8+
```
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
Similar to [`$env/dynamic/private`](https://kit.svelte.dev/docs/modules#$env-dynamic-private), but only includes variables that begin with [`config.kit.env.publicPrefix`](https://kit.svelte.dev/docs/configuration#kit-env-publicprefix) (which defaults to `PUBLIC_`), and can therefore safely be exposed to client-side code.
2+
3+
Note that public dynamic environment variables must all be sent from the server to the client, causing larger network requests — when possible, use `$env/static/public` instead.
4+
5+
```ts
6+
import { env } from '$env/dynamic/public';
7+
console.log(env.PUBLIC_DEPLOYMENT_SPECIFIC_VARIABLE);
8+
```

packages/kit/src/core/env.js

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ export function create_dynamic_module(type) {
3434
* @param {Record<string, string>} env
3535
* @returns {string}
3636
*/
37-
export function create_types(id, env) {
37+
export function create_static_types(id, env) {
3838
const declarations = Object.keys(env)
3939
.filter((k) => valid_identifier.test(k))
4040
.map((k) => `\texport const ${k}: string;`)
@@ -43,6 +43,21 @@ export function create_types(id, env) {
4343
return `declare module '${id}' {\n${declarations}\n}`;
4444
}
4545

46+
/**
47+
* @param {string} id
48+
* @param {Record<string, string>} env
49+
* @returns {string}
50+
*/
51+
export function create_dynamic_types(id, env) {
52+
const properties = Object.keys(env)
53+
.filter((k) => valid_identifier.test(k))
54+
.map((k) => `\t\t${k}: string;`);
55+
56+
properties.push(`\t\t[key: string]: string | undefined;`);
57+
58+
return `declare module '${id}' {\n\texport const env: {\n${properties.join('\n')}\n\t}\n}`;
59+
}
60+
4661
export const reserved = new Set([
4762
'do',
4863
'if',
Lines changed: 36 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,43 @@
1+
import fs from 'fs';
12
import path from 'path';
23
import { get_env } from '../../exports/vite/utils.js';
34
import { GENERATED_COMMENT } from '../../constants.js';
4-
import { create_types } from '../env.js';
5+
import { create_dynamic_types, create_static_types } from '../env.js';
56
import { write_if_changed } from './utils.js';
7+
import { fileURLToPath } from 'url';
68

7-
const types_reference = '/// <reference types="@sveltejs/kit" />\n\n';
9+
const descriptions_dir = fileURLToPath(new URL('../../../scripts/special-types', import.meta.url));
10+
11+
/** @param {string} filename */
12+
function read_description(filename) {
13+
const content = fs.readFileSync(`${descriptions_dir}/${filename}`, 'utf8');
14+
return `/**\n${content
15+
.trim()
16+
.split('\n')
17+
.map((line) => ` * ${line}`)
18+
.join('\n')}\n */`;
19+
}
20+
21+
/**
22+
* @param {{ public: Record<string, string>, private: Record<string, string> }} env
23+
*/
24+
const template = (env) => `
25+
${GENERATED_COMMENT}
26+
27+
/// <reference types="@sveltejs/kit" />
28+
29+
${read_description('$env+static+private.md')}
30+
${create_static_types('$env/static/private', env.private)}
31+
32+
${read_description('$env+static+public.md')}
33+
${create_static_types('$env/static/public', env.public)}
34+
35+
${read_description('$env+dynamic+private.md')}
36+
${create_dynamic_types('$env/dynamic/private', env.private)}
37+
38+
${read_description('$env+dynamic+public.md')}
39+
${create_dynamic_types('$env/dynamic/public', env.public)}
40+
`;
841

942
/**
1043
* Writes ambient declarations including types reference to @sveltejs/kit,
@@ -16,12 +49,5 @@ const types_reference = '/// <reference types="@sveltejs/kit" />\n\n';
1649
export function write_ambient(config, mode) {
1750
const env = get_env(config.env, mode);
1851

19-
write_if_changed(
20-
path.join(config.outDir, 'ambient.d.ts'),
21-
GENERATED_COMMENT +
22-
types_reference +
23-
create_types('$env/static/public', env.public) +
24-
'\n\n' +
25-
create_types('$env/static/private', env.private)
26-
);
52+
write_if_changed(path.join(config.outDir, 'ambient.d.ts'), template(env));
2753
}

packages/kit/src/runtime/env-private.js

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
/** @type {App.PrivateEnv} */
21
export let env = {};
32

43
/** @type {(environment: Record<string, string>) => void} */

0 commit comments

Comments
 (0)