0
# karma-babel-preprocessor
1
2
karma-babel-preprocessor is a Karma plugin that provides on-the-fly ES6/ES2015+ JavaScript compilation using Babel during test execution. It enables developers to write modern JavaScript syntax in their test files and source code while maintaining compatibility with various module systems and testing environments.
3
4
## Package Information
5
6
- **Package Name**: karma-babel-preprocessor
7
- **Package Type**: npm
8
- **Language**: JavaScript
9
- **Installation**: `npm install karma-babel-preprocessor @babel/core @babel/preset-env --save-dev`
10
- **Peer Dependencies**: @babel/core v7
11
12
## Core Imports
13
14
The package is automatically loaded by Karma when installed. No direct imports are needed in test files.
15
16
Karma configuration:
17
18
```javascript
19
module.exports = function (config) {
20
config.set({
21
preprocessors: {
22
'src/**/*.js': ['babel'],
23
'test/**/*.js': ['babel']
24
}
25
});
26
};
27
```
28
29
## Basic Usage
30
31
```javascript
32
// karma.conf.js
33
module.exports = function (config) {
34
config.set({
35
frameworks: ['jasmine'],
36
37
files: [
38
'src/**/*.js',
39
'test/**/*.spec.js'
40
],
41
42
preprocessors: {
43
'src/**/*.js': ['babel'],
44
'test/**/*.spec.js': ['babel']
45
},
46
47
babelPreprocessor: {
48
options: {
49
presets: ['@babel/preset-env'],
50
sourceMap: 'inline'
51
}
52
},
53
54
browsers: ['Chrome']
55
});
56
};
57
```
58
59
## Architecture
60
61
karma-babel-preprocessor follows Karma's plugin architecture pattern with these key components:
62
63
- **Plugin Registration**: Exports a factory function registered as `preprocessor:babel` in Karma's plugin system
64
- **Dependency Injection**: Uses Karma's DI pattern to receive configuration, logging, and helper services
65
- **Processing Pipeline**: Integrates into Karma's file preprocessing pipeline, transforming files before test execution
66
- **Configuration Merging**: Hierarchical configuration system supporting base config, custom config, and per-file functions
67
- **Error Handling**: Graceful error handling with detailed logging and callback-based error reporting
68
69
The plugin acts as a bridge between Karma's preprocessing system and Babel's transformation engine, handling configuration merging and error management.
70
71
## Capabilities
72
73
### Babel Preprocessor Registration
74
75
The package registers a Karma preprocessor plugin that integrates with Karma's preprocessing pipeline.
76
77
```javascript { .api }
78
/**
79
* Main module export that registers the babel preprocessor with Karma
80
*/
81
module.exports = {
82
'preprocessor:babel': ['factory', createPreprocessor]
83
};
84
```
85
86
### Preprocessor Factory Function
87
88
Creates a Babel preprocessor instance with dependency injection.
89
90
```javascript { .api }
91
/**
92
* Factory function that creates a babel preprocessor instance
93
* @param {Object} args - Config object of custom preprocessor
94
* @param {Object} config - Config object of babelPreprocessor
95
* @param {Object} logger - Karma's logger instance
96
* @param {Object} helper - Karma's helper functions
97
* @returns {Function} Preprocessor function for processing files
98
*/
99
function createPreprocessor(args, config, logger, helper): Function;
100
```
101
102
The dependency injection configuration:
103
104
```javascript { .api }
105
createPreprocessor.$inject = [
106
'args',
107
'config.babelPreprocessor',
108
'logger',
109
'helper'
110
];
111
```
112
113
### File Processing Function
114
115
The core preprocessing function that transforms JavaScript files using Babel.
116
117
```javascript { .api }
118
/**
119
* Processes a JavaScript file through Babel transformation
120
* @param {string} content - File content to process
121
* @param {Object} file - Karma file object with originalPath and path properties
122
* @param {Function} done - Callback function (error, result)
123
* @returns {void} Calls done callback with transformed code or error
124
*/
125
function preprocess(content, file, done): void;
126
```
127
128
The file object structure:
129
130
```javascript { .api }
131
interface KarmaFile {
132
/** Original file path */
133
originalPath: string;
134
/** Current file path (may be modified by preprocessor) */
135
path: string;
136
}
137
```
138
139
### Configuration Options Merger
140
141
Merges base and custom configuration options for Babel transformation.
142
143
```javascript { .api }
144
/**
145
* Merges configuration options for Babel transformation
146
* @param {Object} customConfig - Custom preprocessor config
147
* @param {Object} baseConfig - Base babelPreprocessor config
148
* @param {Object} helper - Karma helper functions
149
* @param {Object} file - File being processed
150
* @returns {Object} Merged Babel options
151
*/
152
function createOptions(customConfig, baseConfig, helper, file): Object;
153
```
154
155
### Per-File Options Processor
156
157
Processes function-based configuration options for per-file customization.
158
159
```javascript { .api }
160
/**
161
* Processes function-based configuration options for per-file customization
162
* @param {Object} config - Configuration object
163
* @param {Object} helper - Karma helper functions
164
* @param {Object} file - File being processed
165
* @returns {Object} Per-file options object
166
*/
167
function createPerFileOptions(config, helper, file): Object;
168
```
169
170
## Configuration
171
172
### Standard Configuration
173
174
Configure the preprocessor in your Karma configuration file:
175
176
```javascript
177
module.exports = function (config) {
178
config.set({
179
preprocessors: {
180
'src/**/*.js': ['babel'],
181
'test/**/*.js': ['babel']
182
},
183
184
babelPreprocessor: {
185
options: {
186
presets: ['@babel/preset-env'],
187
plugins: ['@babel/plugin-transform-runtime'],
188
sourceMap: 'inline'
189
}
190
}
191
});
192
};
193
```
194
195
### Per-File Function Configuration
196
197
Use functions for dynamic per-file configuration:
198
199
```javascript
200
module.exports = function (config) {
201
config.set({
202
babelPreprocessor: {
203
options: {
204
presets: ['@babel/preset-env']
205
},
206
filename: function (file) {
207
return file.originalPath.replace(/\.js$/, '.es5.js');
208
},
209
sourceFileName: function (file) {
210
return file.originalPath;
211
}
212
}
213
});
214
};
215
```
216
217
### Custom Preprocessor Configuration
218
219
Create named custom preprocessors extending the babel preprocessor:
220
221
```javascript
222
module.exports = function (config) {
223
config.set({
224
preprocessors: {
225
'src/**/*.js': ['babelSourceMap'],
226
'test/**/*.js': ['babelTypeScript']
227
},
228
229
customPreprocessors: {
230
babelSourceMap: {
231
base: 'babel',
232
options: {
233
presets: ['@babel/preset-env'],
234
sourceMap: 'inline'
235
}
236
},
237
babelTypeScript: {
238
base: 'babel',
239
options: {
240
presets: ['@babel/preset-env', '@babel/preset-typescript']
241
},
242
filename: function (file) {
243
return file.originalPath.replace(/\.ts$/, '.js');
244
}
245
}
246
}
247
});
248
};
249
```
250
251
## Configuration Options
252
253
### Standard Babel Options
254
255
All standard Babel options are supported through the `options` property:
256
257
```javascript { .api }
258
interface BabelOptions {
259
/** Array of Babel presets to apply */
260
presets?: string[] | Array<[string, object]>;
261
/** Array of Babel plugins to apply */
262
plugins?: string[] | Array<[string, object]>;
263
/** Source map generation ('inline', true, false, or object) */
264
sourceMap?: boolean | 'inline' | 'both' | 'hidden' | object;
265
/** Output filename for the transformed code */
266
filename?: string;
267
/** Source filename for source maps */
268
sourceFileName?: string;
269
/** Additional Babel transformation options */
270
[key: string]: any;
271
}
272
```
273
274
### Per-File Function Options
275
276
Configuration options that accept functions for per-file customization:
277
278
```javascript { .api }
279
interface PerFileOptions {
280
/** Function to determine output filename per file */
281
filename?: (file: KarmaFile) => string;
282
/** Function to determine source filename per file */
283
sourceFileName?: (file: KarmaFile) => string;
284
/** Any other Babel option as a function */
285
[optionName: string]: (file: KarmaFile) => any;
286
}
287
```
288
289
### Configuration Structure
290
291
The complete configuration structure:
292
293
```javascript { .api }
294
interface BabelPreprocessorConfig {
295
/** Standard Babel options object */
296
options?: BabelOptions;
297
/** Per-file function-based options */
298
[key: string]: ((file: KarmaFile) => any) | BabelOptions;
299
}
300
301
interface CustomPreprocessorConfig extends BabelPreprocessorConfig {
302
/** Must be 'babel' to extend babel preprocessor */
303
base: 'babel';
304
}
305
```
306
307
## Error Handling
308
309
The preprocessor handles Babel transformation errors gracefully:
310
311
- Catches all Babel transformation errors
312
- Logs errors with file path context using Karma's logger
313
- Returns errors through the callback mechanism
314
- Validates per-file function configuration and throws descriptive errors
315
316
Common error scenarios:
317
318
```javascript
319
// Per-file option validation error
320
throw new Error('Per-file option "filename" must be a function.');
321
322
// Babel transformation errors are caught and logged:
323
log.error('%s\n at %s', e.message, file.originalPath);
324
```
325
326
## Integration Notes
327
328
### Karma Plugin System
329
330
The package integrates with Karma's plugin architecture:
331
332
- Automatically discovered when installed (name starts with `karma-`)
333
- Uses dependency injection pattern for configuration and services
334
- Registers as `preprocessor:babel` in Karma's plugin registry
335
336
### Module System Compatibility
337
338
The preprocessor works with various module systems by transforming ES6 modules to:
339
- CommonJS (default)
340
- AMD
341
- SystemJS
342
- UMD
343
344
Configure module transformation via Babel presets and plugins.
345
346
### Polyfill Support
347
348
For polyfill support, include them in Karma's files configuration:
349
350
```javascript
351
module.exports = function (config) {
352
config.set({
353
files: [
354
'node_modules/@babel/polyfill/dist/polyfill.js',
355
'src/**/*.js',
356
'test/**/*.js'
357
]
358
});
359
};
360
```