@schukai/monster 1.23.0 → 1.26.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (221) hide show
  1. package/CHANGELOG +53 -0
  2. package/README.md +4 -4
  3. package/dist/modules/constants.js +2 -2
  4. package/dist/modules/constraints/abstract.js +1 -1
  5. package/dist/modules/constraints/abstractoperator.js +1 -1
  6. package/dist/modules/constraints/andoperator.js +1 -1
  7. package/dist/modules/constraints/invalid.js +1 -1
  8. package/dist/modules/constraints/isarray.js +1 -1
  9. package/dist/modules/constraints/isobject.js +1 -1
  10. package/dist/modules/constraints/namespace.js +1 -1
  11. package/dist/modules/constraints/oroperator.js +1 -1
  12. package/dist/modules/constraints/valid.js +1 -1
  13. package/dist/modules/data/buildmap.js +2 -2
  14. package/dist/modules/data/buildtree.js +2 -0
  15. package/dist/modules/data/datasource/namespace.js +1 -1
  16. package/dist/modules/data/datasource/restapi/writeerror.js +2 -0
  17. package/dist/modules/data/datasource/restapi.js +2 -2
  18. package/dist/modules/data/datasource/storage/localstorage.js +2 -2
  19. package/dist/modules/data/datasource/storage/namespace.js +1 -1
  20. package/dist/modules/data/datasource/storage/sessionstorage.js +2 -2
  21. package/dist/modules/data/datasource/storage.js +2 -2
  22. package/dist/modules/data/datasource.js +2 -2
  23. package/dist/modules/data/diff.js +2 -2
  24. package/dist/modules/data/extend.js +1 -1
  25. package/dist/modules/data/namespace.js +1 -1
  26. package/dist/modules/data/pathfinder.js +2 -2
  27. package/dist/modules/data/pipe.js +1 -1
  28. package/dist/modules/data/transformer.js +2 -2
  29. package/dist/modules/dom/assembler.js +1 -1
  30. package/dist/modules/dom/attributes.js +1 -1
  31. package/dist/modules/dom/constants.js +2 -2
  32. package/dist/modules/dom/customcontrol.js +2 -2
  33. package/dist/modules/dom/customelement.js +2 -2
  34. package/dist/modules/dom/events.js +1 -1
  35. package/dist/modules/dom/focusmanager.js +2 -0
  36. package/dist/modules/dom/locale.js +1 -1
  37. package/dist/modules/dom/namespace.js +1 -1
  38. package/dist/modules/dom/resource/data.js +2 -0
  39. package/dist/modules/dom/resource/link/stylesheet.js +2 -0
  40. package/dist/modules/dom/resource/link.js +2 -0
  41. package/dist/modules/dom/resource/script.js +2 -0
  42. package/dist/modules/dom/resource.js +2 -0
  43. package/dist/modules/dom/resourcemanager.js +2 -0
  44. package/dist/modules/dom/template.js +2 -2
  45. package/dist/modules/dom/theme.js +1 -1
  46. package/dist/modules/dom/updater.js +2 -2
  47. package/dist/modules/dom/util.js +1 -1
  48. package/dist/modules/dom/worker/factory.js +2 -0
  49. package/dist/modules/i18n/formatter.js +2 -0
  50. package/dist/modules/i18n/locale.js +1 -1
  51. package/dist/modules/i18n/namespace.js +1 -1
  52. package/dist/modules/i18n/provider.js +1 -1
  53. package/dist/modules/i18n/providers/fetch.js +2 -2
  54. package/dist/modules/i18n/providers/namespace.js +1 -1
  55. package/dist/modules/i18n/translations.js +1 -1
  56. package/dist/modules/logging/handler/console.js +1 -1
  57. package/dist/modules/logging/handler/namespace.js +1 -1
  58. package/dist/modules/logging/handler.js +1 -1
  59. package/dist/modules/logging/logentry.js +1 -1
  60. package/dist/modules/logging/logger.js +1 -1
  61. package/dist/modules/logging/namespace.js +1 -1
  62. package/dist/modules/math/namespace.js +1 -1
  63. package/dist/modules/math/random.js +2 -2
  64. package/dist/modules/monster.js +1 -1
  65. package/dist/modules/namespace.js +1 -1
  66. package/dist/modules/text/formatter.js +2 -2
  67. package/dist/modules/text/namespace.js +1 -1
  68. package/dist/modules/types/base.js +1 -1
  69. package/dist/modules/types/basewithoptions.js +2 -2
  70. package/dist/modules/types/binary.js +1 -1
  71. package/dist/modules/types/dataurl.js +1 -1
  72. package/dist/modules/types/global.js +1 -1
  73. package/dist/modules/types/id.js +1 -1
  74. package/dist/modules/types/is.js +2 -2
  75. package/dist/modules/types/mediatype.js +1 -1
  76. package/dist/modules/types/namespace.js +1 -1
  77. package/dist/modules/types/node.js +2 -0
  78. package/dist/modules/types/nodelist.js +2 -0
  79. package/dist/modules/types/noderecursiveiterator.js +2 -0
  80. package/dist/modules/types/observer.js +1 -1
  81. package/dist/modules/types/observerlist.js +2 -2
  82. package/dist/modules/types/proxyobserver.js +2 -2
  83. package/dist/modules/types/queue.js +1 -1
  84. package/dist/modules/types/randomid.js +1 -1
  85. package/dist/modules/types/regex.js +2 -0
  86. package/dist/modules/types/stack.js +1 -1
  87. package/dist/modules/types/tokenlist.js +2 -2
  88. package/dist/modules/types/typeof.js +1 -1
  89. package/dist/modules/types/uniquequeue.js +1 -1
  90. package/dist/modules/types/uuid.js +2 -0
  91. package/dist/modules/types/validate.js +1 -1
  92. package/dist/modules/types/version.js +2 -2
  93. package/dist/modules/util/clone.js +1 -1
  94. package/dist/modules/util/comparator.js +2 -2
  95. package/dist/modules/util/freeze.js +1 -1
  96. package/dist/modules/util/namespace.js +1 -1
  97. package/dist/modules/util/processing.js +2 -2
  98. package/dist/modules/util/trimspaces.js +2 -0
  99. package/dist/monster.dev.js +1684 -696
  100. package/dist/monster.dev.js.map +1 -1
  101. package/dist/monster.js +2 -2
  102. package/package.json +13 -2
  103. package/source/constants.js +16 -7
  104. package/source/constraints/abstract.js +5 -0
  105. package/source/constraints/abstractoperator.js +5 -0
  106. package/source/constraints/andoperator.js +10 -5
  107. package/source/constraints/invalid.js +8 -3
  108. package/source/constraints/isarray.js +9 -4
  109. package/source/constraints/isobject.js +8 -3
  110. package/source/constraints/oroperator.js +10 -5
  111. package/source/constraints/valid.js +8 -3
  112. package/source/data/buildmap.js +27 -11
  113. package/source/data/buildtree.js +95 -0
  114. package/source/data/datasource/restapi/writeerror.js +49 -0
  115. package/source/data/datasource/restapi.js +87 -20
  116. package/source/data/datasource/storage/localstorage.js +4 -10
  117. package/source/data/datasource/storage/sessionstorage.js +4 -12
  118. package/source/data/datasource/storage.js +7 -14
  119. package/source/data/datasource.js +55 -17
  120. package/source/data/diff.js +8 -8
  121. package/source/data/extend.js +5 -5
  122. package/source/data/pathfinder.js +12 -6
  123. package/source/data/pipe.js +6 -5
  124. package/source/data/transformer.js +131 -24
  125. package/source/dom/assembler.js +2 -2
  126. package/source/dom/attributes.js +24 -24
  127. package/source/dom/constants.js +305 -12
  128. package/source/dom/customcontrol.js +40 -19
  129. package/source/dom/customelement.js +121 -92
  130. package/source/dom/events.js +6 -6
  131. package/source/dom/focusmanager.js +250 -0
  132. package/source/dom/locale.js +10 -5
  133. package/source/dom/resource/data.js +170 -0
  134. package/source/dom/resource/link/stylesheet.js +54 -0
  135. package/source/dom/resource/link.js +125 -0
  136. package/source/dom/resource/script.js +112 -0
  137. package/source/dom/resource.js +268 -0
  138. package/source/dom/resourcemanager.js +214 -0
  139. package/source/dom/template.js +52 -12
  140. package/source/dom/theme.js +3 -3
  141. package/source/dom/updater.js +47 -33
  142. package/source/dom/util.js +6 -6
  143. package/source/dom/worker/factory.js +134 -0
  144. package/source/i18n/formatter.js +140 -0
  145. package/source/i18n/locale.js +10 -8
  146. package/source/i18n/provider.js +4 -4
  147. package/source/i18n/providers/fetch.js +24 -14
  148. package/source/i18n/translations.js +20 -10
  149. package/source/logging/handler/console.js +2 -2
  150. package/source/logging/handler.js +2 -2
  151. package/source/logging/logentry.js +2 -2
  152. package/source/logging/logger.js +4 -4
  153. package/source/math/random.js +11 -5
  154. package/source/namespace.js +1 -1
  155. package/source/text/formatter.js +244 -27
  156. package/source/types/base.js +4 -4
  157. package/source/types/basewithoptions.js +10 -15
  158. package/source/types/binary.js +4 -4
  159. package/source/types/dataurl.js +6 -6
  160. package/source/types/global.js +9 -7
  161. package/source/types/id.js +6 -3
  162. package/source/types/is.js +103 -85
  163. package/source/types/mediatype.js +4 -4
  164. package/source/types/node.js +179 -0
  165. package/source/types/nodelist.js +125 -0
  166. package/source/types/noderecursiveiterator.js +126 -0
  167. package/source/types/observer.js +3 -3
  168. package/source/types/observerlist.js +3 -3
  169. package/source/types/proxyobserver.js +24 -7
  170. package/source/types/queue.js +6 -6
  171. package/source/types/randomid.js +2 -2
  172. package/source/types/regex.js +49 -0
  173. package/source/types/stack.js +2 -2
  174. package/source/types/tokenlist.js +8 -9
  175. package/source/types/typeof.js +3 -3
  176. package/source/types/uniquequeue.js +4 -4
  177. package/source/types/uuid.js +102 -0
  178. package/source/types/validate.js +20 -20
  179. package/source/types/version.js +6 -6
  180. package/source/util/clone.js +4 -5
  181. package/source/util/comparator.js +5 -5
  182. package/source/util/freeze.js +5 -5
  183. package/source/util/processing.js +33 -36
  184. package/source/util/trimspaces.js +85 -0
  185. package/test/cases/data/buildtree.js +149 -0
  186. package/test/cases/data/datasource/restapi.js +1 -1
  187. package/test/cases/data/datasource.js +4 -4
  188. package/test/cases/data/diff.js +4 -4
  189. package/test/cases/data/pathfinder.js +18 -9
  190. package/test/cases/data/pipe.js +26 -2
  191. package/test/cases/data/transformer.js +41 -10
  192. package/test/cases/dom/attributes.js +18 -14
  193. package/test/cases/dom/customcontrol.js +6 -5
  194. package/test/cases/dom/customelement.js +14 -16
  195. package/test/cases/dom/focusmanager.js +111 -0
  196. package/test/cases/dom/locale.js +1 -4
  197. package/test/cases/dom/resource/data.js +129 -0
  198. package/test/cases/dom/resource/link/stylesheet.js +101 -0
  199. package/test/cases/dom/resource/link.js +101 -0
  200. package/test/cases/dom/resource/script.js +115 -0
  201. package/test/cases/dom/resourcemanager.js +118 -0
  202. package/test/cases/dom/updater.js +28 -4
  203. package/test/cases/dom/worker/factory.js +63 -0
  204. package/test/cases/i18n/formatter.js +66 -0
  205. package/test/cases/monster.js +1 -1
  206. package/test/cases/text/formatter.js +71 -8
  207. package/test/cases/types/node.js +196 -0
  208. package/test/cases/types/nodelist.js +64 -0
  209. package/test/cases/types/noderecursiveiterator.js +54 -0
  210. package/test/cases/types/proxyobserver.js +55 -11
  211. package/test/cases/types/regex.js +32 -0
  212. package/test/cases/types/uuid.js +42 -0
  213. package/test/cases/util/freeze.js +30 -4
  214. package/test/cases/util/trimspaces.js +24 -0
  215. package/test/util/cleanupdom.js +48 -0
  216. package/test/util/jsdom.js +22 -9
  217. package/test/web/import.js +15 -0
  218. package/test/web/monster-dev.html +3 -3
  219. package/test/web/monster.html +2 -2
  220. package/test/web/test.html +3 -3
  221. package/test/web/tests.js +7 -7
@@ -1,12 +1,47 @@
1
1
  'use strict';
2
2
 
3
- import {Pipe} from "../data/pipe.js";
4
3
  /**
5
4
  * @author schukai GmbH
6
5
  */
6
+
7
+ import {internalSymbol} from "../constants.js";
8
+ import {extend} from "../data/extend.js";
9
+ import {Pipe} from "../data/pipe.js";
7
10
  import {assignToNamespace, Monster} from '../namespace.js';
8
- import {Base} from "../types/base.js";
9
- import {validateObject, validateString} from "../types/validate.js";
11
+ import {BaseWithOptions} from "../types/basewithoptions.js";
12
+ import {isObject, isString} from "../types/is.js";
13
+ import {validateArray, validateString} from "../types/validate.js";
14
+
15
+
16
+ /**
17
+ * @private
18
+ * @type {symbol}
19
+ */
20
+ const internalObjectSymbol = Symbol('internalObject');
21
+
22
+ /**
23
+ * @private
24
+ * @type {symbol}
25
+ */
26
+ const watchdogSymbol = Symbol('watchdog');
27
+
28
+ /**
29
+ * @private
30
+ * @type {symbol}
31
+ */
32
+ const markerOpenIndexSymbol = Symbol('markerOpenIndex');
33
+
34
+ /**
35
+ * @private
36
+ * @type {symbol}
37
+ */
38
+ const markerCloseIndexSymbol = Symbol('markercloseIndex');
39
+
40
+ /**
41
+ * @private
42
+ * @type {symbol}
43
+ */
44
+ const workingDataSymbol = Symbol('workingData');
10
45
 
11
46
 
12
47
  /**
@@ -14,12 +49,12 @@ import {validateObject, validateString} from "../types/validate.js";
14
49
  *
15
50
  * Look at the example below. The placeholders use the logic of Pipe.
16
51
  *
17
- * You can call the method via the monster namespace `new Monster.Text.Formatter()`.
52
+ * You can create an instance via the monster namespace `new Monster.Text.Formatter()`.
18
53
  *
19
54
  * ```
20
55
  * <script type="module">
21
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/text/formatter.js';
22
- * console.log(new Monster.Text.Formatter())
56
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
57
+ * new Monster.Text.Formatter()
23
58
  * </script>
24
59
  * ```
25
60
  *
@@ -27,13 +62,53 @@ import {validateObject, validateString} from "../types/validate.js";
27
62
  *
28
63
  * ```
29
64
  * <script type="module">
30
- * import {Formatter} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/text/formatter.js';
31
- * console.log(new Formatter())
65
+ * import {Formatter} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/text/formatter.js';
66
+ * new Formatter()
32
67
  * </script>
33
68
  * ```
34
69
  *
70
+ * ## Marker in marker
71
+ *
72
+ * Markers can be nested. Here, the inner marker is resolved first `${subkey} ↦ 1 = ${mykey2}` and then the outer marker `${mykey2}`.
73
+ *
74
+ * ```
75
+ * const text = '${mykey${subkey}}';
76
+ * let obj = {
77
+ * mykey2: "1",
78
+ * subkey: "2"
79
+ * };
80
+ *
81
+ * new Formatter(obj).format(text);
82
+ * // ↦ 1
83
+ * ```
84
+ *
85
+ * ## Callbacks
86
+ *
87
+ * The values in a formatter can be adjusted via the commands of the `Transformer` or the`Pipe`.
88
+ * There is also the possibility to use callbacks.
89
+ *
90
+ * const formatter = new Formatter({x: '1'}, {
91
+ * callbacks: {
92
+ * quote: (value) => {
93
+ * return '"' + value + '"'
94
+ * }
95
+ * }
96
+ * });
97
+ *
98
+ * formatter.format('${x | call:quote}'))
99
+ * // ↦ "1"
100
+ *
101
+ * ## Marker with parameter
102
+ *
103
+ * A string can also bring its own values. These must then be separated from the key by a separator `::`.
104
+ * The values themselves must be specified in key/value pairs. The key must be separated from the value by a separator `=`.
105
+ *
106
+ * When using a pipe, you must pay attention to the separators.
107
+ *
35
108
  * @example
36
109
  *
110
+ * import {Formatter} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/text/formatter.js';
111
+ *
37
112
  * new Formatter({
38
113
  * a: {
39
114
  * b: {
@@ -41,7 +116,7 @@ import {validateObject, validateString} from "../types/validate.js";
41
116
  * },
42
117
  * d: "world",
43
118
  * }
44
- * }).format("${a.b.c} ${a.d | ucfirst}!");
119
+ * }).format("${a.b.c} ${a.d | ucfirst}!"); // with pipe
45
120
  *
46
121
  * // ↦ Hello World!
47
122
  *
@@ -49,7 +124,7 @@ import {validateObject, validateString} from "../types/validate.js";
49
124
  * @copyright schukai GmbH
50
125
  * @memberOf Monster.Text
51
126
  */
52
- class Formatter extends Base {
127
+ class Formatter extends BaseWithOptions {
53
128
 
54
129
  /**
55
130
  * Default values for the markers are `${` and `}`
@@ -57,11 +132,65 @@ class Formatter extends Base {
57
132
  * @param {object} object
58
133
  * @throws {TypeError} value is not a object
59
134
  */
60
- constructor(object) {
61
- super();
62
- this.object = validateObject(object);
63
- this.openMarker = '${';
64
- this.closeMarker = '}';
135
+ constructor(object, options) {
136
+ super(options);
137
+ this[internalObjectSymbol] = object || {}
138
+ this[markerOpenIndexSymbol] = 0;
139
+ this[markerCloseIndexSymbol] = 0;
140
+ }
141
+
142
+ /**
143
+ * @property {object} marker
144
+ * @property {array} marker.open=["${"]
145
+ * @property {array} marker.close=["${"]
146
+ * @property {object} parameter
147
+ * @property {string} parameter.delimiter="::"
148
+ * @property {string} parameter.assignment="="
149
+ * @property {object} callbacks={}
150
+ */
151
+ get defaults() {
152
+ return extend({}, super.defaults, {
153
+ marker: {
154
+ open: ['${'],
155
+ close: ['}']
156
+ },
157
+ parameter: {
158
+ delimiter: '::',
159
+ assignment: '='
160
+ },
161
+ callbacks: {},
162
+ })
163
+ }
164
+
165
+
166
+ /**
167
+ * Set new Parameter Character
168
+ *
169
+ * Default values for the chars are `::` and `=`
170
+ *
171
+ * ```
172
+ * formatter.setParameterChars('#');
173
+ * formatter.setParameterChars('[',']');
174
+ * formatter.setParameterChars('i18n{','}');
175
+ * ```
176
+ *
177
+ * @param {string} delimiter
178
+ * @param {string} assignment
179
+ * @return {Formatter}
180
+ * @since 1.24.0
181
+ * @throws {TypeError} value is not a string
182
+ */
183
+ setParameterChars(delimiter, assignment) {
184
+
185
+ if (delimiter !== undefined) {
186
+ this[internalSymbol]['parameter']['delimiter'] = validateString(delimiter);
187
+ }
188
+
189
+ if (assignment !== undefined) {
190
+ this[internalSymbol]['parameter']['assignment'] = validateString(assignment);
191
+ }
192
+
193
+ return this;
65
194
  }
66
195
 
67
196
  /**
@@ -75,8 +204,8 @@ class Formatter extends Base {
75
204
  * formatter.setMarker('i18n{','}');
76
205
  * ```
77
206
  *
78
- * @param {string} open
79
- * @param {string} close
207
+ * @param {array|string} open
208
+ * @param {array|string|undefined} close
80
209
  * @return {Formatter}
81
210
  * @since 1.12.0
82
211
  * @throws {TypeError} value is not a string
@@ -87,8 +216,11 @@ class Formatter extends Base {
87
216
  close = open;
88
217
  }
89
218
 
90
- this.openMarker = validateString(open);
91
- this.closeMarker = validateString(close);
219
+ if (isString(open)) open = [open];
220
+ if (isString(close)) close = [close];
221
+
222
+ this[internalSymbol]['marker']['open'] = validateArray(open);
223
+ this[internalSymbol]['marker']['close'] = validateArray(close);
92
224
  return this;
93
225
  }
94
226
 
@@ -97,11 +229,51 @@ class Formatter extends Base {
97
229
  * @param {string} text
98
230
  * @return {string}
99
231
  * @throws {TypeError} value is not a string
232
+ * @throws {Error} too deep nesting
100
233
  */
101
234
  format(text) {
102
- return tokenizer.call(this, validateString(text))
235
+ this[watchdogSymbol] = 0;
236
+ this[markerOpenIndexSymbol] = 0;
237
+ this[markerCloseIndexSymbol] = 0;
238
+ this[workingDataSymbol] = {};
239
+ return format.call(this, text);
240
+ }
241
+
242
+ }
243
+
244
+ /**
245
+ * @private
246
+ * @return {string}
247
+ */
248
+ function format(text) {
249
+ const self = this;
250
+
251
+ self[watchdogSymbol]++;
252
+ if (this[watchdogSymbol] > 20) {
253
+ throw new Error('too deep nesting')
254
+ }
255
+
256
+ let openMarker = self[internalSymbol]['marker']['open']?.[this[markerOpenIndexSymbol]];
257
+ let closeMarker = self[internalSymbol]['marker']['close']?.[this[markerCloseIndexSymbol]];
258
+
259
+ // contains no placeholders
260
+ if (text.indexOf(openMarker) === -1 || text.indexOf(closeMarker) === -1) {
261
+ return text;
262
+ }
263
+
264
+ let result = tokenize.call(this, validateString(text), openMarker, closeMarker)
265
+
266
+ if (self[internalSymbol]['marker']['open']?.[this[markerOpenIndexSymbol] + 1]) {
267
+ this[markerOpenIndexSymbol]++;
268
+ }
269
+
270
+ if (self[internalSymbol]['marker']['close']?.[this[markerCloseIndexSymbol] + 1]) {
271
+ this[markerCloseIndexSymbol]++;
103
272
  }
104
273
 
274
+ result = format.call(self, result)
275
+
276
+ return result;
105
277
  }
106
278
 
107
279
  /**
@@ -110,15 +282,18 @@ class Formatter extends Base {
110
282
  * @param text
111
283
  * @return {string}
112
284
  */
113
- function tokenizer(text) {
285
+ function tokenize(text, openMarker, closeMarker) {
114
286
  const self = this;
115
287
 
116
288
  let formatted = [];
117
289
 
118
- while (true) {
290
+ const parameterAssignment = self[internalSymbol]['parameter']['assignment']
291
+ const parameterDelimiter = self[internalSymbol]['parameter']['delimiter']
292
+ const callbacks = self[internalSymbol]['callbacks'];
119
293
 
294
+ while (true) {
120
295
 
121
- let startIndex = text.indexOf(self.openMarker);
296
+ let startIndex = text.indexOf(openMarker);
122
297
  // no marker
123
298
  if (startIndex === -1) {
124
299
  formatted.push(text);
@@ -128,18 +303,60 @@ function tokenizer(text) {
128
303
  text = text.substring(startIndex)
129
304
  }
130
305
 
131
- let endIndex = text.substring(self.openMarker.length).indexOf(self.closeMarker) + self.openMarker.length;
306
+ let endIndex = text.substring(openMarker.length).indexOf(closeMarker);
307
+ if (endIndex !== -1) endIndex += openMarker.length;
308
+ let insideStartIndex = text.substring(openMarker.length).indexOf(openMarker);
309
+ if (insideStartIndex !== -1) {
310
+ insideStartIndex += openMarker.length;
311
+ if (insideStartIndex < endIndex) {
312
+ let result = tokenize.call(self, text.substring(insideStartIndex), openMarker, closeMarker);
313
+ text = text.substring(0, insideStartIndex) + result
314
+ endIndex = text.substring(openMarker.length).indexOf(closeMarker);
315
+ if (endIndex !== -1) endIndex += openMarker.length;
316
+ }
317
+ }
132
318
 
133
319
  if (endIndex === -1) {
134
320
  throw new Error("syntax error in formatter template")
135
321
  return;
136
322
  }
137
323
 
138
- let command = "path:" + text.substring(self.openMarker.length, endIndex);
324
+ let key = text.substring(openMarker.length, endIndex);
325
+ let parts = key.split(parameterDelimiter);
326
+ let currentPipe = parts.shift();
327
+
328
+ self[workingDataSymbol] = extend({}, self[internalObjectSymbol], self[workingDataSymbol]);
329
+
330
+ for (const kv of parts) {
331
+ const [k, v] = kv.split(parameterAssignment);
332
+ self[workingDataSymbol][k] = v;
333
+ }
334
+
335
+ const t1 = key.split('|').shift().trim(); // pipe symbol
336
+ const t2 = t1.split('::').shift().trim(); // key value delimiter
337
+ const t3 = t2.split('.').shift().trim(); // path delimiter
338
+ let prefix = self[workingDataSymbol]?.[t3] ? 'path:' : 'static:';
339
+
340
+ let command = "";
341
+ if (prefix && key.indexOf(prefix) !== 0
342
+ && key.indexOf('path:') !== 0
343
+ && key.indexOf('static:') !== 0) {
344
+ command = prefix;
345
+ }
346
+
347
+ command += currentPipe;
348
+
349
+ const pipe = new Pipe(command);
350
+
351
+ if (isObject(callbacks)) {
352
+ for (const [name, callback] of Object.entries(callbacks)) {
353
+ pipe.setCallback(name, callback);
354
+ }
355
+ }
139
356
 
140
- formatted.push(validateString(new Pipe(command).run(self.object)));
357
+ formatted.push(validateString(pipe.run(self[workingDataSymbol])));
141
358
 
142
- text = text.substring(endIndex + self.closeMarker.length);
359
+ text = text.substring(endIndex + closeMarker.length);
143
360
 
144
361
  }
145
362
 
@@ -13,8 +13,8 @@ import {assignToNamespace, Monster} from '../namespace.js';
13
13
  *
14
14
  * ```
15
15
  * <script type="module">
16
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/base.js';
17
- * console.log(new Monster.Types.Base())
16
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
17
+ * new Monster.Types.Base()
18
18
  * </script>
19
19
  * ```
20
20
  *
@@ -22,8 +22,8 @@ import {assignToNamespace, Monster} from '../namespace.js';
22
22
  *
23
23
  * ```
24
24
  * <script type="module">
25
- * import {Base} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/base.js';
26
- * console.log(new Base())
25
+ * import {Base} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/base.js';
26
+ * new Base()
27
27
  * </script>
28
28
  * ```
29
29
  *
@@ -1,21 +1,16 @@
1
1
  'use strict';
2
2
 
3
- import {PROPERTY_KEY_INTERNALDATA} from "../constants.js";
4
- import {extend} from "../data/extend.js";
5
- import {Pathfinder} from "../data/pathfinder.js";
6
3
  /**
7
4
  * @author schukai GmbH
8
5
  */
6
+
7
+ import {internalSymbol} from "../constants.js";
8
+ import {extend} from "../data/extend.js";
9
+ import {Pathfinder} from "../data/pathfinder.js";
9
10
  import {assignToNamespace, Monster} from '../namespace.js';
10
11
  import {Base} from "./base.js";
11
12
  import {validateObject} from "./validate.js";
12
13
 
13
- /**
14
- * @private
15
- * @type {symbol}
16
- */
17
- const optionsSymbol = Symbol.for(PROPERTY_KEY_INTERNALDATA);
18
-
19
14
  /**
20
15
  * This is the base class with options from which some monster classes are derived.
21
16
  *
@@ -23,8 +18,8 @@ const optionsSymbol = Symbol.for(PROPERTY_KEY_INTERNALDATA);
23
18
  *
24
19
  * ```
25
20
  * <script type="module">
26
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/basewithoptions.js';
27
- * console.log(new Monster.Types.BaseWithOptions())
21
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
22
+ * new Monster.Types.BaseWithOptions()
28
23
  * </script>
29
24
  * ```
30
25
  *
@@ -32,8 +27,8 @@ const optionsSymbol = Symbol.for(PROPERTY_KEY_INTERNALDATA);
32
27
  *
33
28
  * ```
34
29
  * <script type="module">
35
- * import {BaseWithOptions} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/basewithoptions.js';
36
- * console.log(new BaseWithOptions())
30
+ * import {BaseWithOptions} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/basewithoptions.js';
31
+ * new BaseWithOptions()
37
32
  * </script>
38
33
  * ```
39
34
  *
@@ -56,7 +51,7 @@ class BaseWithOptions extends Base {
56
51
  options = {};
57
52
  }
58
53
 
59
- this[optionsSymbol] = extend({}, this.defaults, validateObject(options));
54
+ this[internalSymbol] = extend({}, this.defaults, validateObject(options));
60
55
 
61
56
  }
62
57
 
@@ -81,7 +76,7 @@ class BaseWithOptions extends Base {
81
76
  let value;
82
77
 
83
78
  try {
84
- value = new Pathfinder(this[optionsSymbol]).getVia(path);
79
+ value = new Pathfinder(this[internalSymbol]).getVia(path);
85
80
  } catch (e) {
86
81
 
87
82
  }
@@ -13,7 +13,7 @@ import {Monster, validateString} from "./validate.js";
13
13
  *
14
14
  * ```
15
15
  * <script type="module">
16
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/binary.js';
16
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
17
17
  * Monster.Types.toBinary()
18
18
  * </script>
19
19
  * ```
@@ -22,7 +22,7 @@ import {Monster, validateString} from "./validate.js";
22
22
  *
23
23
  * ```
24
24
  * <script type="module">
25
- * import {toBinary} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/binary.js';
25
+ * import {toBinary} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/binary.js';
26
26
  * toBinary()
27
27
  * </script>
28
28
  * ```
@@ -54,7 +54,7 @@ function toBinary(string) {
54
54
  *
55
55
  * ```
56
56
  * <script type="module">
57
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/binary.js';
57
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
58
58
  * Monster.Types.fromBinary()
59
59
  * </script>
60
60
  * ```
@@ -63,7 +63,7 @@ function toBinary(string) {
63
63
  *
64
64
  * ```
65
65
  * <script type="module">
66
- * import {fromBinary} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/binary.js';
66
+ * import {fromBinary} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/binary.js';
67
67
  * fromBinary()
68
68
  * </script>
69
69
  * ```
@@ -20,8 +20,8 @@ const internal = Symbol('internal');
20
20
  *
21
21
  * ```
22
22
  * <script type="module">
23
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/dataurl.js';
24
- * console.log(new Monster.Types.DataUrl())
23
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
24
+ * new Monster.Types.DataUrl()
25
25
  * </script>
26
26
  * ```
27
27
  *
@@ -29,8 +29,8 @@ const internal = Symbol('internal');
29
29
  *
30
30
  * ```
31
31
  * <script type="module">
32
- * import {DataUrl} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/dataurl.js';
33
- * console.log(new DataUrl())
32
+ * import {DataUrl} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/dataurl.js';
33
+ * new DataUrl()
34
34
  * </script>
35
35
  * ```
36
36
  *
@@ -98,7 +98,7 @@ class DataUrl extends Base {
98
98
  *
99
99
  * ```
100
100
  * <script type="module">
101
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/dataurl.js';
101
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
102
102
  * console.log(Monster.Types.parseDataURL())
103
103
  * </script>
104
104
  * ```
@@ -107,7 +107,7 @@ class DataUrl extends Base {
107
107
  *
108
108
  * ```
109
109
  * <script type="module">
110
- * import {parseDataURL} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/dataurl.js';
110
+ * import {parseDataURL} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/dataurl.js';
111
111
  * console.log(parseDataURL())
112
112
  * </script>
113
113
  * ```
@@ -78,8 +78,9 @@ function getGlobal() {
78
78
  *
79
79
  * ```
80
80
  * <script type="module">
81
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/global.js';
82
- * console.log(Monster.Types.getGlobalObject('document')) // ↦ { }
81
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
82
+ * Monster.Types.getGlobalObject('document')
83
+ * // ↦ { }
83
84
  * </script>
84
85
  * ```
85
86
  *
@@ -87,8 +88,9 @@ function getGlobal() {
87
88
  *
88
89
  * ```
89
90
  * <script type="module">
90
- * import {getGlobalObject} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/global.js';
91
- * console.log(getGlobalObject('document')) // ↦ { }
91
+ * import {getGlobalObject} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/global.js';
92
+ * getGlobalObject('document')
93
+ * // ↦ { }
92
94
  * </script>
93
95
  * ```
94
96
  *
@@ -115,7 +117,7 @@ function getGlobalObject(name) {
115
117
  *
116
118
  * ```
117
119
  * <script type="module">
118
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/global.js';
120
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
119
121
  * console.log(Monster.Types.getGlobalFunction('parseInt')) // ↦ f parseInt() { }
120
122
  * </script>
121
123
  * ```
@@ -124,7 +126,7 @@ function getGlobalObject(name) {
124
126
  *
125
127
  * ```
126
128
  * <script type="module">
127
- * import {getGlobalFunction} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/global.js';
129
+ * import {getGlobalFunction} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/global.js';
128
130
  * console.log(getGlobalFunction('parseInt')) // ↦ f parseInt() { }
129
131
  * </script>
130
132
  * ```
@@ -132,7 +134,7 @@ function getGlobalObject(name) {
132
134
  * @since 1.6.0
133
135
  * @memberOf Monster.Types
134
136
  * @param {string} name
135
- * @returns {objec}
137
+ * @return {objec}
136
138
  * @throws {TypeError} value is not a function
137
139
  * @throws {Error} the function is not defined
138
140
  * @throws {TypeError} value is not a string
@@ -24,7 +24,7 @@ let internalCounter = new Map;
24
24
  *
25
25
  * ```
26
26
  * <script type="module">
27
- * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/id.js';
27
+ * import {Monster} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/monster.js';
28
28
  * console.log(new Monster.Types.ID())
29
29
  * </script>
30
30
  * ```
@@ -33,7 +33,7 @@ let internalCounter = new Map;
33
33
  *
34
34
  * ```
35
35
  * <script type="module">
36
- * import {ID} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.23.0/dist/modules/types/id.js';
36
+ * import {ID} from 'https://cdn.jsdelivr.net/npm/@schukai/monster@1.26.1/dist/modules/types/id.js';
37
37
  * console.log(new ID())
38
38
  * </script>
39
39
  * ```
@@ -43,11 +43,14 @@ let internalCounter = new Map;
43
43
  * @since 1.0.0
44
44
  * @copyright schukai GmbH
45
45
  * @memberOf Monster.Types
46
+ * @summary Automatic generation of ids
46
47
  */
47
48
  class ID extends Base {
48
49
 
49
50
  /**
50
- * create new object
51
+ * create new id with prefix
52
+ *
53
+ * @param {string} prefix
51
54
  */
52
55
  constructor(prefix) {
53
56
  super();