@kosatyi/ejs 0.0.76 → 0.0.77

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.
@@ -0,0 +1,966 @@
1
+ const typeProp = function () {
2
+ const args = [].slice.call(arguments);
3
+ const callback = args.shift();
4
+ return args.filter(callback).pop()
5
+ };
6
+ const isArray = (v) => Array.isArray(v);
7
+ const isFunction = (v) => typeof v === 'function';
8
+ const isString = (v) => typeof v === 'string';
9
+ const isBoolean = (v) => typeof v === 'boolean';
10
+ const isUndefined = (v) => typeof v === 'undefined';
11
+
12
+ const isNodeEnv =
13
+ Object.prototype.toString.call(
14
+ typeof process !== 'undefined' ? process : 0
15
+ ) === '[object process]';
16
+
17
+ const isNode = () => isNodeEnv;
18
+
19
+ const symbolEntities = {
20
+ "'": "'",
21
+ '\\': '\\',
22
+ '\r': 'r',
23
+ '\n': 'n',
24
+ '\t': 't',
25
+ '\u2028': 'u2028',
26
+ '\u2029': 'u2029',
27
+ };
28
+
29
+ const htmlEntities = {
30
+ '&': '&',
31
+ '<': '&lt;',
32
+ '>': '&gt;',
33
+ '"': '&quot;',
34
+ "'": '&#x27;',
35
+ };
36
+
37
+ const regexKeys = (obj) =>
38
+ new RegExp(['[', Object.keys(obj).join(''), ']'].join(''), 'g');
39
+
40
+ const htmlEntitiesMatch = regexKeys(htmlEntities);
41
+
42
+ const symbolEntitiesMatch = regexKeys(symbolEntities);
43
+
44
+ const entities = (string = '') => {
45
+ return ('' + string).replace(
46
+ htmlEntitiesMatch,
47
+ (match) => htmlEntities[match]
48
+ )
49
+ };
50
+
51
+ const symbols = (string) => {
52
+ return ('' + string).replace(
53
+ symbolEntitiesMatch,
54
+ (match) => '\\' + symbolEntities[match]
55
+ )
56
+ };
57
+
58
+ const safeValue = (value, escape) => {
59
+ const check = value;
60
+ return check == null ? '' : escape === true ? entities(check) : check
61
+ };
62
+
63
+ const instanceOf = (object, instance) => {
64
+ return Boolean(object instanceof instance)
65
+ };
66
+
67
+ const getPath = (context, name, strict) => {
68
+ let data = context;
69
+ let chunks = String(name).split('.');
70
+ let prop = chunks.pop();
71
+ for (let i = 0; i < chunks.length; i++) {
72
+ const part = chunks[i];
73
+ if (isFunction(data['toJSON'])) {
74
+ data = data.toJSON();
75
+ }
76
+ if (strict && data.hasOwnProperty(part) === false) {
77
+ data = {};
78
+ break
79
+ }
80
+ data = data[part] = data[part] || {};
81
+ }
82
+ if (isFunction(data['toJSON'])) {
83
+ data = data.toJSON();
84
+ }
85
+ return [data, prop]
86
+ };
87
+
88
+ const ext = (path, defaults) => {
89
+ const ext = path.split('.').pop();
90
+ if (ext !== defaults) {
91
+ path = [path, defaults].join('.');
92
+ }
93
+ return path
94
+ };
95
+
96
+ /**
97
+ * @type {<T extends {}, U, V, W,Y>(T,U,V,W,Y)=> T & U & V & W & Y}
98
+ */
99
+ const extend = (target, ...args) => {
100
+ return args
101
+ .filter((source) => source)
102
+ .reduce((target, source) => Object.assign(target, source), target)
103
+ };
104
+
105
+ const noop = () => {};
106
+
107
+ const each = (object, callback) => {
108
+ let prop;
109
+ for (prop in object) {
110
+ if (hasProp(object, prop)) {
111
+ callback(object[prop], prop, object);
112
+ }
113
+ }
114
+ };
115
+
116
+ const map = (object, callback, context) => {
117
+ const result = [];
118
+ each(
119
+ object,
120
+ (value, key, object) => {
121
+ let item = callback(value, key, object);
122
+ if (isUndefined(item) === false) {
123
+ result.push(item);
124
+ }
125
+ });
126
+ return result
127
+ };
128
+
129
+ const filter = (object, callback, context) => {
130
+ const isArray = object instanceof Array;
131
+ const result = isArray ? [] : {};
132
+ each(
133
+ object,
134
+ (value, key, object) => {
135
+ let item = callback(value, key, object);
136
+ if (isUndefined(item) === false) {
137
+ if (isArray) {
138
+ result.push(item);
139
+ } else {
140
+ result[key] = item;
141
+ }
142
+ }
143
+ });
144
+ return result
145
+ };
146
+
147
+ const omit = (object, list) => {
148
+ return filter(object, (value, key) => {
149
+ if (list.indexOf(key) === -1) {
150
+ return value
151
+ }
152
+ })
153
+ };
154
+
155
+ const resolve$1 = (value, callback, context) =>
156
+ Promise.resolve(value).then(callback.bind(context));
157
+
158
+ const hasProp = (object, prop) => {
159
+ return object && object.hasOwnProperty(prop)
160
+ };
161
+
162
+ const defaults = {};
163
+
164
+ defaults.export = 'ejsPrecompiled';
165
+ defaults.cache = true;
166
+ defaults.chokidar = null;
167
+ defaults.path = 'views';
168
+ defaults.resolver = function (path, template) {
169
+ return Promise.resolve(
170
+ ['resolver is not defined', path, template].join(' ')
171
+ )
172
+ };
173
+ defaults.extension = 'ejs';
174
+ defaults.rmWhitespace = true;
175
+ defaults.withObject = true;
176
+ defaults.globalHelpers = [];
177
+ defaults.vars = {
178
+ SCOPE: 'ejs',
179
+ COMPONENT: 'ui',
180
+ EXTEND: '$$e',
181
+ BUFFER: '$$a',
182
+ LAYOUT: '$$l',
183
+ BLOCKS: '$$b',
184
+ MACRO: '$$m',
185
+ SAFE: '$$v',
186
+ };
187
+ defaults.token = {
188
+ start: '<%',
189
+ end: '%>',
190
+ regex: '([\\s\\S]+?)',
191
+ };
192
+
193
+ const configSchema = (config, options) => {
194
+ extend(config, {
195
+ path: typeProp(isString, defaults.path, config.path, options.path),
196
+ export: typeProp(
197
+ isString,
198
+ defaults.export,
199
+ config.export,
200
+ options.export
201
+ ),
202
+ resolver: typeProp(
203
+ isFunction,
204
+ defaults.resolver,
205
+ config.resolver,
206
+ options.resolver
207
+ ),
208
+ extension: typeProp(
209
+ isString,
210
+ defaults.extension,
211
+ config.extension,
212
+ options.extension
213
+ ),
214
+ withObject: typeProp(
215
+ isBoolean,
216
+ defaults.withObject,
217
+ config.withObject,
218
+ options.withObject
219
+ ),
220
+ rmWhitespace: typeProp(
221
+ isBoolean,
222
+ defaults.rmWhitespace,
223
+ config.rmWhitespace,
224
+ options.rmWhitespace
225
+ ),
226
+ cache: typeProp(isBoolean, defaults.cache, config.cache, options.cache),
227
+ token: extend({}, defaults.token, config.token, options.token),
228
+ vars: extend({}, defaults.vars, config.vars, options.vars),
229
+ globalHelpers: typeProp(
230
+ isArray,
231
+ defaults.globalHelpers,
232
+ config.globalHelpers,
233
+ options.globalHelpers
234
+ ),
235
+ });
236
+ };
237
+
238
+ const global = typeof globalThis !== 'undefined' ? globalThis : window || self;
239
+
240
+ function Cache(config) {
241
+ if (instanceOf(this, Cache) === false) return new Cache()
242
+ const cache = {
243
+ enabled: true,
244
+ list: {},
245
+ };
246
+ this.configure = function (config) {
247
+ cache.enabled = config.cache;
248
+ if (isNode() === false) {
249
+ this.load(global[config.export]);
250
+ }
251
+ };
252
+ this.clear = function () {
253
+ cache.list = {};
254
+ };
255
+ this.load = function (data) {
256
+ if (cache.enabled) {
257
+ extend(cache.list, data || {});
258
+ }
259
+ return this
260
+ };
261
+ this.get = function (key) {
262
+ if (cache.enabled) {
263
+ return cache.list[key]
264
+ }
265
+ };
266
+ this.set = function (key, value) {
267
+ if (cache.enabled) {
268
+ cache.list[key] = value;
269
+ }
270
+ return this
271
+ };
272
+ this.resolve = function (key) {
273
+ return Promise.resolve(this.get(key))
274
+ };
275
+ this.remove = function (key) {
276
+ delete cache.list[key];
277
+ };
278
+ this.exist = function (key) {
279
+ return hasProp(cache.list, key)
280
+ };
281
+ }
282
+
283
+ const tagList = [
284
+ {
285
+ symbol: '-',
286
+ format(value) {
287
+ return `')\n${this.BUFFER}(${this.SAFE}(${value},1))\n${this.BUFFER}('`
288
+ },
289
+ },
290
+ {
291
+ symbol: '=',
292
+ format(value) {
293
+ return `')\n${this.BUFFER}(${this.SAFE}(${value}))\n${this.BUFFER}('`
294
+ },
295
+ },
296
+ {
297
+ symbol: '#',
298
+ format(value) {
299
+ return `')\n/**${value}**/\n${this.BUFFER}('`
300
+ },
301
+ },
302
+ {
303
+ symbol: '',
304
+ format(value) {
305
+ return `')\n${value.trim()}\n${this.BUFFER}('`
306
+ },
307
+ },
308
+ ];
309
+
310
+ function matchTokens(regex, text, callback) {
311
+ let index = 0;
312
+ text.replace(regex, function () {
313
+ const params = [].slice.call(arguments, 0, -1);
314
+ const offset = params.pop();
315
+ const match = params.shift();
316
+ callback(params, index, offset);
317
+ index = offset + match.length;
318
+ return match
319
+ });
320
+ }
321
+
322
+ function Compiler(config) {
323
+ if (instanceOf(this, Compiler) === false) return new Compiler(config)
324
+
325
+ const compiler = {};
326
+
327
+ this.configure = function (config) {
328
+ compiler.withObject = config.withObject;
329
+ compiler.rmWhitespace = config.rmWhitespace;
330
+ compiler.token = config.token;
331
+ compiler.vars = config.vars;
332
+ compiler.globalHelpers = config.globalHelpers;
333
+ compiler.matches = [];
334
+ compiler.formats = [];
335
+ compiler.slurp = {
336
+ match: '[ \\t]*',
337
+ start: [compiler.token.start, '_'],
338
+ end: ['_', compiler.token.end],
339
+ };
340
+ tagList.forEach((item) => {
341
+ compiler.matches.push(
342
+ compiler.token.start
343
+ .concat(item.symbol)
344
+ .concat(compiler.token.regex)
345
+ .concat(compiler.token.end)
346
+ );
347
+ compiler.formats.push(item.format.bind(compiler.vars));
348
+ });
349
+ compiler.regex = new RegExp(
350
+ compiler.matches.join('|').concat('|$'),
351
+ 'g'
352
+ );
353
+ compiler.slurpStart = new RegExp(
354
+ [compiler.slurp.match, compiler.slurp.start.join('')].join(''),
355
+ 'gm'
356
+ );
357
+ compiler.slurpEnd = new RegExp(
358
+ [compiler.slurp.end.join(''), compiler.slurp.match].join(''),
359
+ 'gm'
360
+ );
361
+ };
362
+
363
+ this.compile = function (content, path) {
364
+ const { SCOPE, SAFE, BUFFER, COMPONENT } = compiler.vars;
365
+ const GLOBALS = compiler.globalHelpers;
366
+ content = String(content);
367
+ if (compiler.rmWhitespace) {
368
+ content = content
369
+ .replace(/[\r\n]+/g, '\n')
370
+ .replace(/^\s+|\s+$/gm, '');
371
+ }
372
+ content = content
373
+ .replace(compiler.slurpStart, compiler.token.start)
374
+ .replace(compiler.slurpEnd, compiler.token.end);
375
+ let source = `${BUFFER}('`;
376
+ matchTokens(compiler.regex, content, (params, index, offset) => {
377
+ source += symbols(content.slice(index, offset));
378
+ params.forEach((value, index) => {
379
+ if (value) {
380
+ source += compiler.formats[index](value);
381
+ }
382
+ });
383
+ });
384
+ source += `');`;
385
+ source = `try{${source}}catch(e){console.info(e)}`;
386
+ if (compiler.withObject) {
387
+ source = `with(${SCOPE}){${source}}`;
388
+ }
389
+ source = `${BUFFER}.start();${source}return ${BUFFER}.end();`;
390
+ source += `\n//# sourceURL=${path}`;
391
+ let result = null;
392
+ let params = [SCOPE, COMPONENT, BUFFER, SAFE].concat(GLOBALS);
393
+ try {
394
+ result = Function.apply(null, params.concat(source));
395
+ result.source = `(function(${params.join(',')}){\n${source}\n})`;
396
+ } catch (e) {
397
+ e.filename = path;
398
+ e.source = source;
399
+ throw e
400
+ }
401
+ return result
402
+ };
403
+
404
+ this.configure(config);
405
+ }
406
+
407
+ function Template(config, cache, compiler) {
408
+ if (instanceOf(this, Template) === false)
409
+ return new Template(config, cache, compiler)
410
+
411
+ if (instanceOf(cache, Cache) === false)
412
+ throw new TypeError('cache is not instance of Cache')
413
+
414
+ if (instanceOf(compiler, Compiler) === false)
415
+ throw new TypeError('compiler is not instance of Compiler')
416
+
417
+ const template = {};
418
+
419
+ const result = (template, content) => {
420
+ cache.set(template, content);
421
+ return content
422
+ };
423
+
424
+ const resolve = (path) => {
425
+ return template.resolver(template.path, path)
426
+ };
427
+
428
+ const compile = (content, template) => {
429
+ if (isFunction(content)) {
430
+ return content
431
+ } else {
432
+ return compiler.compile(content, template)
433
+ }
434
+ };
435
+
436
+ this.configure = function (config) {
437
+ template.path = config.path;
438
+ template.cache = config.cache;
439
+ if (isFunction(config.resolver)) {
440
+ template.resolver = config.resolver;
441
+ }
442
+ };
443
+
444
+ this.get = function (template) {
445
+ if (cache.exist(template)) {
446
+ return cache.resolve(template)
447
+ }
448
+ return resolve(template).then((content) =>
449
+ result(template, compile(content, template))
450
+ )
451
+ };
452
+ this.configure(config);
453
+ }
454
+
455
+ const selfClosed = [
456
+ 'area',
457
+ 'base',
458
+ 'br',
459
+ 'col',
460
+ 'embed',
461
+ 'hr',
462
+ 'img',
463
+ 'input',
464
+ 'link',
465
+ 'meta',
466
+ 'param',
467
+ 'source',
468
+ 'track',
469
+ 'wbr',
470
+ ];
471
+
472
+ const space = ' ';
473
+ const quote = '"';
474
+ const equal = '=';
475
+ const slash = '/';
476
+ const lt = '<';
477
+ const gt = '>';
478
+
479
+ const element = (tag, attrs, content) => {
480
+ const result = [];
481
+ const hasClosedTag = selfClosed.indexOf(tag) === -1;
482
+ const attributes = map(attrs, (value, key) => {
483
+ if (value !== null && value !== undefined) {
484
+ return [
485
+ entities(key),
486
+ [quote, entities(value), quote].join(''),
487
+ ].join(equal)
488
+ }
489
+ }).join(space);
490
+ result.push([lt, tag, space, attributes, gt].join(''));
491
+ if (content) {
492
+ result.push(content instanceof Array ? content.join('') : content);
493
+ }
494
+ if (hasClosedTag) {
495
+ result.push([lt, slash, tag, gt].join(''));
496
+ }
497
+ return result.join('')
498
+ };
499
+
500
+ function resolve(list) {
501
+ return Promise.all(list || []).then((list) => list.join(''))
502
+ }
503
+
504
+ function createBuffer() {
505
+ let store = [],
506
+ array = [];
507
+ function buffer(value) {
508
+ array.push(value);
509
+ }
510
+ buffer.start = function () {
511
+ array = [];
512
+ };
513
+ buffer.backup = function () {
514
+ store.push(array.concat());
515
+ array = [];
516
+ };
517
+ buffer.restore = function () {
518
+ const result = array.concat();
519
+ array = store.pop();
520
+ return resolve(result)
521
+ };
522
+ buffer.error = function (e) {
523
+ throw e
524
+ };
525
+ buffer.end = function () {
526
+ return resolve(array)
527
+ };
528
+ return buffer
529
+ }
530
+
531
+ function Context(config) {
532
+ if (instanceOf(this, Context) === false) return new Context(config)
533
+ this.configure = function (config, methods) {
534
+ const { BLOCKS, MACRO, EXTEND, LAYOUT, BUFFER, COMPONENT } = config.vars;
535
+
536
+ this.create = function (data) {
537
+ return new Scope(data)
538
+ };
539
+
540
+ this.helpers = function (methods) {
541
+ extend(Scope.prototype, methods || {});
542
+ };
543
+
544
+ function Scope(data) {
545
+ this[BLOCKS] = {};
546
+ this[MACRO] = {};
547
+ extend(this, data || {});
548
+ }
549
+
550
+ Scope.prototype = extend({}, methods || {});
551
+ Object.defineProperties(Scope.prototype, {
552
+ [BUFFER]: {
553
+ value: createBuffer(),
554
+ writable: true,
555
+ configurable: false,
556
+ enumerable: false,
557
+ },
558
+ [BLOCKS]: {
559
+ value: {},
560
+ writable: true,
561
+ configurable: false,
562
+ enumerable: false,
563
+ },
564
+ [MACRO]: {
565
+ value: {},
566
+ writable: true,
567
+ configurable: false,
568
+ enumerable: false,
569
+ },
570
+ [LAYOUT]: {
571
+ value: false,
572
+ writable: true,
573
+ configurable: false,
574
+ enumerable: false,
575
+ },
576
+ [EXTEND]: {
577
+ value: false,
578
+ writable: true,
579
+ configurable: false,
580
+ enumerable: false,
581
+ },
582
+ getMacro: {
583
+ value() {
584
+ return this[MACRO]
585
+ },
586
+ writable: false,
587
+ configurable: false,
588
+ enumerable: false,
589
+ },
590
+ getBuffer: {
591
+ value() {
592
+ return this[BUFFER]
593
+ },
594
+ writable: false,
595
+ configurable: false,
596
+ enumerable: false,
597
+ },
598
+ getComponent: {
599
+ value() {
600
+ const context = this;
601
+ if (COMPONENT in context) {
602
+ return function () {
603
+ return context[COMPONENT].apply(context, arguments)
604
+ }
605
+ }
606
+ return function () {
607
+ console.log('%s function not defined', COMPONENT);
608
+ }
609
+ },
610
+ writable: false,
611
+ configurable: false,
612
+ enumerable: false,
613
+ },
614
+ getBlocks: {
615
+ value() {
616
+ return this[BLOCKS]
617
+ },
618
+ writable: false,
619
+ configurable: false,
620
+ enumerable: false,
621
+ },
622
+ setExtend: {
623
+ value(value) {
624
+ this[EXTEND] = value;
625
+ },
626
+ writable: false,
627
+ configurable: false,
628
+ enumerable: false,
629
+ },
630
+ getExtend: {
631
+ value() {
632
+ return this[EXTEND]
633
+ },
634
+ writable: false,
635
+ configurable: false,
636
+ enumerable: false,
637
+ },
638
+ setLayout: {
639
+ value(layout) {
640
+ this[LAYOUT] = layout;
641
+ },
642
+ writable: false,
643
+ configurable: false,
644
+ enumerable: false,
645
+ },
646
+ getLayout: {
647
+ value() {
648
+ return this[LAYOUT]
649
+ },
650
+ writable: false,
651
+ configurable: false,
652
+ enumerable: false,
653
+ },
654
+ clone: {
655
+ value(exclude_blocks) {
656
+ const filter = [LAYOUT, EXTEND, BUFFER];
657
+ if (exclude_blocks === true) {
658
+ filter.push(BLOCKS);
659
+ }
660
+ return omit(this, filter)
661
+ },
662
+ writable: false,
663
+ configurable: false,
664
+ enumerable: false,
665
+ },
666
+
667
+ extend: {
668
+ value(layout) {
669
+ this.setExtend(true);
670
+ this.setLayout(layout);
671
+ },
672
+ writable: false,
673
+ configurable: false,
674
+ enumerable: false,
675
+ },
676
+ echo: {
677
+ value(layout) {
678
+ const buffer = this.getBuffer();
679
+ const params = [].slice.call(arguments);
680
+ params.forEach(buffer);
681
+ },
682
+ writable: false,
683
+ configurable: false,
684
+ enumerable: false,
685
+ },
686
+ fn: {
687
+ value(callback) {
688
+ const buffer = this.getBuffer();
689
+ const context = this;
690
+ return function () {
691
+ buffer.backup();
692
+ if (isFunction(callback)) {
693
+ callback.apply(context, arguments);
694
+ }
695
+ return buffer.restore()
696
+ }
697
+ },
698
+ writable: false,
699
+ configurable: false,
700
+ enumerable: false,
701
+ },
702
+ get: {
703
+ value(name, defaults) {
704
+ const path = getPath(this, name, true);
705
+ const result = path.shift();
706
+ const prop = path.pop();
707
+ return hasProp(result, prop) ? result[prop] : defaults
708
+ },
709
+ writable: false,
710
+ configurable: false,
711
+ enumerable: false,
712
+ },
713
+ set: {
714
+ value(name, value) {
715
+ const path = getPath(this, name, false);
716
+ const result = path.shift();
717
+ const prop = path.pop();
718
+ if (this.getExtend() && hasProp(result, prop)) {
719
+ return result[prop]
720
+ }
721
+ return (result[prop] = value)
722
+ },
723
+ writable: false,
724
+ configurable: false,
725
+ enumerable: false,
726
+ },
727
+ macro: {
728
+ value(name, callback) {
729
+ const list = this.getMacro();
730
+ const macro = this.fn(callback);
731
+ const context = this;
732
+ list[name] = function () {
733
+ return context.echo(macro.apply(undefined, arguments))
734
+ };
735
+ },
736
+ writable: false,
737
+ configurable: false,
738
+ enumerable: false,
739
+ },
740
+ call: {
741
+ value(name) {
742
+ const list = this.getMacro();
743
+ const macro = list[name];
744
+ const params = [].slice.call(arguments, 1);
745
+ if (isFunction(macro)) {
746
+ return macro.apply(macro, params)
747
+ }
748
+ },
749
+ writable: false,
750
+ configurable: false,
751
+ enumerable: false,
752
+ },
753
+ block: {
754
+ value(name, callback) {
755
+ const blocks = this.getBlocks();
756
+ blocks[name] = blocks[name] || [];
757
+ blocks[name].push(this.fn(callback));
758
+ if (this.getExtend()) return
759
+ const list = Object.assign([], blocks[name]);
760
+ const current = function () {
761
+ return list.shift()
762
+ };
763
+ const next = () => {
764
+ const parent = current();
765
+ if (parent) {
766
+ return () => {
767
+ this.echo(parent(next()));
768
+ }
769
+ } else {
770
+ return noop
771
+ }
772
+ };
773
+ this.echo(current()(next()));
774
+ },
775
+ writable: false,
776
+ configurable: false,
777
+ enumerable: false,
778
+ },
779
+ include: {
780
+ value(path, data, cx) {
781
+ const context = cx === false ? {} : this.clone(true);
782
+ const params = extend(context, data || {});
783
+ const promise = this.render(path, params);
784
+ this.echo(promise);
785
+ },
786
+ writable: false,
787
+ configurable: false,
788
+ enumerable: false,
789
+ },
790
+ use: {
791
+ value(path, namespace) {
792
+ const promise = this.require(path);
793
+ this.echo(
794
+ resolve$1(
795
+ promise,
796
+ function (exports) {
797
+ const list = this.getMacro();
798
+ each(exports, function (macro, name) {
799
+ list[[namespace, name].join('.')] = macro;
800
+ });
801
+ },
802
+ this
803
+ )
804
+ );
805
+ },
806
+ writable: false,
807
+ configurable: false,
808
+ enumerable: false,
809
+ },
810
+ async: {
811
+ value(promise, callback) {
812
+ this.echo(
813
+ resolve$1(
814
+ promise,
815
+ function (data) {
816
+ return this.fn(callback)(data)
817
+ },
818
+ this
819
+ )
820
+ );
821
+ },
822
+ writable: false,
823
+ configurable: false,
824
+ enumerable: false,
825
+ },
826
+ each: {
827
+ value: function (object, callback) {
828
+ if (isString(object)) {
829
+ object = this.get(object, []);
830
+ }
831
+ each(object, callback);
832
+ },
833
+ writable: false,
834
+ configurable: false,
835
+ enumerable: false,
836
+ },
837
+ element: {
838
+ value(tag, attr, content) {
839
+ return element(tag, attr, content)
840
+ },
841
+ writable: false,
842
+ configurable: false,
843
+ enumerable: false,
844
+ },
845
+ el: {
846
+ value(tag, attr, content) {
847
+ if (isFunction(content)) {
848
+ content = this.fn(content)();
849
+ }
850
+ this.echo(
851
+ resolve$1(
852
+ content,
853
+ function (content) {
854
+ return this.element(tag, attr, content)
855
+ },
856
+ this
857
+ )
858
+ );
859
+ },
860
+ writable: false,
861
+ configurable: false,
862
+ enumerable: false,
863
+ },
864
+ });
865
+ };
866
+ this.configure(config);
867
+ }
868
+
869
+ function EJS(options) {
870
+ if (instanceOf(this, EJS) === false) return new EJS(options)
871
+
872
+ const scope = {};
873
+ const config = {};
874
+
875
+ configSchema(config, options || {});
876
+
877
+ const context = new Context(config);
878
+ const compiler = new Compiler(config);
879
+ const cache = new Cache();
880
+ const template = new Template(config, cache, compiler);
881
+
882
+ const output = (path, context) => {
883
+ const params = [
884
+ context,
885
+ context.getComponent(),
886
+ context.getBuffer(),
887
+ safeValue,
888
+ ];
889
+ config.globalHelpers.forEach((name) => {
890
+ if (isFunction(context[name]))
891
+ params.push(context[name].bind(context));
892
+ });
893
+ return template.get(path).then(function (callback) {
894
+ return callback.apply(context, params)
895
+ })
896
+ };
897
+ const require = (name) => {
898
+ const filepath = ext(name, config.extension);
899
+ const scope = context.create({});
900
+ return output(filepath, scope).then(() => {
901
+ return scope.getMacro()
902
+ })
903
+ };
904
+ const render = (name, data) => {
905
+ const filepath = ext(name, config.extension);
906
+ const scope = context.create(data);
907
+ return output(filepath, scope).then((content) => {
908
+ if (scope.getExtend()) {
909
+ scope.setExtend(false);
910
+ const layout = scope.getLayout();
911
+ const data = scope.clone();
912
+ return render(layout, data)
913
+ }
914
+ return content
915
+ })
916
+ };
917
+ this.configure = function (options) {
918
+ options = options || {};
919
+ configSchema(config, options);
920
+ context.configure(config, scope);
921
+ compiler.configure(config);
922
+ cache.configure(config);
923
+ template.configure(config);
924
+ return config
925
+ };
926
+ this.render = function (name, data) {
927
+ return render(name, data)
928
+ };
929
+ this.helpers = function (methods) {
930
+ context.helpers(extend(scope, methods));
931
+ };
932
+ this.preload = function (list) {
933
+ return cache.load(list || {})
934
+ };
935
+ this.create = function (options) {
936
+ return new EJS(options)
937
+ };
938
+ this.compile = function (content, path) {
939
+ return compiler.compile(content, path)
940
+ };
941
+ this.context = function (data) {
942
+ return context.create(data)
943
+ };
944
+ this.helpers({ require, render });
945
+ return this
946
+ }
947
+
948
+ const templates = {};
949
+ const ejs = new EJS({
950
+ cache: false,
951
+ withObject: false,
952
+ resolver(path, name) {
953
+ if (name in templates) {
954
+ return Promise.resolve(templates[name])
955
+ }
956
+ return Promise.resolve(['template not found', name])
957
+ },
958
+ });
959
+
960
+ async function useTemplates(list) {
961
+ Object.assign(templates, list || {});
962
+ }
963
+
964
+ const { render, context, compile, helpers, preload, configure, create } = ejs;
965
+
966
+ export { compile, configure, context, create, helpers, preload, render, useTemplates };