@bonsae/nrg-runtime 0.22.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.
Files changed (30) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +24 -0
  3. package/internal/README.md +30 -0
  4. package/internal/client/components.mjs +1287 -0
  5. package/internal/client/index.mjs +229 -0
  6. package/internal/server/index.cjs +298 -0
  7. package/package.json +67 -0
  8. package/server/index.cjs +1407 -0
  9. package/server/resources/nrg-client.js +7493 -0
  10. package/types/client.d.ts +266 -0
  11. package/types/internal/client/components.d.ts +9 -0
  12. package/types/internal/client/index.d.ts +9 -0
  13. package/types/internal/server/index.d.ts +422 -0
  14. package/types/server.d.ts +941 -0
  15. package/types/shims/brands.d.ts +32 -0
  16. package/types/shims/client/form/components/node-red-config-input.vue.d.ts +125 -0
  17. package/types/shims/client/form/components/node-red-editor-input.vue.d.ts +124 -0
  18. package/types/shims/client/form/components/node-red-input-label.vue.d.ts +34 -0
  19. package/types/shims/client/form/components/node-red-input.vue.d.ts +123 -0
  20. package/types/shims/client/form/components/node-red-json-schema-form.vue.d.ts +772 -0
  21. package/types/shims/client/form/components/node-red-select-input.vue.d.ts +132 -0
  22. package/types/shims/client/form/components/node-red-toggle.vue.d.ts +36 -0
  23. package/types/shims/client/form/components/node-red-typed-input.vue.d.ts +151 -0
  24. package/types/shims/client/globals.d.ts +320 -0
  25. package/types/shims/client/types.d.ts +227 -0
  26. package/types/shims/components.d.ts +23 -0
  27. package/types/shims/constants.d.ts +4 -0
  28. package/types/shims/schema-options.d.ts +24 -0
  29. package/types/shims/shims-vue.d.ts +5 -0
  30. package/types/shims/typebox.d.ts +10 -0
@@ -0,0 +1,1287 @@
1
+ (function(){"use strict";try{if(typeof document<"u"){var e=document.createElement("style");e.appendChild(document.createTextNode('.nrg-label[data-v-6a6f1d01]{display:inline-block;width:100%;margin-bottom:4px;cursor:default}.nrg-label i[data-v-6a6f1d01]{margin-right:5px}.nrg-required[data-v-6a6f1d01]{color:var(--red-ui-text-color-error);margin-left:2px}.editor-wrapper[data-v-9e324115]{position:relative}.expand-button[data-v-9e324115]{position:absolute;top:-23px;right:0;z-index:10;transition:color .3s ease;cursor:pointer}.nrg-toggle-wrapper[data-v-c6353798]{display:inline-flex;align-items:center}.nrg-toggle[data-v-c6353798]{position:relative;display:inline-flex!important;flex-direction:column;align-items:flex-start;cursor:pointer;gap:4px;-webkit-user-select:none;user-select:none}.nrg-toggle__input[data-v-c6353798]{position:absolute;opacity:0;width:0;height:0}.nrg-toggle__slider[data-v-c6353798]{position:relative;display:inline-block;width:36px;min-width:36px;height:20px;background-color:var(--red-ui-secondary-border-color, #ccc);border-radius:10px;transition:background-color .2s ease}.nrg-toggle__slider[data-v-c6353798]:after{content:"";position:absolute;top:2px;left:2px;width:16px;height:16px;background-color:#fff;border-radius:50%;transition:transform .2s ease}.nrg-toggle--checked .nrg-toggle__slider[data-v-c6353798]{background-color:var(--red-ui-text-color-link, #0070d2)}.nrg-toggle--checked .nrg-toggle__slider[data-v-c6353798]:after{transform:translate(16px)}.nrg-toggle__label[data-v-c6353798]{cursor:default;white-space:nowrap}.nrg-toggle__label i[data-v-c6353798]{margin-right:2px}')),document.head.appendChild(e)}}catch(t){console.error("vite-plugin-css-injected-by-js",t)}})();
2
+ import { defineComponent as v, openBlock as a, createElementBlock as u, normalizeClass as E, createCommentVNode as p, renderSlot as I, createTextVNode as _, toDisplayString as g, resolveComponent as h, createBlock as m, createElementVNode as c, shallowRef as V, withDirectives as O, vShow as A, Teleport as W, Fragment as R, renderList as q, createVNode as w } from "vue";
3
+ const D = v({
4
+ name: "NodeRedInputLabel",
5
+ props: {
6
+ label: {
7
+ type: String,
8
+ default: ""
9
+ },
10
+ icon: {
11
+ type: String,
12
+ default: ""
13
+ },
14
+ required: {
15
+ type: Boolean,
16
+ default: !1
17
+ }
18
+ },
19
+ computed: {
20
+ iconClass() {
21
+ return this.icon ? `fa ${this.icon.startsWith("fa-") ? this.icon : `fa-${this.icon}`}` : "";
22
+ }
23
+ }
24
+ }), b = (e, t) => {
25
+ const o = e.__vccOpts || e;
26
+ for (const [i, l] of t)
27
+ o[i] = l;
28
+ return o;
29
+ }, B = { class: "nrg-label" }, U = {
30
+ key: 1,
31
+ class: "nrg-required"
32
+ };
33
+ function F(e, t, o, i, l, s) {
34
+ return a(), u("span", B, [
35
+ e.icon ? (a(), u(
36
+ "i",
37
+ {
38
+ key: 0,
39
+ class: E(e.iconClass)
40
+ },
41
+ null,
42
+ 2
43
+ /* CLASS */
44
+ )) : p("v-if", !0),
45
+ I(e.$slots, "default", {}, () => [
46
+ _(
47
+ g(e.label),
48
+ 1
49
+ /* TEXT */
50
+ )
51
+ ], !0),
52
+ e.required ? (a(), u("span", U, "*")) : p("v-if", !0)
53
+ ]);
54
+ }
55
+ const T = /* @__PURE__ */ b(D, [["render", F], ["__scopeId", "data-v-6a6f1d01"]]), N = "*************", P = v({
56
+ components: { NodeRedInputLabel: T },
57
+ props: {
58
+ modelValue: {
59
+ type: [String, Number],
60
+ default: void 0
61
+ },
62
+ value: {
63
+ type: [String, Number],
64
+ default: ""
65
+ },
66
+ type: {
67
+ type: String,
68
+ default: "text"
69
+ },
70
+ placeholder: {
71
+ type: String,
72
+ default: ""
73
+ },
74
+ label: {
75
+ type: String,
76
+ default: ""
77
+ },
78
+ icon: {
79
+ type: String,
80
+ default: ""
81
+ },
82
+ required: {
83
+ type: Boolean,
84
+ default: !1
85
+ },
86
+ error: {
87
+ type: String,
88
+ default: ""
89
+ }
90
+ },
91
+ emits: ["update:modelValue", "update:value", "input"],
92
+ data() {
93
+ return {
94
+ internalValue: ""
95
+ };
96
+ },
97
+ computed: {
98
+ effectiveValue() {
99
+ return this.modelValue !== void 0 ? this.modelValue : this.value;
100
+ }
101
+ },
102
+ beforeMount() {
103
+ this.internalValue = this.effectiveValue, this.onBlur();
104
+ },
105
+ methods: {
106
+ onInput(e) {
107
+ this.internalValue = e.target.value, this.$emit("update:modelValue", this.internalValue), this.$emit("update:value", this.internalValue), this.$emit("input", this.internalValue);
108
+ },
109
+ onFocus() {
110
+ this.type === "password" && this.internalValue === N && (this.internalValue = "");
111
+ },
112
+ onBlur() {
113
+ this.type === "password" && this.effectiveValue === "__PWD__" && (this.internalValue = N);
114
+ }
115
+ }
116
+ }), z = { style: { display: "flex", "flex-direction": "column", width: "100%" } }, M = ["type", "value", "placeholder"], J = {
117
+ key: 0,
118
+ class: "node-red-vue-input-error-message"
119
+ };
120
+ function K(e, t, o, i, l, s) {
121
+ const r = h("NodeRedInputLabel");
122
+ return a(), u("div", z, [
123
+ I(e.$slots, "label", {}, () => [
124
+ e.label ? (a(), m(r, {
125
+ key: 0,
126
+ label: e.label,
127
+ icon: e.icon,
128
+ required: e.required
129
+ }, null, 8, ["label", "icon", "required"])) : p("v-if", !0)
130
+ ]),
131
+ c("input", {
132
+ ref: "inputField",
133
+ type: e.type,
134
+ value: e.internalValue,
135
+ placeholder: e.placeholder,
136
+ style: { width: "100%" },
137
+ onInput: t[0] || (t[0] = (...f) => e.onInput && e.onInput(...f)),
138
+ onFocus: t[1] || (t[1] = (...f) => e.onFocus && e.onFocus(...f)),
139
+ onBlur: t[2] || (t[2] = (...f) => e.onBlur && e.onBlur(...f))
140
+ }, null, 40, M),
141
+ e.error ? (a(), u(
142
+ "div",
143
+ J,
144
+ g(e.error),
145
+ 1
146
+ /* TEXT */
147
+ )) : p("v-if", !0)
148
+ ]);
149
+ }
150
+ const Y = /* @__PURE__ */ b(P, [["render", K]]), H = [
151
+ "msg",
152
+ "flow",
153
+ "global",
154
+ "str",
155
+ "num",
156
+ "bool",
157
+ "json",
158
+ "bin",
159
+ "re",
160
+ "jsonata",
161
+ "date",
162
+ "env",
163
+ "node",
164
+ "cred"
165
+ ], Z = ["errorPort", "completePort", "statusPort"], G = v({
166
+ components: { NodeRedInputLabel: T },
167
+ props: {
168
+ modelValue: {
169
+ type: Object,
170
+ default: void 0,
171
+ validator: function(e) {
172
+ if (e === void 0) return !0;
173
+ if (typeof e != "object" || e === null)
174
+ return console.warn(
175
+ "[WARN] Invalid modelValue for TypedInput. It must be an object."
176
+ ), !1;
177
+ const t = typeof e.value == "string" && typeof e.type == "string";
178
+ return t || console.warn(
179
+ "[WARN] Invalid modelValue for TypedInput. It must be an object with 'value' and 'type' properties being strings.",
180
+ e
181
+ ), t;
182
+ }
183
+ },
184
+ value: {
185
+ type: Object,
186
+ default: void 0,
187
+ validator: function(e) {
188
+ if (e === void 0) return !0;
189
+ if (typeof e != "object" || e === null)
190
+ return console.warn(
191
+ "[WARN] Invalid value for TypedInput. It must be an object."
192
+ ), !1;
193
+ const t = typeof e.value == "string" && typeof e.type == "string";
194
+ return t || console.warn(
195
+ "[WARN] Invalid value for TypedInput. It must be an object with 'value' and 'type' properties being strings.",
196
+ e
197
+ ), t;
198
+ }
199
+ },
200
+ types: {
201
+ type: Array,
202
+ default: () => H
203
+ },
204
+ label: {
205
+ type: String,
206
+ default: ""
207
+ },
208
+ icon: {
209
+ type: String,
210
+ default: ""
211
+ },
212
+ required: {
213
+ type: Boolean,
214
+ default: !1
215
+ },
216
+ error: {
217
+ type: String,
218
+ default: ""
219
+ }
220
+ },
221
+ emits: ["update:modelValue", "update:value"],
222
+ setup() {
223
+ return {
224
+ inputWidget: V(null),
225
+ mutationObserver: V(null)
226
+ };
227
+ },
228
+ computed: {
229
+ effectiveValue() {
230
+ return this.modelValue !== void 0 ? this.modelValue : this.value;
231
+ },
232
+ isProvidedValueTypeValid() {
233
+ const e = this.effectiveValue.type;
234
+ return this.types.includes(e);
235
+ }
236
+ },
237
+ watch: {
238
+ isProvidedValueTypeValid: {
239
+ handler(e) {
240
+ e || console.warn(
241
+ `Validation failed: type (${this.effectiveValue.type}) must be one of the provided types (${this.types}).`
242
+ );
243
+ },
244
+ immediate: !0
245
+ },
246
+ error(e) {
247
+ this.$nextTick(() => {
248
+ const t = this.$el.querySelector(
249
+ ".red-ui-typedInput-container"
250
+ );
251
+ t && (e ? t.classList.add("input-error") : t.classList.remove("input-error"));
252
+ });
253
+ }
254
+ },
255
+ mounted() {
256
+ const e = this.$refs.typedInput;
257
+ this.inputWidget = $(e), this.inputWidget.typedInput({
258
+ default: this.effectiveValue.type || this.types[0],
259
+ types: this.types
260
+ }), this.inputWidget.typedInput("value", this.effectiveValue.value || ""), this.inputWidget.typedInput(
261
+ "type",
262
+ this.effectiveValue.type || this.types[0]
263
+ ), this.$nextTick(() => {
264
+ const t = new MutationObserver((o) => {
265
+ for (const i of o)
266
+ i.attributeName === "value" && this.onChange();
267
+ });
268
+ t.observe(e, {
269
+ attributes: !0,
270
+ attributeFilter: ["value"]
271
+ }), this.mutationObserver = t;
272
+ }), this.inputWidget.on("change", () => {
273
+ this.onChange();
274
+ });
275
+ },
276
+ beforeUnmount() {
277
+ this.mutationObserver && (this.mutationObserver.disconnect(), this.mutationObserver = null);
278
+ },
279
+ methods: {
280
+ onChange() {
281
+ const e = this.inputWidget.typedInput("value"), t = this.inputWidget.typedInput("type");
282
+ if (this.effectiveValue.value !== e || this.effectiveValue.type !== t) {
283
+ const o = { value: e, type: t };
284
+ this.$emit("update:modelValue", o), this.$emit("update:value", o);
285
+ }
286
+ }
287
+ }
288
+ }), Q = { style: { display: "flex", "flex-direction": "column", width: "100%" } }, X = {
289
+ ref: "typedInput",
290
+ type: "text",
291
+ class: "node-red-typed-input",
292
+ style: { flex: "1", width: "100%" }
293
+ }, x = {
294
+ key: 0,
295
+ class: "node-red-vue-input-error-message"
296
+ };
297
+ function ee(e, t, o, i, l, s) {
298
+ const r = h("NodeRedInputLabel");
299
+ return a(), u("div", Q, [
300
+ I(e.$slots, "label", {}, () => [
301
+ e.label ? (a(), m(r, {
302
+ key: 0,
303
+ label: e.label,
304
+ icon: e.icon,
305
+ required: e.required
306
+ }, null, 8, ["label", "icon", "required"])) : p("v-if", !0)
307
+ ]),
308
+ c(
309
+ "input",
310
+ X,
311
+ null,
312
+ 512
313
+ /* NEED_PATCH */
314
+ ),
315
+ e.error ? (a(), u(
316
+ "div",
317
+ x,
318
+ g(e.error),
319
+ 1
320
+ /* TEXT */
321
+ )) : p("v-if", !0)
322
+ ]);
323
+ }
324
+ const te = /* @__PURE__ */ b(G, [["render", ee]]), ne = v({
325
+ components: { NodeRedInputLabel: T },
326
+ props: {
327
+ modelValue: {
328
+ type: String,
329
+ default: void 0
330
+ },
331
+ value: {
332
+ type: String,
333
+ default: ""
334
+ },
335
+ type: {
336
+ type: String,
337
+ required: !0
338
+ },
339
+ node: {
340
+ type: Object,
341
+ required: !0
342
+ },
343
+ propName: {
344
+ type: String,
345
+ required: !0
346
+ },
347
+ label: {
348
+ type: String,
349
+ default: ""
350
+ },
351
+ icon: {
352
+ type: String,
353
+ default: ""
354
+ },
355
+ required: {
356
+ type: Boolean,
357
+ default: !1
358
+ },
359
+ error: {
360
+ type: String,
361
+ default: ""
362
+ }
363
+ },
364
+ emits: ["update:modelValue", "update:value"],
365
+ setup() {
366
+ return {
367
+ jqInput: V(null)
368
+ };
369
+ },
370
+ computed: {
371
+ inputId() {
372
+ return "node-input-" + this.propName;
373
+ },
374
+ effectiveValue() {
375
+ return this.modelValue !== void 0 ? this.modelValue : this.value;
376
+ }
377
+ },
378
+ mounted() {
379
+ RED.editor.prepareConfigNodeSelect(
380
+ this.node,
381
+ this.propName,
382
+ this.type,
383
+ "node-input"
384
+ );
385
+ const e = $("#" + this.inputId);
386
+ this.jqInput = e, e.on("change", () => {
387
+ const t = e.val(), o = t === "_ADD_" ? "" : t;
388
+ this.$emit("update:modelValue", o), this.$emit("update:value", o);
389
+ }), e.val(this.effectiveValue || "_ADD_");
390
+ },
391
+ beforeUnmount() {
392
+ this.jqInput && (this.jqInput.off("change"), this.jqInput = null);
393
+ }
394
+ }), oe = { style: { display: "flex", "flex-direction": "column", width: "100%" } }, re = ["id"], ie = {
395
+ key: 0,
396
+ class: "node-red-vue-input-error-message"
397
+ };
398
+ function ae(e, t, o, i, l, s) {
399
+ const r = h("NodeRedInputLabel");
400
+ return a(), u("div", oe, [
401
+ I(e.$slots, "label", {}, () => [
402
+ e.label ? (a(), m(r, {
403
+ key: 0,
404
+ label: e.label,
405
+ icon: e.icon,
406
+ required: e.required
407
+ }, null, 8, ["label", "icon", "required"])) : p("v-if", !0)
408
+ ]),
409
+ c("input", {
410
+ id: e.inputId,
411
+ type: "text",
412
+ style: { width: "100%" }
413
+ }, null, 8, re),
414
+ e.error ? (a(), u(
415
+ "div",
416
+ ie,
417
+ g(e.error),
418
+ 1
419
+ /* TEXT */
420
+ )) : p("v-if", !0)
421
+ ]);
422
+ }
423
+ const le = /* @__PURE__ */ b(ne, [["render", ae]]), se = v({
424
+ components: { NodeRedInputLabel: T },
425
+ props: {
426
+ modelValue: {
427
+ type: [String, Array],
428
+ default: void 0
429
+ },
430
+ value: {
431
+ type: [String, Array],
432
+ default: () => ""
433
+ },
434
+ options: {
435
+ type: Array,
436
+ required: !0,
437
+ validator: function(e) {
438
+ if (!Array.isArray(e))
439
+ return console.warn(
440
+ "[WARN] Invalid value for 'options' property. It must be an array."
441
+ ), !1;
442
+ const t = e.every(
443
+ (o) => typeof o == "object" && o !== null && typeof o.value == "string" && typeof o.label == "string" && Object.prototype.hasOwnProperty.call(o, "value") && Object.prototype.hasOwnProperty.call(o, "label")
444
+ );
445
+ return t || console.warn(
446
+ "[WARN] Invalid value for 'options' property. Each item must be an object with 'value' and 'label' properties being strings.",
447
+ e
448
+ ), t;
449
+ }
450
+ },
451
+ multiple: {
452
+ type: Boolean,
453
+ default: !1
454
+ },
455
+ label: {
456
+ type: String,
457
+ default: ""
458
+ },
459
+ icon: {
460
+ type: String,
461
+ default: ""
462
+ },
463
+ required: {
464
+ type: Boolean,
465
+ default: !1
466
+ },
467
+ error: {
468
+ type: String,
469
+ default: ""
470
+ }
471
+ },
472
+ emits: ["update:modelValue", "update:value"],
473
+ setup() {
474
+ return {
475
+ selectWidget: V(null)
476
+ };
477
+ },
478
+ computed: {
479
+ effectiveValue() {
480
+ return this.modelValue !== void 0 ? this.modelValue : this.value;
481
+ }
482
+ },
483
+ mounted() {
484
+ const e = this.$refs.selectInput, t = $(e);
485
+ this.selectWidget = t, t.typedInput({
486
+ types: [
487
+ {
488
+ multiple: this.multiple,
489
+ options: this.options
490
+ }
491
+ ]
492
+ }), t.typedInput(
493
+ "value",
494
+ Array.isArray(this.effectiveValue) ? this.effectiveValue.join(",") : this.effectiveValue
495
+ ), t.on("change", () => {
496
+ var i;
497
+ const o = this.multiple ? ((i = t.typedInput("value")) == null ? void 0 : i.split(",").filter(Boolean)) ?? [] : t.typedInput("value");
498
+ this.$emit("update:modelValue", o), this.$emit("update:value", o);
499
+ });
500
+ },
501
+ beforeUnmount() {
502
+ this.selectWidget && (this.selectWidget.off("change"), this.selectWidget = null);
503
+ }
504
+ }), ue = { style: { display: "flex", "flex-direction": "column", width: "100%" } }, de = {
505
+ ref: "selectInput",
506
+ type: "text",
507
+ class: "node-input-select",
508
+ style: { width: "100%" }
509
+ }, pe = {
510
+ key: 0,
511
+ class: "node-red-vue-input-error-message"
512
+ };
513
+ function ce(e, t, o, i, l, s) {
514
+ const r = h("NodeRedInputLabel");
515
+ return a(), u("div", ue, [
516
+ I(e.$slots, "label", {}, () => [
517
+ e.label ? (a(), m(r, {
518
+ key: 0,
519
+ label: e.label,
520
+ icon: e.icon,
521
+ required: e.required
522
+ }, null, 8, ["label", "icon", "required"])) : p("v-if", !0)
523
+ ]),
524
+ c(
525
+ "input",
526
+ de,
527
+ null,
528
+ 512
529
+ /* NEED_PATCH */
530
+ ),
531
+ e.error ? (a(), u(
532
+ "div",
533
+ pe,
534
+ g(e.error),
535
+ 1
536
+ /* TEXT */
537
+ )) : p("v-if", !0)
538
+ ]);
539
+ }
540
+ const ye = /* @__PURE__ */ b(se, [["render", ce]]), he = v({
541
+ components: { NodeRedInputLabel: T },
542
+ props: {
543
+ modelValue: {
544
+ type: String,
545
+ default: void 0
546
+ },
547
+ value: {
548
+ type: String,
549
+ default: ""
550
+ },
551
+ language: {
552
+ type: String,
553
+ default: "json",
554
+ validator: function(e) {
555
+ const t = [
556
+ "abap",
557
+ "apex",
558
+ "azcli",
559
+ "bat",
560
+ "bicep",
561
+ "cameligo",
562
+ "clojure",
563
+ "coffee",
564
+ "cpp",
565
+ "csharp",
566
+ "csp",
567
+ "css",
568
+ "cypher",
569
+ "dart",
570
+ "dockerfile",
571
+ "ecl",
572
+ "elixir",
573
+ "flow9",
574
+ "freemarker2",
575
+ "fsharp",
576
+ "go",
577
+ "graphql",
578
+ "handlebars",
579
+ "hcl",
580
+ "html",
581
+ "ini",
582
+ "java",
583
+ "javascript",
584
+ "json",
585
+ "julia",
586
+ "kotlin",
587
+ "less",
588
+ "lexon",
589
+ "liquid",
590
+ "lua",
591
+ "m3",
592
+ "markdown",
593
+ "mdx",
594
+ "mips",
595
+ "msdax",
596
+ "mysql",
597
+ "objective-c",
598
+ "pascal",
599
+ "pascaligo",
600
+ "perl",
601
+ "pgsql",
602
+ "php",
603
+ "pla",
604
+ "postiats",
605
+ "powerquery",
606
+ "powershell",
607
+ "protobuf",
608
+ "pub",
609
+ "python",
610
+ "qsharp",
611
+ "r",
612
+ "razor",
613
+ "redis",
614
+ "redshift",
615
+ "restructuredtext",
616
+ "ruby",
617
+ "rust",
618
+ "sb",
619
+ "scala",
620
+ "scheme",
621
+ "scss",
622
+ "shell",
623
+ "solidity",
624
+ "sophia",
625
+ "sparql",
626
+ "sql",
627
+ "st",
628
+ "swift",
629
+ "systemverilog",
630
+ "tcl",
631
+ "twig",
632
+ "typescript",
633
+ "typespec",
634
+ "vb",
635
+ "wgsl",
636
+ "xml",
637
+ "yaml"
638
+ ], o = t.includes(e);
639
+ return o || console.warn(
640
+ `[WARN]: Invalid value for 'type' property: "${e}". Expected one of: ${t.join(", ")}`
641
+ ), o;
642
+ }
643
+ },
644
+ label: {
645
+ type: String,
646
+ default: ""
647
+ },
648
+ icon: {
649
+ type: String,
650
+ default: ""
651
+ },
652
+ required: {
653
+ type: Boolean,
654
+ default: !1
655
+ },
656
+ error: {
657
+ type: String,
658
+ default: ""
659
+ }
660
+ },
661
+ emits: [
662
+ "update:modelValue",
663
+ "update:value",
664
+ "editor-ready",
665
+ "tray-open",
666
+ "tray-close"
667
+ ],
668
+ setup() {
669
+ return {
670
+ // NOTE: must not be named "editor" — the template's ref="editor" would
671
+ // overwrite this with the DOM element on every re-render.
672
+ editorInstance: V(null),
673
+ expandedEditorTray: V(null)
674
+ };
675
+ },
676
+ data() {
677
+ const e = Math.random().toString(36).substring(2, 9);
678
+ return {
679
+ editorId: "node-red-editor-" + e,
680
+ stateId: e,
681
+ trayElement: null
682
+ };
683
+ },
684
+ computed: {
685
+ effectiveValue() {
686
+ return this.modelValue !== void 0 ? this.modelValue : this.value;
687
+ }
688
+ },
689
+ mounted() {
690
+ const e = $(this.$refs["expand-button"]);
691
+ RED.popover.tooltip(e, RED._("node-red:common.label.expand")), this.mountEditor(), this.createExpandeEditorTray();
692
+ },
693
+ beforeUnmount() {
694
+ if (this.editorInstance) {
695
+ try {
696
+ this.editorInstance.destroy();
697
+ } catch (e) {
698
+ console.error(`Error destroying editor for ID ${this.editorId}:`, e);
699
+ }
700
+ this.editorInstance = null;
701
+ }
702
+ },
703
+ methods: {
704
+ mountEditor() {
705
+ this.$nextTick(() => {
706
+ const e = this.$refs.container, t = this.$refs.editor;
707
+ if (e && t)
708
+ try {
709
+ const o = e.style.height, i = e.style.width;
710
+ o ? t.style.height = o : t.style.height = "200px", i ? t.style.width = i : t.style.width = "100%", this.createEditorInstance();
711
+ } catch (o) {
712
+ console.error(
713
+ "[NodeRedEditorInput] Error setting initial editor style:",
714
+ o
715
+ ), this.createEditorInstance();
716
+ }
717
+ else
718
+ console.error(
719
+ "[NodeRedEditorInput] Container or Editor div refs not found on mount."
720
+ );
721
+ });
722
+ },
723
+ createEditorInstance() {
724
+ this.editorInstance = RED.editor.createEditor({
725
+ id: this.editorId,
726
+ mode: this.language,
727
+ value: this.effectiveValue
728
+ }), this.editorInstance.getSession().on("change", () => {
729
+ const e = this.editorInstance.getValue();
730
+ e !== this.effectiveValue && (this.$emit("update:modelValue", e), this.$emit("update:value", e));
731
+ }), this.$emit("editor-ready", this.editorInstance);
732
+ },
733
+ createExpandeEditorTray() {
734
+ let e;
735
+ const t = () => {
736
+ setTimeout(() => {
737
+ var i;
738
+ (i = this.editorInstance) == null || i.focus();
739
+ }, 250), RED.tray.close();
740
+ }, o = () => {
741
+ var i;
742
+ e.saveView(), (i = this.editorInstance) == null || i.setValue(e.getValue(), -1), setTimeout(() => {
743
+ var l, s;
744
+ (l = this.editorInstance) == null || l.restoreView(), (s = this.editorInstance) == null || s.focus();
745
+ }, 250), RED.tray.close();
746
+ };
747
+ this.expandedEditorTray = {
748
+ title: "Editor",
749
+ focusElement: !0,
750
+ width: "Infinity",
751
+ buttons: [
752
+ {
753
+ id: "node-dialog-cancel",
754
+ text: RED._("common.label.cancel"),
755
+ click: t
756
+ },
757
+ {
758
+ id: "node-dialog-ok",
759
+ text: RED._("common.label.done"),
760
+ class: "primary",
761
+ click: o
762
+ }
763
+ ],
764
+ open: (i) => {
765
+ const l = $(
766
+ '<form id="dialog-form" class="form-horizontal" autocomplete="off"></form>'
767
+ ).appendTo(i.find(".red-ui-tray-body"));
768
+ l.html(
769
+ '<div id="expanded-editor-input" style="height: 100%"></div>'
770
+ ), e = RED.editor.createEditor({
771
+ id: "expanded-editor-input",
772
+ stateId: this.stateId,
773
+ mode: this.language,
774
+ focus: !0,
775
+ value: this.effectiveValue
776
+ }), l.i18n();
777
+ const s = i.find(".red-ui-tray-body")[0], r = document.createElement("div");
778
+ r.className = "red-ui-tray-footer", s.insertAdjacentElement("afterend", r), this.trayElement = r, this.$emit("tray-open", this.trayElement);
779
+ },
780
+ close: () => {
781
+ this.$emit("tray-close"), this.trayElement && (this.trayElement.remove(), this.trayElement = null), e.destroy();
782
+ }
783
+ };
784
+ },
785
+ onClickExpand() {
786
+ RED.tray.show(this.expandedEditorTray);
787
+ }
788
+ }
789
+ }), me = {
790
+ ref: "container",
791
+ class: "container"
792
+ }, fe = { class: "editor-wrapper" }, ve = ["id"];
793
+ function ge(e, t, o, i, l, s) {
794
+ const r = h("NodeRedInputLabel");
795
+ return a(), u(
796
+ "div",
797
+ me,
798
+ [
799
+ I(e.$slots, "label", {}, () => [
800
+ e.label ? (a(), m(r, {
801
+ key: 0,
802
+ label: e.label,
803
+ icon: e.icon,
804
+ required: e.required
805
+ }, null, 8, ["label", "icon", "required"])) : p("v-if", !0)
806
+ ], !0),
807
+ c("div", fe, [
808
+ c(
809
+ "button",
810
+ {
811
+ ref: "expand-button",
812
+ class: "red-ui-button red-ui-button-small expand-button",
813
+ onClick: t[0] || (t[0] = (...f) => e.onClickExpand && e.onClickExpand(...f))
814
+ },
815
+ [...t[1] || (t[1] = [
816
+ c(
817
+ "i",
818
+ { class: "fa fa-expand" },
819
+ null,
820
+ -1
821
+ /* CACHED */
822
+ )
823
+ ])],
824
+ 512
825
+ /* NEED_PATCH */
826
+ ),
827
+ c("div", {
828
+ id: e.editorId,
829
+ ref: "editor"
830
+ }, null, 8, ve)
831
+ ]),
832
+ O(c(
833
+ "div",
834
+ { class: "node-red-vue-input-error-message" },
835
+ g(e.error),
836
+ 513
837
+ /* TEXT, NEED_PATCH */
838
+ ), [
839
+ [A, e.error]
840
+ ]),
841
+ e.trayElement ? (a(), m(W, {
842
+ key: 0,
843
+ to: e.trayElement
844
+ }, [
845
+ I(e.$slots, "tray-footer", {}, void 0, !0)
846
+ ], 8, ["to"])) : p("v-if", !0)
847
+ ],
848
+ 512
849
+ /* NEED_PATCH */
850
+ );
851
+ }
852
+ const be = /* @__PURE__ */ b(he, [["render", ge], ["__scopeId", "data-v-9e324115"]]), $e = v({
853
+ name: "NodeRedToggle",
854
+ props: {
855
+ modelValue: {
856
+ type: Boolean,
857
+ default: !1
858
+ },
859
+ label: {
860
+ type: String,
861
+ default: ""
862
+ },
863
+ icon: {
864
+ type: String,
865
+ default: ""
866
+ }
867
+ },
868
+ emits: ["update:modelValue"],
869
+ computed: {
870
+ iconClass() {
871
+ return this.icon ? `fa ${this.icon.startsWith("fa-") ? this.icon : `fa-${this.icon}`}` : "";
872
+ }
873
+ }
874
+ }), Ie = { class: "nrg-toggle-wrapper" }, Ve = ["checked"], Te = {
875
+ key: 0,
876
+ class: "nrg-toggle__label"
877
+ };
878
+ function ke(e, t, o, i, l, s) {
879
+ return a(), u("div", Ie, [
880
+ c(
881
+ "label",
882
+ {
883
+ class: E(["nrg-toggle", { "nrg-toggle--checked": e.modelValue }])
884
+ },
885
+ [
886
+ c("input", {
887
+ type: "checkbox",
888
+ checked: e.modelValue,
889
+ class: "nrg-toggle__input",
890
+ onChange: t[0] || (t[0] = (r) => e.$emit(
891
+ "update:modelValue",
892
+ r.target.checked
893
+ ))
894
+ }, null, 40, Ve),
895
+ e.icon || e.label ? (a(), u("span", Te, [
896
+ e.icon ? (a(), u(
897
+ "i",
898
+ {
899
+ key: 0,
900
+ class: E(e.iconClass)
901
+ },
902
+ null,
903
+ 2
904
+ /* CLASS */
905
+ )) : p("v-if", !0),
906
+ _(
907
+ " " + g(e.label),
908
+ 1
909
+ /* TEXT */
910
+ )
911
+ ])) : p("v-if", !0),
912
+ t[1] || (t[1] = c(
913
+ "span",
914
+ { class: "nrg-toggle__slider" },
915
+ null,
916
+ -1
917
+ /* CACHED */
918
+ ))
919
+ ],
920
+ 2
921
+ /* CLASS */
922
+ )
923
+ ]);
924
+ }
925
+ const we = /* @__PURE__ */ b($e, [["render", ke], ["__scopeId", "data-v-c6353798"]]), Ee = /* @__PURE__ */ new Set([
926
+ "id",
927
+ "type",
928
+ "x",
929
+ "y",
930
+ "z",
931
+ "g",
932
+ "wires",
933
+ "credentials",
934
+ "_users",
935
+ "validateInput",
936
+ "validateOutputs",
937
+ "outputs",
938
+ "outputContextModes",
939
+ "outputReturnProperties",
940
+ ...Z
941
+ ]);
942
+ function Re(e) {
943
+ return e.replace(/([A-Z])/g, " $1").replace(/^./, (t) => t.toUpperCase()).trim();
944
+ }
945
+ function qe(e) {
946
+ var t, o;
947
+ return e.type === "object" && !!((t = e.properties) != null && t.value) && !!((o = e.properties) != null && o.type);
948
+ }
949
+ function S(e, t, o, i) {
950
+ var k;
951
+ const l = i || t.title || Re(e), s = t["x-nrg-form"] ?? {}, r = s.icon || "";
952
+ if (t["x-nrg-node-type"])
953
+ return {
954
+ key: e,
955
+ label: l,
956
+ icon: r,
957
+ inputType: "config",
958
+ required: o,
959
+ configType: t["x-nrg-node-type"]
960
+ };
961
+ if (qe(t))
962
+ return {
963
+ key: e,
964
+ label: l,
965
+ icon: r,
966
+ inputType: "typed",
967
+ required: o,
968
+ // serialized schemas carry plain strings; trust them as typed-input type names
969
+ types: s.typedInputTypes
970
+ };
971
+ if (t.type === "array" && ((k = t.items) != null && k.enum))
972
+ return {
973
+ key: e,
974
+ label: l,
975
+ icon: r,
976
+ inputType: "select",
977
+ required: o,
978
+ multiple: !0,
979
+ options: t.items.enum.map((y) => ({
980
+ value: String(y),
981
+ label: String(y)
982
+ }))
983
+ };
984
+ if (t.enum)
985
+ return {
986
+ key: e,
987
+ label: l,
988
+ icon: r,
989
+ inputType: "select",
990
+ required: o,
991
+ multiple: !1,
992
+ options: t.enum.map((y) => ({
993
+ value: String(y),
994
+ label: String(y)
995
+ }))
996
+ };
997
+ if (t.anyOf && t.anyOf.every((y) => y.const !== void 0))
998
+ return {
999
+ key: e,
1000
+ label: l,
1001
+ icon: r,
1002
+ inputType: "select",
1003
+ required: o,
1004
+ multiple: !1,
1005
+ options: t.anyOf.map((y) => ({
1006
+ value: String(y.const),
1007
+ label: String(y.const)
1008
+ }))
1009
+ };
1010
+ switch (Array.isArray(t.type) ? t.type[0] : t.type) {
1011
+ case "boolean":
1012
+ return {
1013
+ key: e,
1014
+ label: l,
1015
+ icon: r,
1016
+ inputType: "boolean",
1017
+ required: o,
1018
+ toggle: s.toggle
1019
+ };
1020
+ case "number":
1021
+ case "integer":
1022
+ return {
1023
+ key: e,
1024
+ label: l,
1025
+ icon: r,
1026
+ inputType: "number",
1027
+ required: o,
1028
+ htmlType: "number"
1029
+ };
1030
+ case "array":
1031
+ return s.editorLanguage ? {
1032
+ key: e,
1033
+ label: l,
1034
+ icon: r,
1035
+ inputType: "editor",
1036
+ required: o,
1037
+ language: s.editorLanguage
1038
+ } : { key: e, label: l, icon: r, inputType: "array-text", required: o };
1039
+ case "object":
1040
+ return s.editorLanguage ? {
1041
+ key: e,
1042
+ label: l,
1043
+ icon: r,
1044
+ inputType: "editor",
1045
+ required: o,
1046
+ language: s.editorLanguage
1047
+ } : {
1048
+ key: e,
1049
+ label: l,
1050
+ icon: r,
1051
+ inputType: "text",
1052
+ required: o,
1053
+ htmlType: "text"
1054
+ };
1055
+ default:
1056
+ return s.editorLanguage ? {
1057
+ key: e,
1058
+ label: l,
1059
+ icon: r,
1060
+ inputType: "editor",
1061
+ required: o,
1062
+ language: s.editorLanguage
1063
+ } : {
1064
+ key: e,
1065
+ label: l,
1066
+ icon: r,
1067
+ inputType: "text",
1068
+ required: o,
1069
+ htmlType: t.format === "password" ? "password" : "text"
1070
+ };
1071
+ }
1072
+ }
1073
+ const Ne = v({
1074
+ name: "NodeRedJsonSchemaForm",
1075
+ components: {
1076
+ NodeRedInputLabel: T,
1077
+ NodeRedToggle: we,
1078
+ NodeRedInput: Y,
1079
+ NodeRedSelectInput: ye,
1080
+ NodeRedTypedInput: te,
1081
+ NodeRedConfigInput: le,
1082
+ NodeRedEditorInput: be
1083
+ },
1084
+ props: {
1085
+ node: {
1086
+ type: Object,
1087
+ required: !0
1088
+ },
1089
+ schema: {
1090
+ type: Object,
1091
+ required: !0
1092
+ },
1093
+ errors: {
1094
+ type: Object,
1095
+ default: () => ({})
1096
+ }
1097
+ },
1098
+ computed: {
1099
+ configFields() {
1100
+ var t;
1101
+ if (!((t = this.schema) != null && t.properties)) return [];
1102
+ const e = new Set(this.schema.required ?? []);
1103
+ return Object.entries(this.schema.properties).filter(([o]) => !Ee.has(o)).map(
1104
+ ([o, i]) => S(
1105
+ o,
1106
+ i,
1107
+ e.has(o),
1108
+ this.resolveI18n("configs", o)
1109
+ )
1110
+ );
1111
+ },
1112
+ credentialFields() {
1113
+ var o, i;
1114
+ const e = (i = (o = this.schema) == null ? void 0 : o.properties) == null ? void 0 : i.credentials;
1115
+ if (!(e != null && e.properties)) return [];
1116
+ const t = new Set(e.required ?? []);
1117
+ return Object.entries(e.properties).map(([l, s]) => {
1118
+ const r = S(
1119
+ l,
1120
+ s,
1121
+ t.has(l),
1122
+ this.resolveI18n("credentials", l)
1123
+ );
1124
+ return r.inputType !== "text" ? {
1125
+ ...r,
1126
+ inputType: "text",
1127
+ htmlType: s.format === "password" ? "password" : "text"
1128
+ } : r;
1129
+ });
1130
+ }
1131
+ },
1132
+ methods: {
1133
+ resolveI18n(e, t) {
1134
+ const o = this.$i18n(`${e}.${t}`), i = `${this.node.type}.${e}.${t}`;
1135
+ if (o && o !== i && o !== `${e}.${t}`)
1136
+ return o;
1137
+ }
1138
+ }
1139
+ }), Se = { key: 1 }, _e = { key: 2 }, je = ["checked", "onChange"], Ce = { key: 6 }, Le = ["value", "onInput"], Oe = {
1140
+ key: 0,
1141
+ class: "node-red-vue-input-error-message"
1142
+ };
1143
+ function Ae(e, t, o, i, l, s) {
1144
+ const r = h("NodeRedInput"), f = h("NodeRedToggle"), k = h("NodeRedInputLabel"), y = h("NodeRedSelectInput"), j = h("NodeRedTypedInput"), C = h("NodeRedConfigInput"), L = h("NodeRedEditorInput");
1145
+ return a(), u("div", null, [
1146
+ (a(!0), u(
1147
+ R,
1148
+ null,
1149
+ q(e.configFields, (n) => (a(), u("div", {
1150
+ key: n.key,
1151
+ class: "form-row"
1152
+ }, [
1153
+ n.inputType === "text" || n.inputType === "number" ? (a(), m(r, {
1154
+ key: 0,
1155
+ value: e.node[n.key],
1156
+ "onUpdate:value": (d) => e.node[n.key] = d,
1157
+ type: n.htmlType,
1158
+ label: n.label,
1159
+ icon: n.icon,
1160
+ required: n.required,
1161
+ error: e.errors[`node.${n.key}`]
1162
+ }, null, 8, ["value", "onUpdate:value", "type", "label", "icon", "required", "error"])) : n.inputType === "boolean" && n.toggle ? (a(), u("div", Se, [
1163
+ w(f, {
1164
+ "model-value": e.node[n.key],
1165
+ label: n.label,
1166
+ icon: n.icon,
1167
+ "onUpdate:modelValue": (d) => e.node[n.key] = d
1168
+ }, null, 8, ["model-value", "label", "icon", "onUpdate:modelValue"])
1169
+ ])) : n.inputType === "boolean" ? (a(), u("div", _e, [
1170
+ w(k, {
1171
+ label: n.label,
1172
+ icon: n.icon,
1173
+ required: n.required
1174
+ }, null, 8, ["label", "icon", "required"]),
1175
+ c("input", {
1176
+ type: "checkbox",
1177
+ checked: e.node[n.key],
1178
+ style: { width: "auto", margin: "0" },
1179
+ onChange: (d) => {
1180
+ e.node[n.key] = d.target.checked;
1181
+ }
1182
+ }, null, 40, je)
1183
+ ])) : n.inputType === "select" ? (a(), m(y, {
1184
+ key: 3,
1185
+ value: e.node[n.key],
1186
+ "onUpdate:value": (d) => e.node[n.key] = d,
1187
+ options: n.options,
1188
+ multiple: n.multiple,
1189
+ label: n.label,
1190
+ icon: n.icon,
1191
+ required: n.required,
1192
+ error: e.errors[`node.${n.key}`]
1193
+ }, null, 8, ["value", "onUpdate:value", "options", "multiple", "label", "icon", "required", "error"])) : n.inputType === "typed" ? (a(), m(j, {
1194
+ key: 4,
1195
+ value: e.node[n.key],
1196
+ "onUpdate:value": (d) => e.node[n.key] = d,
1197
+ types: n.types,
1198
+ label: n.label,
1199
+ icon: n.icon,
1200
+ required: n.required,
1201
+ error: e.errors[`node.${n.key}`]
1202
+ }, null, 8, ["value", "onUpdate:value", "types", "label", "icon", "required", "error"])) : n.inputType === "config" ? (a(), m(C, {
1203
+ key: 5,
1204
+ value: e.node[n.key],
1205
+ "onUpdate:value": (d) => e.node[n.key] = d,
1206
+ type: n.configType,
1207
+ node: e.node,
1208
+ "prop-name": n.key,
1209
+ label: n.label,
1210
+ icon: n.icon,
1211
+ required: n.required,
1212
+ error: e.errors[`node.${n.key}`]
1213
+ }, null, 8, ["value", "onUpdate:value", "type", "node", "prop-name", "label", "icon", "required", "error"])) : n.inputType === "array-text" ? (a(), u("div", Ce, [
1214
+ w(k, {
1215
+ label: n.label,
1216
+ icon: n.icon,
1217
+ required: n.required
1218
+ }, null, 8, ["label", "icon", "required"]),
1219
+ t[0] || (t[0] = c(
1220
+ "span",
1221
+ { style: { display: "block", "font-size": "11px", color: "var(--red-ui-text-color-disabled, #999)", "margin-bottom": "4px" } },
1222
+ " One entry per line ",
1223
+ -1
1224
+ /* CACHED */
1225
+ )),
1226
+ c("textarea", {
1227
+ value: Array.isArray(e.node[n.key]) ? e.node[n.key].join(`
1228
+ `) : e.node[n.key] ?? "",
1229
+ rows: "4",
1230
+ style: { width: "100%", resize: "vertical", "font-family": "monospace", "font-size": "13px" },
1231
+ onInput: (d) => e.node[n.key] = d.target.value.split(`
1232
+ `).filter(Boolean)
1233
+ }, null, 40, Le),
1234
+ e.errors[`node.${n.key}`] ? (a(), u(
1235
+ "span",
1236
+ Oe,
1237
+ g(e.errors[`node.${n.key}`]),
1238
+ 1
1239
+ /* TEXT */
1240
+ )) : p("v-if", !0)
1241
+ ])) : n.inputType === "editor" ? (a(), m(L, {
1242
+ key: 7,
1243
+ value: e.node[n.key],
1244
+ "onUpdate:value": (d) => e.node[n.key] = d,
1245
+ language: n.language,
1246
+ label: n.label,
1247
+ icon: n.icon,
1248
+ required: n.required,
1249
+ error: e.errors[`node.${n.key}`]
1250
+ }, null, 8, ["value", "onUpdate:value", "language", "label", "icon", "required", "error"])) : p("v-if", !0)
1251
+ ]))),
1252
+ 128
1253
+ /* KEYED_FRAGMENT */
1254
+ )),
1255
+ (a(!0), u(
1256
+ R,
1257
+ null,
1258
+ q(e.credentialFields, (n) => (a(), u("div", {
1259
+ key: `cred-${n.key}`,
1260
+ class: "form-row"
1261
+ }, [
1262
+ w(r, {
1263
+ value: e.node.credentials[n.key],
1264
+ "onUpdate:value": (d) => e.node.credentials[n.key] = d,
1265
+ type: n.htmlType,
1266
+ label: n.label,
1267
+ icon: n.icon,
1268
+ required: n.required,
1269
+ error: e.errors[`node.credentials.${n.key}`]
1270
+ }, null, 8, ["value", "onUpdate:value", "type", "label", "icon", "required", "error"])
1271
+ ]))),
1272
+ 128
1273
+ /* KEYED_FRAGMENT */
1274
+ ))
1275
+ ]);
1276
+ }
1277
+ const De = /* @__PURE__ */ b(Ne, [["render", Ae]]);
1278
+ export {
1279
+ le as NodeRedConfigInput,
1280
+ be as NodeRedEditorInput,
1281
+ Y as NodeRedInput,
1282
+ T as NodeRedInputLabel,
1283
+ De as NodeRedJsonSchemaForm,
1284
+ ye as NodeRedSelectInput,
1285
+ we as NodeRedToggle,
1286
+ te as NodeRedTypedInput
1287
+ };