forked from dfinity/icp-js-bindgen
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathvite.ts
More file actions
136 lines (127 loc) · 3.54 KB
/
vite.ts
File metadata and controls
136 lines (127 loc) · 3.54 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
/**
* The Vite plugin is used to generate bindings for a `.did` file during the build process.
*
* ## Installation
*
* ```bash
* npm install -D @icp-sdk/bindgen
* ```
*
* ## Usage
*
* Suppose you have a `./canisters/hello_world.did` file, and you want to output the generated bindings for your Vite app in the `src/bindings/` folder.
* Here's how the plugin configuration would look like:
*
* ```ts title="vite.config.ts"
* import { defineConfig } from "vite";
* import { icpBindgen } from '@icp-sdk/bindgen/plugins/vite';
*
* export default defineConfig({
* plugins: [
* // ... other plugins
* icpBindgen({
* didFile: './canisters/hello_world.did',
* outDir: './src/bindings',
* }),
* ],
* });
* ```
*
* For an explanation of the generated files, see the [Bindings Structure](https://js.icp.build/bindgen/latest/structure/) page.
*
* @module plugins/vite
*/
import { resolve } from 'node:path';
import type { Plugin, ViteDevServer } from 'vite';
import {
type GenerateOptions,
type GenerateOutputOptions,
generate,
} from '../core/generate/index.ts';
import { VITE_PLUGIN_NAME } from './utils/constants.ts';
import { cyan, green } from './utils/log.ts';
/**
* Options for the Vite plugin.
*/
export interface Options extends Omit<GenerateOptions, 'output'> {
/**
* Options for controlling the generated output files.
*/
output?: Omit<GenerateOutputOptions, 'force'>;
/**
* Disables watching for changes in the `.did` file when using the dev server.
*
* @default false
*/
disableWatch?: boolean;
}
/**
* Vite plugin to generate bindings for a `.did` file during the build process.
*
* The plugin also watches the `.did` file in dev mode and regenerates the bindings on change.
* You can disable this behavior by setting `disableWatch` to `true`.
*
* For more info, see the [docs](https://js.icp.build/bindgen/latest/plugins/vite).
*
* @example
*
* Suppose we have a `.did` file in `./canisters/hello_world.did` and we want to generate bindings in `./src/bindings`.
*
* ```ts
* // vite.config.ts
* import { defineConfig } from 'vite';
* import { icpBindgen } from '@icp-sdk/bindgen/plugins/vite';
*
* export default defineConfig({
* plugins: [
* // ... other plugins
* icpBindgen({
* didFile: './canisters/hello_world.did',
* outDir: './src/bindings',
* }),
* ],
* });
* ```
*
* @ignore
*/
export function icpBindgen(options: Options): Plugin {
return {
name: VITE_PLUGIN_NAME,
async buildStart() {
await run(options);
},
configureServer(server) {
if (!options.disableWatch) {
watchDidFileChanges(server, options);
}
},
sharedDuringBuild: true,
};
}
function watchDidFileChanges(server: ViteDevServer, options: Options) {
if (!options.didFile) {
return;
}
const didFilePath = resolve(options.didFile);
server.watcher.add(didFilePath);
server.watcher.on('change', async (changedPath) => {
if (resolve(changedPath) === resolve(didFilePath)) {
await run(options);
}
});
}
async function run(options: Options) {
const source = options.didFile || options.didRemoteUrl || 'unknown source';
console.log(cyan(`[${VITE_PLUGIN_NAME}] Generating bindings from`), green(source));
await generate({
didFile: options.didFile,
outDir: options.outDir,
output: {
...options.output,
// We want to overwrite existing files in the build process
force: true,
},
});
console.log(cyan(`[${VITE_PLUGIN_NAME}] Bindings generated at`), green(options.outDir));
}