33/** @import { PluginAPI } from '../types/plugin-api.js' */
44/** @import { StatCollection } from '../types/vite-plugin-svelte-stats.js' */
55/** @import { CompileOptions } from 'svelte/compiler' */
6- /** @import { Plugin, ResolvedConfig, Rollup , UserConfig } from 'vite' */
6+ /** @import { Plugin, ResolvedConfig, Rolldown , UserConfig } from 'vite' */
77
88import fs from 'node:fs/promises' ;
99import path from 'node:path' ;
1010import * as svelte from 'svelte/compiler' ;
1111import { log } from '../utils/log.js' ;
1212import { toRollupError } from '../utils/error.js' ;
13+ import { SVELTE_IMPORTS } from '../utils/constants.js' ;
14+ import { isDepExcluded } from 'vitefu' ;
1315
1416/**
15- * @typedef {NonNullable<Rollup .Plugin> } RollupPlugin
17+ * @typedef {NonNullable<Rolldown .Plugin> } RollupPlugin
1618 */
1719
1820const optimizeSveltePluginName = 'vite-plugin-svelte:optimize' ;
@@ -29,36 +31,31 @@ export function setupOptimizer(api) {
2931 return {
3032 name : 'vite-plugin-svelte:setup-optimizer' ,
3133 apply : 'serve' ,
32- config ( ) {
34+ configEnvironment ( name , config ) {
35+ // fall back to vite behavior when consumer isn't set
36+ const consumer = ( config . consumer ?? name === 'client' ) ? 'client' : 'server' ;
3337 /** @type {UserConfig['optimizeDeps'] } */
3438 const optimizeDeps = {
3539 // Experimental Vite API to allow these extensions to be scanned and prebundled
3640 extensions : [ '.svelte' ]
3741 } ;
38- // Add optimizer plugins to prebundle Svelte files.
39- // Currently, a placeholder as more information is needed after Vite config is resolved,
40- // the added plugins are patched in configResolved below
4142
43+ // Add optimizer plugins to prebundle Svelte files.
4244 optimizeDeps . rolldownOptions = {
4345 plugins : [
44- placeholderRolldownOptimizerPlugin ( optimizeSveltePluginName ) ,
45- placeholderRolldownOptimizerPlugin ( optimizeSvelteModulePluginName )
46+ rolldownOptimizerPlugin ( api , consumer , true ) ,
47+ rolldownOptimizerPlugin ( api , consumer , false )
4648 ]
4749 } ;
4850
51+ if ( consumer === 'server' && ! isDepExcluded ( 'svelte' , config . optimizeDeps ?. exclude ?? [ ] ) ) {
52+ optimizeDeps . include = [ ...SVELTE_IMPORTS ] ;
53+ }
54+
4955 return { optimizeDeps } ;
5056 } ,
5157 configResolved ( c ) {
5258 viteConfig = c ;
53- const optimizeDeps = c . optimizeDeps ;
54- const plugins =
55- // @ts -expect-error not typed
56- optimizeDeps . rolldownOptions ?. plugins ?. filter ( ( p ) =>
57- [ optimizeSveltePluginName , optimizeSvelteModulePluginName ] . includes ( p . name )
58- ) ?? [ ] ;
59- for ( const plugin of plugins ) {
60- patchRolldownOptimizerPlugin ( plugin , api . options ) ;
61- }
6259 } ,
6360 async buildStart ( ) {
6461 if ( ! api . options . prebundleSvelteLibraries ) return ;
@@ -73,21 +70,29 @@ export function setupOptimizer(api) {
7370}
7471
7572/**
76- * @param {RollupPlugin } plugin
77- * @param {ResolvedOptions } options
73+ * @param {import('../types/plugin-api.d.ts').PluginAPI } api
74+ * @param {'server'|'client' } consumer
75+ * @param {boolean } components
76+ * @return {Rolldown.Plugin }
7877 */
79- function patchRolldownOptimizerPlugin ( plugin , options ) {
80- const components = plugin . name === optimizeSveltePluginName ;
78+ function rolldownOptimizerPlugin ( api , consumer , components ) {
79+ const name = components ? optimizeSveltePluginName : optimizeSvelteModulePluginName ;
8180 const compileFn = components ? compileSvelte : compileSvelteModule ;
8281 const statsName = components ? 'prebundle library components' : 'prebundle library modules' ;
8382 const includeRe = components ? / ^ [ ^ ? # ] + \. s v e l t e (?: [ ? # ] | $ ) / : / ^ [ ^ ? # ] + \. s v e l t e \. [ j t ] s (?: [ ? # ] | $ ) / ;
83+ const generate = consumer === 'server' ? 'server' : 'client' ;
8484 /** @type {StatCollection | undefined } */
8585 let statsCollection ;
8686
87+ /**@type {Rolldown.Plugin }*/
88+ const plugin = {
89+ name
90+ } ;
91+
8792 plugin . options = ( opts ) => {
8893 // @ts -expect-error plugins is an array here
8994 const isScanner = opts . plugins . some (
90- ( /** @type {{ name: string; } } */ p ) => p . name === 'vite:dep-scan:resolve'
95+ ( /** @type {{ name: string; } | undefined } */ p ) => p ? .name === 'vite:dep-scan:resolve'
9196 ) ;
9297 if ( isScanner ) {
9398 delete plugin . buildStart ;
@@ -102,14 +107,14 @@ function patchRolldownOptimizerPlugin(plugin, options) {
102107 */
103108 async handler ( code , filename ) {
104109 try {
105- return await compileFn ( options , { filename, code } , statsCollection ) ;
110+ return await compileFn ( api . options , { filename, code } , generate , statsCollection ) ;
106111 } catch ( e ) {
107- throw toRollupError ( e , options ) ;
112+ throw toRollupError ( e , api . options ) ;
108113 }
109114 }
110115 } ;
111116 plugin . buildStart = ( ) => {
112- statsCollection = options . stats ?. startCollection ( statsName , {
117+ statsCollection = api . options . stats ?. startCollection ( statsName , {
113118 logResult : ( c ) => c . stats . length > 1
114119 } ) ;
115120 } ;
@@ -118,15 +123,18 @@ function patchRolldownOptimizerPlugin(plugin, options) {
118123 } ;
119124 }
120125 } ;
126+
127+ return plugin ;
121128}
122129
123130/**
124131 * @param {ResolvedOptions } options
125132 * @param {{ filename: string, code: string } } input
133+ * @param {'client'|'server' } generate
126134 * @param {StatCollection } [statsCollection]
127135 * @returns {Promise<Code> }
128136 */
129- async function compileSvelte ( options , { filename, code } , statsCollection ) {
137+ async function compileSvelte ( options , { filename, code } , generate , statsCollection ) {
130138 let css = options . compilerOptions . css ;
131139 if ( css !== 'injected' ) {
132140 // TODO ideally we'd be able to externalize prebundled styles too, but for now always put them in the js
@@ -138,7 +146,7 @@ async function compileSvelte(options, { filename, code }, statsCollection) {
138146 ...options . compilerOptions ,
139147 css,
140148 filename,
141- generate : 'client'
149+ generate
142150 } ;
143151
144152 let preprocessed ;
@@ -189,15 +197,16 @@ async function compileSvelte(options, { filename, code }, statsCollection) {
189197/**
190198 * @param {ResolvedOptions } options
191199 * @param {{ filename: string; code: string } } input
200+ * @param {'client'|'server' } generate
192201 * @param {StatCollection } [statsCollection]
193202 * @returns {Promise<Code> }
194203 */
195- async function compileSvelteModule ( options , { filename, code } , statsCollection ) {
204+ async function compileSvelteModule ( options , { filename, code } , generate , statsCollection ) {
196205 const endStat = statsCollection ?. start ( filename ) ;
197206 const compiled = svelte . compileModule ( code , {
198207 dev : options . compilerOptions ?. dev ?? true , // default to dev: true because prebundling is only used in dev
199208 filename,
200- generate : 'client'
209+ generate
201210 } ) ;
202211 if ( endStat ) {
203212 endStat ( ) ;
@@ -247,21 +256,6 @@ async function svelteMetadataChanged(cacheDir, options) {
247256 return currentSvelteMetadata !== existingSvelteMetadata ;
248257}
249258
250- /**
251- *
252- * @param {string } name
253- * @returns {Rollup.Plugin }
254- */
255- function placeholderRolldownOptimizerPlugin ( name ) {
256- return {
257- name,
258- options ( ) { } ,
259- buildStart ( ) { } ,
260- buildEnd ( ) { } ,
261- transform : { filter : { id : / ^ $ / } , handler ( ) { } }
262- } ;
263- }
264-
265259/**
266260 * @param {ResolvedOptions } options
267261 * @returns {Partial<ResolvedOptions> }
0 commit comments