mikel 0.4.0 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +70 -5
- package/index.js +32 -25
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -199,11 +199,46 @@ const data = {
|
|
|
199
199
|
console.log(m("{{#unless isAdmin}}Hello guest{{/unless}}", data)); // --> 'Hello guest'
|
|
200
200
|
```
|
|
201
201
|
|
|
202
|
-
###
|
|
202
|
+
### Custom Helpers
|
|
203
|
+
|
|
204
|
+
> Added in `v0.5.0`.
|
|
205
|
+
|
|
206
|
+
Custom helpers should be provided as an object in the `options.helpers` field, where each key represents the name of the helper and the corresponding value is a function defining the helper's behavior.
|
|
207
|
+
|
|
208
|
+
Example:
|
|
209
|
+
|
|
210
|
+
```javascript
|
|
211
|
+
const template = "{{#greeting name}}{{/greeting}}";
|
|
212
|
+
const data = {
|
|
213
|
+
name: "World!",
|
|
214
|
+
};
|
|
215
|
+
const options = {
|
|
216
|
+
helpers: {
|
|
217
|
+
customHelper: ({context, value, key, options, fn}) => {
|
|
218
|
+
return `Hello, ${value}!`;
|
|
219
|
+
},
|
|
220
|
+
},
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
const result = m(template, data, options);
|
|
224
|
+
console.log(result); // Output: "Hello, World!"
|
|
225
|
+
```
|
|
226
|
+
|
|
227
|
+
Custom helper functions receive a single object parameter containing the following fields:
|
|
228
|
+
|
|
229
|
+
- `context`: The current context (data) where the helper has been executed.
|
|
230
|
+
- `value`: The current value passed to the helper.
|
|
231
|
+
- `key`: The field used to extract the value from the current context.
|
|
232
|
+
- `options`: The global options object.
|
|
233
|
+
- `fn`: A function that executes the template provided in the helper block and returns a string with the evaluated template in the provided context.
|
|
234
|
+
|
|
235
|
+
The helper function must return a string, which will be injected into the result string.
|
|
236
|
+
|
|
237
|
+
### Variables
|
|
203
238
|
|
|
204
239
|
> Added in `v0.4.0`.
|
|
205
240
|
|
|
206
|
-
|
|
241
|
+
Data Variables in Mikel provide convenient access to special values within your templates. These variables, denoted by the `@` symbol, allow users to interact with specific data contexts or values.
|
|
207
242
|
|
|
208
243
|
#### @root
|
|
209
244
|
|
|
@@ -231,10 +266,30 @@ The `@key` variable allows users to retrieve the current key of the object entry
|
|
|
231
266
|
|
|
232
267
|
The `@value` variable allows users to retrieve the current value of the object entry when iterating over an object using the `#each` helper. It simplifies access to object values for dynamic rendering and data manipulation.
|
|
233
268
|
|
|
269
|
+
### Custom variables
|
|
270
|
+
|
|
271
|
+
> Added in `v0.5.0`
|
|
272
|
+
|
|
273
|
+
Mikel allows users to define custom data variables, providing enhanced flexibility and customization options for templates. These custom data variables can be accessed within the template using the `@` character.
|
|
274
|
+
|
|
275
|
+
Custom data variables should be provided in the `options.variables` field of the options object when rendering a template. Each custom data variable should be defined as a key-value pair, where the key represents the variable name and the value represents the data associated with that variable.
|
|
276
|
+
|
|
277
|
+
Example:
|
|
278
|
+
|
|
279
|
+
```javascript
|
|
280
|
+
const result = m("Hello, {{@customVariable}}!", {}, {
|
|
281
|
+
variables: {
|
|
282
|
+
customVariable: "World",
|
|
283
|
+
},
|
|
284
|
+
});
|
|
285
|
+
console.log(result); // --> 'Hello, World!'
|
|
286
|
+
```
|
|
287
|
+
|
|
288
|
+
In this example, the custom data variable `customVariable` is defined with the value `"World"`, and it can be accessed in the template using `@customVariable`.
|
|
234
289
|
|
|
235
290
|
## API
|
|
236
291
|
|
|
237
|
-
### `
|
|
292
|
+
### `mikel(template, data[, options])`
|
|
238
293
|
|
|
239
294
|
Render the given template string with the provided data object.
|
|
240
295
|
|
|
@@ -242,20 +297,30 @@ Render the given template string with the provided data object.
|
|
|
242
297
|
- `data` (object): The data object containing the values to render.
|
|
243
298
|
- `options` (object): An object containing the following optional values:
|
|
244
299
|
- `partials` (object): An object containing the available partials.
|
|
300
|
+
- `variables` (object): An object containing custom data variables.
|
|
301
|
+
- `helpers` (object): An object containing custom helpers.
|
|
245
302
|
|
|
246
303
|
Returns: A string with the rendered output.
|
|
247
304
|
|
|
248
305
|
```javascript
|
|
249
|
-
import
|
|
306
|
+
import mikel from "mikel";
|
|
250
307
|
|
|
251
308
|
const data = {
|
|
252
309
|
name: "World",
|
|
253
310
|
};
|
|
254
311
|
|
|
255
|
-
const result =
|
|
312
|
+
const result = mikel("Hello, {{name}}!", data);
|
|
256
313
|
console.log(result); // Output: "Hello, World!"
|
|
257
314
|
```
|
|
258
315
|
|
|
316
|
+
### `mikel.escape(str)`
|
|
317
|
+
|
|
318
|
+
This function converts special HTML characters `&`, `<`, `>`, `"`, and `'` to their corresponding HTML entities.
|
|
319
|
+
|
|
320
|
+
### `mikel.get(object, path)`
|
|
321
|
+
|
|
322
|
+
This function returns the value in `object` following the provided `path` string.
|
|
323
|
+
|
|
259
324
|
## License
|
|
260
325
|
|
|
261
326
|
This project is licensed under the [MIT License](LICENSE).
|
package/index.js
CHANGED
|
@@ -7,50 +7,47 @@ const escapedChars = {
|
|
|
7
7
|
"'": "'",
|
|
8
8
|
};
|
|
9
9
|
|
|
10
|
-
const escape =
|
|
11
|
-
return str.toString().replace(/[&<>\"']/g, m => escapedChars[m]);
|
|
12
|
-
};
|
|
10
|
+
const escape = s => s.toString().replace(/[&<>\"']/g, m => escapedChars[m]);
|
|
13
11
|
|
|
14
|
-
const get = (
|
|
15
|
-
return (path === "." ? ctx : path.split(".").reduce((p, k) => p?.[k], ctx)) ?? "";
|
|
16
|
-
};
|
|
12
|
+
const get = (c, p) => (p === "." ? c : p.split(".").reduce((x, k) => x?.[k], c)) ?? "";
|
|
17
13
|
|
|
18
|
-
const
|
|
19
|
-
"
|
|
14
|
+
const defaultHelpers = {
|
|
15
|
+
"each": ({value, fn}) => {
|
|
20
16
|
return (typeof value === "object" ? Object.entries(value || {}) : [])
|
|
21
|
-
.map((item, index) =>
|
|
17
|
+
.map((item, index) => fn(item[1], {index: index, key: item[0], value: item[1]}))
|
|
22
18
|
.join("");
|
|
23
19
|
},
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
}
|
|
20
|
+
"if": ({value, fn, context}) => !!value ? fn(context) : "",
|
|
21
|
+
"unless": ({value, fn, context}) => !!!value ? fn(context) : "",
|
|
22
|
+
};
|
|
27
23
|
|
|
28
|
-
const compile = (tokens, output, context,
|
|
24
|
+
const compile = (tokens, output, context, partials, helpers, vars, index = 0, section = "") => {
|
|
29
25
|
let i = index;
|
|
30
26
|
while (i < tokens.length) {
|
|
31
27
|
if (i % 2 === 0) {
|
|
32
28
|
output.push(tokens[i]);
|
|
33
29
|
}
|
|
34
30
|
else if (tokens[i].startsWith("@")) {
|
|
35
|
-
output.push(get(vars
|
|
31
|
+
output.push(get(vars, tokens[i].slice(1).trim() ?? "_") ?? "");
|
|
36
32
|
}
|
|
37
33
|
else if (tokens[i].startsWith("!")) {
|
|
38
34
|
output.push(get(context, tokens[i].slice(1).trim()));
|
|
39
35
|
}
|
|
40
|
-
else if (tokens[i].startsWith("#") && helpers
|
|
36
|
+
else if (tokens[i].startsWith("#") && typeof helpers[tokens[i].slice(1).trim().split(" ")[0]] === "function") {
|
|
41
37
|
const [t, v] = tokens[i].slice(1).trim().split(" ");
|
|
42
38
|
const j = i + 1;
|
|
43
|
-
output.push(helpers
|
|
39
|
+
output.push(helpers[t]({
|
|
44
40
|
context: context,
|
|
45
|
-
|
|
41
|
+
key: v || ".",
|
|
42
|
+
value: get(context, v || "."),
|
|
46
43
|
fn: (blockContext = {}, blockVars = {}, blockOutput = []) => {
|
|
47
|
-
i = compile(tokens, blockOutput, blockContext,
|
|
44
|
+
i = compile(tokens, blockOutput, blockContext, partials, helpers, {...vars, ...blockVars, root: vars.root}, j, t);
|
|
48
45
|
return blockOutput.join("");
|
|
49
46
|
},
|
|
50
47
|
}));
|
|
51
48
|
// Make sure that this block has been executed
|
|
52
49
|
if (i + 1 === j) {
|
|
53
|
-
i = compile(tokens, [], {},
|
|
50
|
+
i = compile(tokens, [], {}, partials, helpers, vars, j, t);
|
|
54
51
|
}
|
|
55
52
|
}
|
|
56
53
|
else if (tokens[i].startsWith("#") || tokens[i].startsWith("^")) {
|
|
@@ -60,18 +57,18 @@ const compile = (tokens, output, context, opt, index = 0, section = "", vars = {
|
|
|
60
57
|
if (!negate && value && Array.isArray(value)) {
|
|
61
58
|
const j = i + 1;
|
|
62
59
|
(value.length > 0 ? value : [""]).forEach(item => {
|
|
63
|
-
i = compile(tokens, value.length > 0 ? output : [], item,
|
|
60
|
+
i = compile(tokens, value.length > 0 ? output : [], item, partials, helpers, vars, j, t);
|
|
64
61
|
});
|
|
65
62
|
}
|
|
66
63
|
else {
|
|
67
64
|
const includeOutput = (!negate && !!value) || (negate && !!!value);
|
|
68
|
-
i = compile(tokens, includeOutput ? output : [], context,
|
|
65
|
+
i = compile(tokens, includeOutput ? output : [], context, partials, helpers, vars, i + 1, t);
|
|
69
66
|
}
|
|
70
67
|
}
|
|
71
68
|
else if (tokens[i].startsWith(">")) {
|
|
72
69
|
const [t, v] = tokens[i].slice(1).trim().split(" ");
|
|
73
|
-
if (typeof
|
|
74
|
-
compile(
|
|
70
|
+
if (typeof partials[t] === "string") {
|
|
71
|
+
compile(partials[t].split(tags), output, v ? get(context, v) : context, partials, helpers, vars, 0, "");
|
|
75
72
|
}
|
|
76
73
|
}
|
|
77
74
|
else if (tokens[i].startsWith("/")) {
|
|
@@ -88,7 +85,17 @@ const compile = (tokens, output, context, opt, index = 0, section = "", vars = {
|
|
|
88
85
|
return i;
|
|
89
86
|
};
|
|
90
87
|
|
|
91
|
-
|
|
92
|
-
|
|
88
|
+
// @description main compiler function
|
|
89
|
+
const mikel = (str, context = {}, opt = {}, output = []) => {
|
|
90
|
+
const partials = Object.assign({}, opt.partials || {});
|
|
91
|
+
const helpers = Object.assign({}, defaultHelpers, opt.helpers || {});
|
|
92
|
+
const variables = Object.assign({}, opt.variables || {}, {root: context});
|
|
93
|
+
compile(str.split(tags), output, context, partials, helpers, variables, 0, "");
|
|
93
94
|
return output.join("");
|
|
94
95
|
};
|
|
96
|
+
|
|
97
|
+
// @description assign utilities
|
|
98
|
+
mikel.escape = escape;
|
|
99
|
+
mikel.get = get;
|
|
100
|
+
|
|
101
|
+
export default mikel;
|