11import path from 'path' ;
22import { fileURLToPath } from 'url' ;
33import { execSync } from 'child_process' ;
4- import { defineConfig , loadEnv , ConfigEnv , LibraryFormats } from 'vite' ;
5- import type { PreRenderedAsset } from 'rollup' ;
4+ import {
5+ defineConfig ,
6+ loadEnv ,
7+ ConfigEnv ,
8+ BuildEnvironmentOptions ,
9+ } from 'vite' ;
10+ import type { InputOption , PreRenderedAsset } from 'rollup' ;
611import react from '@vitejs/plugin-react-swc' ;
712import checker from 'vite-plugin-checker' ;
813import { nodePolyfills } from 'vite-plugin-node-polyfills' ;
@@ -12,10 +17,11 @@ import packageJson from './package.json';
1217
1318const __filename = fileURLToPath ( import . meta. url ) ;
1419const __dirname = path . dirname ( __filename ) ;
15-
1620const { version } = packageJson ;
21+ const isAnalyze = process . env . ANALYZE === 'true' ;
1722
1823let gitHash = 'unknown' ;
24+
1925try {
2026 gitHash = execSync ( 'git log -1 --format=%H' ) . toString ( ) . replace ( '\n' , '' ) ;
2127} catch ( e ) {
@@ -27,11 +33,6 @@ console.info(
2733 `\nBuilding Wormhole Connect version=${ version } hash=${ gitHash } \n` ,
2834) ;
2935
30- // There are three configs this file can return.
31- // 1. local dev server
32- // 2. production build, for direct import
33- // 3. production build, hosted by unpkg.com (includes React, auto-binds to DOM)
34-
3536// TODO: consider using the "VITE_APP_" prefix which is the default for Vite
3637const envPrefix = 'REACT_APP_' ;
3738
@@ -65,12 +66,8 @@ const resolve = {
6566} ;
6667
6768const plugins = [
68- checker ( {
69- typescript : true ,
70- } ) ,
71- dts ( {
72- insertTypesEntry : true ,
73- } ) ,
69+ checker ( { typescript : true } ) ,
70+ dts ( { insertTypesEntry : true } ) ,
7471 react ( ) ,
7572 nodePolyfills ( {
7673 include : [
@@ -97,135 +94,148 @@ const plugins = [
9794 } ) ,
9895] . filter ( Boolean ) ;
9996
100- const optimizeDeps = { } ;
97+ function assetFileNames ( assetInfo : PreRenderedAsset ) {
98+ if ( assetInfo . name === 'main.css' ) {
99+ return '[name][extname]' ;
100+ }
101101
102- const output : {
103- assetFileNames : ( assetInfo : PreRenderedAsset ) => string ;
104- inlineDynamicImports : boolean ;
105- exports : 'named' | 'default' | 'none' | 'auto' ;
106- } = {
107- assetFileNames : ( assetInfo : PreRenderedAsset ) => {
108- if ( assetInfo . name === 'main.css' ) {
109- return '[name][extname]' ;
110- }
111- return '[name]-[hash][extname]' ;
102+ return '[name]-[hash][extname]' ;
103+ }
104+
105+ // Netlify and local dev server
106+ const sampleAppBuild : BuildEnvironmentOptions = {
107+ outDir : './build' ,
108+ rollupOptions : {
109+ input : {
110+ main : 'src/SampleApp.tsx' ,
111+ index : 'index.html' ,
112+ } as Record < string , string > ,
113+ output : {
114+ assetFileNames,
115+ inlineDynamicImports : false ,
116+ exports : 'named' as const ,
117+ } ,
118+ } ,
119+ } ;
120+
121+ // Legacy production build, hosted by unpkg.com (includes React, auto-binds to DOM)
122+ const hostedBuild : BuildEnvironmentOptions = {
123+ outDir : './dist' ,
124+ rollupOptions : {
125+ input : {
126+ main : 'src/main.tsx' ,
127+ } as Record < string , string > ,
128+ output : {
129+ entryFileNames : '[name].mjs' ,
130+ assetFileNames,
131+ inlineDynamicImports : false ,
132+ exports : 'named' as const ,
133+ } ,
134+ } ,
135+ } ;
136+
137+ const libEntry : InputOption = [
138+ path . resolve ( __dirname , 'src/exports/index.ts' ) ,
139+ path . resolve ( __dirname , 'src/exports/mayan.ts' ) ,
140+ path . resolve ( __dirname , 'src/exports/ntt.ts' ) ,
141+ path . resolve ( __dirname , 'src/exports/hosted.ts' ) ,
142+ path . resolve ( __dirname , 'src/exports/executor.ts' ) ,
143+ ] ;
144+
145+ const rollupInput : InputOption = {
146+ index : 'src/exports/index.ts' ,
147+ mayan : 'src/exports/mayan.ts' ,
148+ ntt : 'src/exports/ntt.ts' ,
149+ hosted : 'src/exports/hosted.ts' ,
150+ executor : 'src/exports/executor.ts' ,
151+ } ;
152+
153+ const external = [
154+ 'react' ,
155+ 'react/jsx-runtime' ,
156+ '@emotion/react' ,
157+ '@emotion/styled' ,
158+ '@mui/material' ,
159+ '@mui/icons-material' ,
160+ '@mui/styled-engine' ,
161+ '@mui/system' ,
162+ ] ;
163+
164+ // Production build, for npm import
165+ const libBuild : BuildEnvironmentOptions = {
166+ outDir : './lib' ,
167+ lib : {
168+ entry : libEntry ,
169+ formats : isAnalyze ? [ 'es' ] : [ 'es' , 'cjs' ] ,
170+ fileName : ( format , entryname ) => {
171+ const n = entryname . split ( '/' ) . pop ( ) ! ;
172+ return `${ n . split ( '.' ) [ 0 ] } .${ format === 'es' ? 'mjs' : 'js' } ` ;
173+ } ,
174+ } ,
175+ rollupOptions : {
176+ input : rollupInput ,
177+ output : {
178+ assetFileNames,
179+ inlineDynamicImports : false ,
180+ exports : 'named' as const ,
181+ } ,
182+ external,
183+ } ,
184+ } ;
185+
186+ // Minimal build, for submodule import
187+ const minimalBuild : BuildEnvironmentOptions = {
188+ sourcemap : true ,
189+ minify : false ,
190+ outDir : './lib' ,
191+ lib : {
192+ entry : libEntry ,
193+ formats : [ 'es' ] ,
194+ } ,
195+ rollupOptions : {
196+ input : rollupInput ,
197+ output : {
198+ entryFileNames : '[name].mjs' ,
199+ chunkFileNames : '[name].mjs' ,
200+ assetFileNames : '[name].[ext]' ,
201+ inlineDynamicImports : false ,
202+ preserveModules : true ,
203+ preserveModulesRoot : 'src' ,
204+ } ,
205+ external,
206+ } ,
207+ terserOptions : {
208+ mangle : false ,
209+ compress : false ,
112210 } ,
113- inlineDynamicImports : false ,
114- exports : 'named' as const ,
115211} ;
116212
117213export default defineConfig ( ( { command, mode } : ConfigEnv ) => {
118214 const env = loadEnv ( mode , process . cwd ( ) , '' ) ;
119215 const isHosted = ! ! env . VITE_BUILD_HOSTED ;
120216 const isNetlify = ! ! env . VITE_BUILD_NETLIFY ;
121- const isAnalyze = process . env . ANALYZE === 'true' ;
122-
123- if ( command === 'serve' || ( command === 'build' && isNetlify ) ) {
124- // Local development
125- return {
126- define,
127- envPrefix,
128- resolve,
129- build : {
130- outDir : './build' ,
131- rollupOptions : {
132- input : {
133- main : 'src/SampleApp.tsx' ,
134- index : 'index.html' ,
135- } as Record < string , string > ,
136- output,
137- } ,
138- } ,
139- plugins,
140- optimizeDeps,
141- } ;
142- } else if ( command === 'build' ) {
143- //
144- // Building for production
145- // There are two possible configs here: invoked by "npm run build" and "npm run build:hosted"
146- //
147- // - by default, we build a component library that can be imported and used in React apps
148- //
149- // - alternatively, VITE_BUILD_HOSTED=1 causes Vite to build a bundle that is used
150- // via unpkg.com hosting. This build looks for a DOM element #wormhole-connect and comes
151- // bundled with a copy of React. This is "legacy mode" and useful only on web apps that don't
152- // use React.
153- //
217+ const isMinimal = ! ! env . VITE_BUILD_MINIMAL ;
218+ const isSampleApp = command === 'serve' || ( command === 'build' && isNetlify ) ;
154219
220+ let build : BuildEnvironmentOptions | undefined = undefined ;
221+
222+ if ( isSampleApp ) {
223+ build = sampleAppBuild ;
224+ } else if ( command === 'build' ) {
155225 if ( isHosted ) {
156- return {
157- define,
158- envPrefix,
159- resolve,
160- build : {
161- outDir : './dist' ,
162- rollupOptions : {
163- input : {
164- main : 'src/main.tsx' ,
165- } as Record < string , string > ,
166- output : {
167- entryFileNames : '[name].js' ,
168- ...output ,
169- } ,
170- } ,
171- } ,
172- plugins,
173- optimizeDeps,
174- } ;
226+ build = hostedBuild ;
227+ } else if ( isMinimal ) {
228+ build = minimalBuild ;
175229 } else {
176- return {
177- define,
178- envPrefix,
179- resolve,
180- build : {
181- outDir : './lib' ,
182- lib : {
183- entry : [
184- path . resolve ( __dirname , 'src/exports/index.ts' ) ,
185- path . resolve ( __dirname , 'src/exports/mayan.ts' ) ,
186- path . resolve ( __dirname , 'src/exports/ntt.ts' ) ,
187- path . resolve ( __dirname , 'src/exports/hosted.ts' ) ,
188- path . resolve ( __dirname , 'src/exports/executor.ts' ) ,
189- ] ,
190- formats : ( isAnalyze ? [ 'es' ] : [ 'es' , 'cjs' ] ) as LibraryFormats [ ] ,
191- fileName : ( format , entryname ) => {
192- const n = entryname . split ( '/' ) . pop ( ) ! ;
193- return `${ n . split ( '.' ) [ 0 ] } .${ format === 'es' ? 'mjs' : 'js' } ` ;
194- } ,
195- } ,
196- rollupOptions : {
197- input : {
198- index : 'src/exports/index.ts' ,
199- mayan : 'src/exports/mayan.ts' ,
200- ntt : 'src/exports/ntt.ts' ,
201- hosted : 'src/exports/hosted.ts' ,
202- executor : 'src/exports/executor.ts' ,
203- } ,
204- output,
205- external : [
206- 'react' ,
207- 'react/jsx-runtime' ,
208- '@emotion/react' ,
209- '@emotion/styled' ,
210- '@mui/material' ,
211- '@mui/icons-material' ,
212- '@mui/styled-engine' ,
213- '@mui/system' ,
214- ] ,
215- } ,
216- } ,
217- plugins,
218- optimizeDeps,
219- } ;
230+ build = libBuild ;
220231 }
221232 }
222233
223- // Default configuration if no conditions are met
224234 return {
235+ build,
225236 define,
226237 envPrefix,
227238 resolve,
228239 plugins,
229- optimizeDeps,
230240 } ;
231241} ) ;
0 commit comments