or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

build-system.mdconfiguration.mdcss-processing.mddev-server.mdhmr.mdindex.mdmodule-resolution.mdplugin-system.mdssr.mdutilities.md

plugin-system.mddocs/

0

# Plugin System

1

2

Vite's plugin system provides extensible architecture compatible with Rollup plugins. It supports hooks for all phases of development and build processes, with environment-specific plugin capabilities and comprehensive lifecycle management.

3

4

## Capabilities

5

6

### Plugin Interface

7

8

Core plugin interface extending Rollup plugins with Vite-specific hooks.

9

10

```typescript { .api }

11

interface Plugin extends RollupPlugin {

12

/** Plugin name (required) */

13

name: string;

14

/** Plugin enforcement order */

15

enforce?: 'pre' | 'post';

16

/** When to apply plugin */

17

apply?: 'build' | 'serve' | ((config: UserConfig, env: ConfigEnv) => boolean);

18

/** Config modification hook */

19

config?: (config: UserConfig, env: ConfigEnv) => void | UserConfig | Promise<void | UserConfig>;

20

/** Config resolved hook */

21

configResolved?: (config: ResolvedConfig) => void | Promise<void>;

22

/** Configure server hook */

23

configureServer?: (server: ViteDevServer) => void | Promise<void>;

24

/** Configure preview server hook */

25

configurePreviewServer?: (server: PreviewServer) => void | Promise<void>;

26

/** Build start hook */

27

buildStart?: (opts: InputOptions) => void | Promise<void>;

28

/** Build end hook */

29

buildEnd?: (err?: Error) => void | Promise<void>;

30

/** Write bundle hook */

31

writeBundle?: (options: OutputOptions, bundle: OutputBundle) => void | Promise<void>;

32

/** Close bundle hook */

33

closeBundle?: () => void | Promise<void>;

34

/** Generate bundle hook */

35

generateBundle?: (options: OutputOptions, bundle: OutputBundle) => void | Promise<void>;

36

/** Render chunk hook */

37

renderChunk?: (code: string, chunk: RenderedChunk, options: OutputOptions) => string | { code: string; map?: SourceMapInput } | null | Promise<string | { code: string; map?: SourceMapInput } | null>;

38

/** Transform hook */

39

transform?: (code: string, id: string) => string | { code: string; map?: SourceMapInput } | null | Promise<string | { code: string; map?: SourceMapInput } | null>;

40

/** Load hook */

41

load?: (id: string) => string | { code: string; map?: SourceMapInput } | null | Promise<string | { code: string; map?: SourceMapInput } | null>;

42

/** Resolve ID hook */

43

resolveId?: (id: string, importer?: string, options?: { custom?: any; isEntry: boolean }) => string | { id: string; external?: boolean } | null | Promise<string | { id: string; external?: boolean } | null>;

44

/** Handle HMR update */

45

handleHotUpdate?: (ctx: HmrContext) => Array<ModuleNode> | void | Promise<Array<ModuleNode> | void>;

46

}

47

48

type PluginOption = Plugin | false | null | undefined | PluginOption[];

49

50

/**

51

* Plugin hook handler with context

52

*/

53

interface HookHandler<T, O> {

54

handler: T;

55

order?: 'pre' | 'post' | null;

56

once?: boolean;

57

}

58

```

59

60

**Usage Examples:**

61

62

```typescript

63

import type { Plugin } from "vite";

64

65

// Basic plugin

66

function myPlugin(): Plugin {

67

return {

68

name: 'my-plugin',

69

config(config, { command }) {

70

if (command === 'serve') {

71

config.define = config.define || {};

72

config.define.__DEV__ = true;

73

}

74

},

75

configureServer(server) {

76

server.middlewares.use('/api', myApiHandler);

77

}

78

};

79

}

80

81

// Plugin with options

82

interface MyPluginOptions {

83

prefix?: string;

84

debug?: boolean;

85

}

86

87

function myPluginWithOptions(options: MyPluginOptions = {}): Plugin {

88

return {

89

name: 'my-plugin-with-options',

90

enforce: 'pre',

91

apply: 'build',

92

transform(code, id) {

93

if (options.debug) {

94

console.log(`Transforming: ${id}`);

95

}

96

return options.prefix ? `${options.prefix}\n${code}` : code;

97

}

98

};

99

}

100

```

101

102

### Per-Environment Plugin

103

104

Create environment-specific plugins that can behave differently across environments.

105

106

```typescript { .api }

107

/**

108

* Create environment-specific plugin

109

* @param name - Plugin name

110

* @param factory - Factory function returning environment-specific plugin

111

* @returns Plugin that adapts to different environments

112

*/

113

function perEnvironmentPlugin(

114

name: string,

115

factory: (environment: Environment) => Plugin

116

): Plugin;

117

```

118

119

### Plugin Context

120

121

Context objects available to plugin hooks for accessing Vite functionality.

122

123

```typescript { .api }

124

interface ConfigPluginContext {

125

/** Add watch files */

126

addWatchFile(file: string): void;

127

/** Get watch files */

128

getWatchFiles(): string[];

129

}

130

131

interface MinimalPluginContextWithoutEnvironment {

132

/** Emit file */

133

emitFile(file: EmittedFile): string;

134

/** Get file name */

135

getFileName(referenceId: string): string;

136

/** Get module info */

137

getModuleInfo(id: string): ModuleInfo | null;

138

/** Get module IDs */

139

getModuleIds(): IterableIterator<string>;

140

/** Parse */

141

parse(input: string, options?: any): any;

142

/** Resolve */

143

resolve(id: string, importer?: string, options?: ResolveOptions): Promise<ResolveIdResult | null>;

144

/** Set asset source */

145

setAssetSource(referenceId: string, source: string | Uint8Array): void;

146

/** Error */

147

error(message: string | RollupError, position?: number | { column: number; line: number }): never;

148

/** Warn */

149

warn(message: string | RollupError, position?: number | { column: number; line: number }): void;

150

}

151

```

152

153

### Plugin Utilities

154

155

Utility interfaces and types for plugin development.

156

157

```typescript { .api }

158

interface PluginHookUtils {

159

/** Get combined transforms */

160

getCombinedSourcemap(): SourceMap;

161

}

162

163

/**

164

* Plugin with required hook constraint

165

*/

166

type PluginWithRequiredHook<K extends keyof Plugin> = Plugin & Required<Pick<Plugin, K>>;

167

168

/**

169

* Falsy plugin type for conditional plugins

170

*/

171

type FalsyPlugin = false | null | undefined;

172

```

173

174

### Plugin Container

175

176

Container that manages and executes plugins during development and build.

177

178

```typescript { .api }

179

interface PluginContainer {

180

/** Build start */

181

buildStart(options: InputOptions): Promise<void>;

182

/** Resolve ID */

183

resolveId(id: string, importer?: string, options?: ResolveOptions): Promise<string | null>;

184

/** Load module */

185

load(id: string, options?: { ssr?: boolean }): Promise<LoadResult | null>;

186

/** Transform code */

187

transform(code: string, id: string, options?: TransformOptions): Promise<TransformResult | null>;

188

/** Close container */

189

close(): Promise<void>;

190

}

191

192

interface SkipInformation {

193

/** Skipped plugin names */

194

skipped: Set<string>;

195

/** Skip reason */

196

reason: string;

197

}

198

```

199

200

## Built-in Plugin Hooks

201

202

### Configuration Hooks

203

204

Hooks for modifying and accessing configuration.

205

206

```typescript { .api }

207

/**

208

* Modify configuration before resolution

209

* @param config - User configuration

210

* @param env - Configuration environment

211

* @returns Modified config or void

212

*/

213

type ConfigHook = (

214

config: UserConfig,

215

env: ConfigEnv

216

) => void | UserConfig | Promise<void | UserConfig>;

217

218

/**

219

* Access resolved configuration

220

* @param config - Resolved configuration

221

*/

222

type ConfigResolvedHook = (config: ResolvedConfig) => void | Promise<void>;

223

```

224

225

### Server Hooks

226

227

Hooks for configuring development and preview servers.

228

229

```typescript { .api }

230

/**

231

* Configure development server

232

* @param server - Vite dev server instance

233

*/

234

type ConfigureServerHook = (server: ViteDevServer) => void | Promise<void>;

235

236

/**

237

* Configure preview server

238

* @param server - Preview server instance

239

*/

240

type ConfigurePreviewServerHook = (server: PreviewServer) => void | Promise<void>;

241

```

242

243

### HMR Hooks

244

245

Hooks for handling Hot Module Replacement.

246

247

```typescript { .api }

248

/**

249

* Handle HMR update

250

* @param ctx - HMR context with file and modules information

251

* @returns Array of modules to update or void

252

*/

253

type HandleHotUpdateHook = (

254

ctx: HmrContext

255

) => Array<ModuleNode> | void | Promise<Array<ModuleNode> | void>;

256

257

interface HmrContext {

258

/** File path that changed */

259

file: string;

260

/** Timestamp of change */

261

timestamp: number;

262

/** Affected modules */

263

modules: Set<ModuleNode>;

264

/** Read file contents */

265

read: () => string | Promise<string>;

266

/** Vite dev server */

267

server: ViteDevServer;

268

}

269

```

270

271

## Plugin Development Patterns

272

273

### Conditional Plugins

274

275

Apply plugins conditionally based on environment or configuration.

276

277

```typescript { .api }

278

// Environment-based application

279

const myPlugin = (): Plugin => ({

280

name: 'my-plugin',

281

apply: 'build', // Only during build

282

// ... plugin implementation

283

});

284

285

// Function-based application

286

const conditionalPlugin = (): Plugin => ({

287

name: 'conditional-plugin',

288

apply: (config, { command, mode }) => {

289

return command === 'build' && mode === 'production';

290

},

291

// ... plugin implementation

292

});

293

```

294

295

### Plugin Ordering

296

297

Control plugin execution order with enforcement.

298

299

```typescript { .api }

300

// Pre-plugins run before Vite's internal plugins

301

const prePlugin = (): Plugin => ({

302

name: 'pre-plugin',

303

enforce: 'pre',

304

// ... runs early

305

});

306

307

// Post-plugins run after Vite's internal plugins

308

const postPlugin = (): Plugin => ({

309

name: 'post-plugin',

310

enforce: 'post',

311

// ... runs late

312

});

313

```