0
# MJML Browser
1
2
MJML Browser is a client-side version of MJML (Mailjet Markup Language) that enables responsive email template generation directly in web browsers. It provides the full MJML compilation engine as a UMD bundle, making it possible to convert MJML markup to responsive HTML without server-side processing.
3
4
## Package Information
5
6
- **Package Name**: mjml-browser
7
- **Package Type**: npm
8
- **Language**: JavaScript
9
- **Installation**: `npm install mjml-browser`
10
11
## Core Imports
12
13
```javascript
14
var mjml2html = require('mjml-browser');
15
```
16
17
UMD/Browser Global:
18
19
```javascript
20
// Available as global 'mjml' when loaded via script tag
21
var result = mjml(mjmlString, options);
22
```
23
24
ES6 (if using with bundler):
25
26
```javascript
27
import mjml2html from 'mjml-browser';
28
```
29
30
## Basic Usage
31
32
```javascript
33
var mjml2html = require('mjml-browser');
34
35
// Simple usage
36
var mjmlMarkup = `
37
<mjml>
38
<mj-body>
39
<mj-section>
40
<mj-column>
41
<mj-text>Hello World!</mj-text>
42
</mj-column>
43
</mj-section>
44
</mj-body>
45
</mjml>
46
`;
47
48
var result = mjml2html(mjmlMarkup);
49
console.log(result.html); // Generated responsive HTML
50
console.log(result.errors); // Validation errors/warnings
51
```
52
53
## Architecture
54
55
MJML Browser is built around several key architectural components that work together to transform MJML markup into responsive HTML:
56
57
- **MJML Parser**: Parses MJML markup string into a structured JSON representation, handling components and attributes
58
- **Component System**: Registry of available MJML components (mj-body, mj-section, mj-text, etc.) with rendering logic
59
- **Validation Engine**: Validates MJML structure and component usage according to MJML rules and dependencies
60
- **Rendering Pipeline**: Processes parsed MJML through component renderers to generate HTML output
61
- **CSS Processing**: Handles CSS inlining, media queries, and responsive breakpoints for email client compatibility
62
- **Browser Compilation**: Webpack bundle that packages the full MJML engine for browser environments with Node.js module mocks
63
64
The browser version maintains the same component architecture as the Node.js version but replaces filesystem operations with mocked implementations, enabling client-side email template generation while preserving full MJML functionality.
65
66
## Capabilities
67
68
### MJML to HTML Conversion
69
70
Core function that converts MJML markup into responsive HTML email templates.
71
72
```javascript { .api }
73
/**
74
* Converts MJML markup to responsive HTML
75
* @param {string|object} mjml - MJML markup string or parsed MJML object
76
* @param {object} [options={}] - Configuration options
77
* @returns {object} Result object with html, json, and errors
78
*/
79
function mjml2html(mjml, options);
80
81
interface MjmlResult {
82
html: string; // Generated responsive HTML
83
json: object; // Parsed MJML object representation
84
errors: Array<ValidationError>; // Validation errors and warnings
85
}
86
87
interface ValidationError {
88
line: number;
89
message: string;
90
tagName: string;
91
formattedMessage: string;
92
}
93
```
94
95
### Configuration Options
96
97
Comprehensive options for customizing MJML compilation behavior.
98
99
```javascript { .api }
100
interface MjmlOptions {
101
/** Format HTML output (deprecated, use external tool) */
102
beautify?: boolean;
103
104
/** Custom font definitions with URLs */
105
fonts?: {
106
[fontName: string]: string;
107
};
108
109
/** Preserve HTML comments in output */
110
keepComments?: boolean;
111
112
/** Minify HTML output (deprecated, use external tool) */
113
minify?: boolean;
114
115
/** HTML minification options when minify is true */
116
minifyOptions?: object;
117
118
/** Ignore mj-include tags (always true in browser) */
119
ignoreIncludes?: boolean;
120
121
/** Options for CSS inlining with juice */
122
juiceOptions?: object;
123
124
/** Tags to preserve during CSS inlining */
125
juicePreserveTags?: {
126
[tagName: string]: any;
127
};
128
129
/** Custom HTML skeleton template function or string path */
130
skeleton?: Function | string;
131
132
/** Validation strictness: 'skip', 'soft', 'strict' */
133
validationLevel?: 'skip' | 'soft' | 'strict';
134
135
/** File path for error reporting */
136
filePath?: string;
137
138
/** Actual file path for includes (not functional in browser) */
139
actualPath?: string;
140
141
/** Suppress MJML v3 migration warnings */
142
noMigrateWarn?: boolean;
143
144
/** Custom preprocessor functions */
145
preprocessors?: Array<Function>;
146
147
/** Component and dependency presets */
148
presets?: Array<{
149
components: object;
150
dependencies: object;
151
}>;
152
153
/** Add printer-friendly styles */
154
printerSupport?: boolean;
155
}
156
```
157
158
### Component System Integration
159
160
Access to MJML's component system for advanced usage.
161
162
```javascript { .api }
163
/** Registry of available MJML components */
164
var components: object;
165
166
/**
167
* Initialize a component instance
168
* @param {object} config - Component configuration
169
* @returns {object|null} Component instance or null
170
*/
171
function initComponent(config);
172
173
/**
174
* Register a custom component
175
* @param {object} component - Component definition
176
*/
177
function registerComponent(component);
178
179
/**
180
* Assign components to component registry
181
* @param {object} target - Target component registry
182
* @param {object} source - Source components to assign
183
*/
184
function assignComponents(target, source);
185
```
186
187
### Utility Functions
188
189
Helper functions for CSS and component manipulation.
190
191
```javascript { .api }
192
/**
193
* Create responsive breakpoint CSS
194
* @param {string} breakpoint - Breakpoint value
195
* @returns {string} CSS media query
196
*/
197
function makeLowerBreakpoint(breakpoint);
198
199
/**
200
* Add suffix to CSS class names
201
* @param {string} classes - CSS classes string
202
* @param {string} suffix - Suffix to add
203
* @returns {string} Modified CSS classes
204
*/
205
function suffixCssClasses(classes, suffix);
206
207
/**
208
* Initialize MJML component types
209
* @param {object} type - Type definition
210
* @returns {object} Initialized type
211
*/
212
function initializeType(type);
213
```
214
215
### Component Base Classes
216
217
Base classes for creating custom MJML components.
218
219
```javascript { .api }
220
/**
221
* Base class for MJML body components
222
*/
223
class BodyComponent {
224
constructor(initialDatas);
225
render();
226
}
227
228
/**
229
* Base class for MJML head components
230
*/
231
class HeadComponent {
232
constructor(initialDatas);
233
handler();
234
}
235
```
236
237
### Error Handling
238
239
Error class for validation failures in strict mode.
240
241
```javascript { .api }
242
/**
243
* Error thrown when validation fails in strict mode
244
*/
245
class ValidationError extends Error {
246
constructor(message, errors);
247
248
/** Array of detailed validation errors */
249
errors: Array<object>;
250
}
251
```
252
253
## Default Configuration
254
255
### Built-in Fonts
256
257
```javascript
258
{
259
'Open Sans': 'https://fonts.googleapis.com/css?family=Open+Sans:300,400,500,700',
260
'Droid Sans': 'https://fonts.googleapis.com/css?family=Droid+Sans:300,400,500,700',
261
'Lato': 'https://fonts.googleapis.com/css?family=Lato:300,400,500,700',
262
'Roboto': 'https://fonts.googleapis.com/css?family=Roboto:300,400,500,700',
263
'Ubuntu': 'https://fonts.googleapis.com/css?family=Ubuntu:300,400,500,700'
264
}
265
```
266
267
### Default Options
268
269
- **validationLevel**: 'soft' (returns errors without throwing)
270
- **breakpoint**: '480px'
271
- **ignoreIncludes**: true (mj-include tags are not supported)
272
- **beautify**: false
273
- **minify**: false
274
275
## Browser Limitations
276
277
The browser version of MJML provides nearly identical functionality to the Node.js version but with specific limitations due to the browser security model and environment constraints:
278
279
### Unavailable Features
280
281
- **mj-include tags**: Cannot include external MJML files since browsers don't have filesystem access
282
- **.mjmlconfig files**: Configuration files cannot be loaded from the filesystem
283
- **Custom component loading**: External component files cannot be dynamically loaded
284
- **File system operations**: All Node.js `fs` module calls are replaced with browser-compatible mocks
285
286
### Behavioral Differences
287
288
- **ignoreIncludes option**: Always behaves as `true` regardless of setting
289
- **filePath/actualPath options**: Used only for error reporting, not file resolution
290
- **Custom skeleton templates**: String paths to skeleton files are not supported (function templates still work)
291
- **Component registration**: Must be done programmatically at runtime rather than via configuration files
292
293
### What Still Works
294
295
- **Full MJML component library**: All standard MJML components (mj-text, mj-button, mj-section, etc.)
296
- **Custom fonts**: Via URL-based font definitions in options
297
- **Validation**: Complete MJML validation with all strictness levels
298
- **CSS processing**: Full CSS inlining and responsive breakpoint handling
299
- **Component customization**: Programmatic component registration and configuration
300
301
## Advanced Usage Examples
302
303
### Custom Fonts Configuration
304
305
```javascript
306
var result = mjml2html(mjmlString, {
307
fonts: {
308
'Custom Font': 'https://fonts.example.com/custom-font.css'
309
}
310
});
311
```
312
313
### Strict Validation Mode
314
315
```javascript
316
try {
317
var result = mjml2html(mjmlString, {
318
validationLevel: 'strict'
319
});
320
} catch (error) {
321
if (error instanceof ValidationError) {
322
console.log('Validation errors:', error.errors);
323
}
324
}
325
```
326
327
### CSS Inlining Options
328
329
```javascript
330
var result = mjml2html(mjmlString, {
331
juiceOptions: {
332
preserveImportant: true,
333
removeStyleTags: false
334
}
335
});
336
```
337
338
### Component Registration
339
340
```javascript
341
// Register a custom component
342
registerComponent({
343
name: 'mj-custom',
344
handler: function() {
345
return '<div>Custom content</div>';
346
}
347
});
348
349
// Use the custom component
350
var mjmlWithCustom = `
351
<mjml>
352
<mj-body>
353
<mj-section>
354
<mj-column>
355
<mj-custom></mj-custom>
356
</mj-column>
357
</mj-section>
358
</mj-body>
359
</mjml>
360
`;
361
```