@wral/report-it 0.1.4 → 0.2.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.
@@ -1,6 +1,222 @@
1
- import { css as f, html as a, nothing as c, LitElement as T } from "lit";
2
- import { getAuthContext as Q, createStorage as G, verifyCode as J, extractTokens as D, saveTokens as z, decodeJwtPayload as B, refreshTokenSimple as X, sendCode as Z, createUserPool as ee, signUpIfNeeded as te, createCognitoUser as re, getAuthHeaders as se, STORAGE_KEYS as I, isAuthenticatedSimple as ie } from "@wral/sdk-auth-audience";
3
- const ne = f`
1
+ import { css as y, html as c, nothing as f, LitElement as G } from "lit";
2
+ import { getAuthContext as Se, createStorage as Ce, verifyCode as Te, extractTokens as Z, saveTokens as X, decodeJwtPayload as ee, refreshTokenSimple as te, sendCode as Re, createUserPool as Me, signUpIfNeeded as De, createCognitoUser as Pe, STORAGE_KEYS as S, isAuthenticatedSimple as ze } from "@wral/sdk-auth-audience";
3
+ const K = globalThis, re = (s) => s, B = K.trustedTypes, se = B ? B.createPolicy("lit-html", { createHTML: (s) => s }) : void 0, xe = "$lit$", v = `lit$${Math.random().toFixed(9).slice(2)}$`, ve = "?" + v, Be = `<${ve}>`, A = document, O = () => A.createComment(""), R = (s) => s === null || typeof s != "object" && typeof s != "function", Q = Array.isArray, Oe = (s) => Q(s) || typeof s?.[Symbol.iterator] == "function", H = `[
4
+ \f\r]`, C = /<(?:(!--|\/[^a-zA-Z])|(\/?[a-zA-Z][^>\s]*)|(\/?$))/g, ie = /-->/g, ne = />/g, $ = RegExp(`>|${H}(?:([^\\s"'>=/]+)(${H}*=${H}*(?:[^
5
+ \f\r"'\`<>=]|("|')|))|$)`, "g"), oe = /'/g, ae = /"/g, _e = /^(?:script|style|textarea|title)$/i, M = /* @__PURE__ */ Symbol.for("lit-noChange"), m = /* @__PURE__ */ Symbol.for("lit-nothing"), le = /* @__PURE__ */ new WeakMap(), k = A.createTreeWalker(A, 129);
6
+ function $e(s, e) {
7
+ if (!Q(s) || !s.hasOwnProperty("raw")) throw Error("invalid template strings array");
8
+ return se !== void 0 ? se.createHTML(e) : e;
9
+ }
10
+ const Ue = (s, e) => {
11
+ const t = s.length - 1, r = [];
12
+ let i, n = e === 2 ? "<svg>" : e === 3 ? "<math>" : "", o = C;
13
+ for (let a = 0; a < t; a++) {
14
+ const l = s[a];
15
+ let d, p, u = -1, h = 0;
16
+ for (; h < l.length && (o.lastIndex = h, p = o.exec(l), p !== null); ) h = o.lastIndex, o === C ? p[1] === "!--" ? o = ie : p[1] !== void 0 ? o = ne : p[2] !== void 0 ? (_e.test(p[2]) && (i = RegExp("</" + p[2], "g")), o = $) : p[3] !== void 0 && (o = $) : o === $ ? p[0] === ">" ? (o = i ?? C, u = -1) : p[1] === void 0 ? u = -2 : (u = o.lastIndex - p[2].length, d = p[1], o = p[3] === void 0 ? $ : p[3] === '"' ? ae : oe) : o === ae || o === oe ? o = $ : o === ie || o === ne ? o = C : (o = $, i = void 0);
17
+ const b = o === $ && s[a + 1].startsWith("/>") ? " " : "";
18
+ n += o === C ? l + Be : u >= 0 ? (r.push(d), l.slice(0, u) + xe + l.slice(u) + v + b) : l + v + (u === -2 ? a : b);
19
+ }
20
+ return [$e(s, n + (s[t] || "<?>") + (e === 2 ? "</svg>" : e === 3 ? "</math>" : "")), r];
21
+ };
22
+ class D {
23
+ constructor({ strings: e, _$litType$: t }, r) {
24
+ let i;
25
+ this.parts = [];
26
+ let n = 0, o = 0;
27
+ const a = e.length - 1, l = this.parts, [d, p] = Ue(e, t);
28
+ if (this.el = D.createElement(d, r), k.currentNode = this.el.content, t === 2 || t === 3) {
29
+ const u = this.el.content.firstChild;
30
+ u.replaceWith(...u.childNodes);
31
+ }
32
+ for (; (i = k.nextNode()) !== null && l.length < a; ) {
33
+ if (i.nodeType === 1) {
34
+ if (i.hasAttributes()) for (const u of i.getAttributeNames()) if (u.endsWith(xe)) {
35
+ const h = p[o++], b = i.getAttribute(u).split(v), w = /([.?@])?(.*)/.exec(h);
36
+ l.push({ type: 1, index: n, name: w[2], strings: b, ctor: w[1] === "." ? Ne : w[1] === "?" ? qe : w[1] === "@" ? He : L }), i.removeAttribute(u);
37
+ } else u.startsWith(v) && (l.push({ type: 6, index: n }), i.removeAttribute(u));
38
+ if (_e.test(i.tagName)) {
39
+ const u = i.textContent.split(v), h = u.length - 1;
40
+ if (h > 0) {
41
+ i.textContent = B ? B.emptyScript : "";
42
+ for (let b = 0; b < h; b++) i.append(u[b], O()), k.nextNode(), l.push({ type: 2, index: ++n });
43
+ i.append(u[h], O());
44
+ }
45
+ }
46
+ } else if (i.nodeType === 8) if (i.data === ve) l.push({ type: 2, index: n });
47
+ else {
48
+ let u = -1;
49
+ for (; (u = i.data.indexOf(v, u + 1)) !== -1; ) l.push({ type: 7, index: n }), u += v.length - 1;
50
+ }
51
+ n++;
52
+ }
53
+ }
54
+ static createElement(e, t) {
55
+ const r = A.createElement("template");
56
+ return r.innerHTML = e, r;
57
+ }
58
+ }
59
+ function E(s, e, t = s, r) {
60
+ if (e === M) return e;
61
+ let i = r !== void 0 ? t._$Co?.[r] : t._$Cl;
62
+ const n = R(e) ? void 0 : e._$litDirective$;
63
+ return i?.constructor !== n && (i?._$AO?.(!1), n === void 0 ? i = void 0 : (i = new n(s), i._$AT(s, t, r)), r !== void 0 ? (t._$Co ??= [])[r] = i : t._$Cl = i), i !== void 0 && (e = E(s, i._$AS(s, e.values), i, r)), e;
64
+ }
65
+ class Le {
66
+ constructor(e, t) {
67
+ this._$AV = [], this._$AN = void 0, this._$AD = e, this._$AM = t;
68
+ }
69
+ get parentNode() {
70
+ return this._$AM.parentNode;
71
+ }
72
+ get _$AU() {
73
+ return this._$AM._$AU;
74
+ }
75
+ u(e) {
76
+ const { el: { content: t }, parts: r } = this._$AD, i = (e?.creationScope ?? A).importNode(t, !0);
77
+ k.currentNode = i;
78
+ let n = k.nextNode(), o = 0, a = 0, l = r[0];
79
+ for (; l !== void 0; ) {
80
+ if (o === l.index) {
81
+ let d;
82
+ l.type === 2 ? d = new U(n, n.nextSibling, this, e) : l.type === 1 ? d = new l.ctor(n, l.name, l.strings, this, e) : l.type === 6 && (d = new je(n, this, e)), this._$AV.push(d), l = r[++a];
83
+ }
84
+ o !== l?.index && (n = k.nextNode(), o++);
85
+ }
86
+ return k.currentNode = A, i;
87
+ }
88
+ p(e) {
89
+ let t = 0;
90
+ for (const r of this._$AV) r !== void 0 && (r.strings !== void 0 ? (r._$AI(e, r, t), t += r.strings.length - 2) : r._$AI(e[t])), t++;
91
+ }
92
+ }
93
+ class U {
94
+ get _$AU() {
95
+ return this._$AM?._$AU ?? this._$Cv;
96
+ }
97
+ constructor(e, t, r, i) {
98
+ this.type = 2, this._$AH = m, this._$AN = void 0, this._$AA = e, this._$AB = t, this._$AM = r, this.options = i, this._$Cv = i?.isConnected ?? !0;
99
+ }
100
+ get parentNode() {
101
+ let e = this._$AA.parentNode;
102
+ const t = this._$AM;
103
+ return t !== void 0 && e?.nodeType === 11 && (e = t.parentNode), e;
104
+ }
105
+ get startNode() {
106
+ return this._$AA;
107
+ }
108
+ get endNode() {
109
+ return this._$AB;
110
+ }
111
+ _$AI(e, t = this) {
112
+ e = E(this, e, t), R(e) ? e === m || e == null || e === "" ? (this._$AH !== m && this._$AR(), this._$AH = m) : e !== this._$AH && e !== M && this._(e) : e._$litType$ !== void 0 ? this.$(e) : e.nodeType !== void 0 ? this.T(e) : Oe(e) ? this.k(e) : this._(e);
113
+ }
114
+ O(e) {
115
+ return this._$AA.parentNode.insertBefore(e, this._$AB);
116
+ }
117
+ T(e) {
118
+ this._$AH !== e && (this._$AR(), this._$AH = this.O(e));
119
+ }
120
+ _(e) {
121
+ this._$AH !== m && R(this._$AH) ? this._$AA.nextSibling.data = e : this.T(A.createTextNode(e)), this._$AH = e;
122
+ }
123
+ $(e) {
124
+ const { values: t, _$litType$: r } = e, i = typeof r == "number" ? this._$AC(e) : (r.el === void 0 && (r.el = D.createElement($e(r.h, r.h[0]), this.options)), r);
125
+ if (this._$AH?._$AD === i) this._$AH.p(t);
126
+ else {
127
+ const n = new Le(i, this), o = n.u(this.options);
128
+ n.p(t), this.T(o), this._$AH = n;
129
+ }
130
+ }
131
+ _$AC(e) {
132
+ let t = le.get(e.strings);
133
+ return t === void 0 && le.set(e.strings, t = new D(e)), t;
134
+ }
135
+ k(e) {
136
+ Q(this._$AH) || (this._$AH = [], this._$AR());
137
+ const t = this._$AH;
138
+ let r, i = 0;
139
+ for (const n of e) i === t.length ? t.push(r = new U(this.O(O()), this.O(O()), this, this.options)) : r = t[i], r._$AI(n), i++;
140
+ i < t.length && (this._$AR(r && r._$AB.nextSibling, i), t.length = i);
141
+ }
142
+ _$AR(e = this._$AA.nextSibling, t) {
143
+ for (this._$AP?.(!1, !0, t); e !== this._$AB; ) {
144
+ const r = re(e).nextSibling;
145
+ re(e).remove(), e = r;
146
+ }
147
+ }
148
+ setConnected(e) {
149
+ this._$AM === void 0 && (this._$Cv = e, this._$AP?.(e));
150
+ }
151
+ }
152
+ class L {
153
+ get tagName() {
154
+ return this.element.tagName;
155
+ }
156
+ get _$AU() {
157
+ return this._$AM._$AU;
158
+ }
159
+ constructor(e, t, r, i, n) {
160
+ this.type = 1, this._$AH = m, this._$AN = void 0, this.element = e, this.name = t, this._$AM = i, this.options = n, r.length > 2 || r[0] !== "" || r[1] !== "" ? (this._$AH = Array(r.length - 1).fill(new String()), this.strings = r) : this._$AH = m;
161
+ }
162
+ _$AI(e, t = this, r, i) {
163
+ const n = this.strings;
164
+ let o = !1;
165
+ if (n === void 0) e = E(this, e, t, 0), o = !R(e) || e !== this._$AH && e !== M, o && (this._$AH = e);
166
+ else {
167
+ const a = e;
168
+ let l, d;
169
+ for (e = n[0], l = 0; l < n.length - 1; l++) d = E(this, a[r + l], t, l), d === M && (d = this._$AH[l]), o ||= !R(d) || d !== this._$AH[l], d === m ? e = m : e !== m && (e += (d ?? "") + n[l + 1]), this._$AH[l] = d;
170
+ }
171
+ o && !i && this.j(e);
172
+ }
173
+ j(e) {
174
+ e === m ? this.element.removeAttribute(this.name) : this.element.setAttribute(this.name, e ?? "");
175
+ }
176
+ }
177
+ class Ne extends L {
178
+ constructor() {
179
+ super(...arguments), this.type = 3;
180
+ }
181
+ j(e) {
182
+ this.element[this.name] = e === m ? void 0 : e;
183
+ }
184
+ }
185
+ class qe extends L {
186
+ constructor() {
187
+ super(...arguments), this.type = 4;
188
+ }
189
+ j(e) {
190
+ this.element.toggleAttribute(this.name, !!e && e !== m);
191
+ }
192
+ }
193
+ class He extends L {
194
+ constructor(e, t, r, i, n) {
195
+ super(e, t, r, i, n), this.type = 5;
196
+ }
197
+ _$AI(e, t = this) {
198
+ if ((e = E(this, e, t, 0) ?? m) === M) return;
199
+ const r = this._$AH, i = e === m && r !== m || e.capture !== r.capture || e.once !== r.once || e.passive !== r.passive, n = e !== m && (r === m || i);
200
+ i && this.element.removeEventListener(this.name, this, r), n && this.element.addEventListener(this.name, this, e), this._$AH = e;
201
+ }
202
+ handleEvent(e) {
203
+ typeof this._$AH == "function" ? this._$AH.call(this.options?.host ?? this.element, e) : this._$AH.handleEvent(e);
204
+ }
205
+ }
206
+ class je {
207
+ constructor(e, t, r) {
208
+ this.element = e, this.type = 6, this._$AN = void 0, this._$AM = t, this.options = r;
209
+ }
210
+ get _$AU() {
211
+ return this._$AM._$AU;
212
+ }
213
+ _$AI(e) {
214
+ E(this, e);
215
+ }
216
+ }
217
+ const We = K.litHtmlPolyfillSupport;
218
+ We?.(D, U), (K.litHtmlVersions ??= []).push("3.3.3");
219
+ const ce = (s) => s ?? m, Ve = y`
4
220
  :host {
5
221
  display: block;
6
222
  box-sizing: border-box;
@@ -24,7 +240,7 @@ const ne = f`
24
240
  position: absolute; width: 1px; height: 1px; overflow: hidden;
25
241
  clip: rect(0 0 0 0); white-space: nowrap;
26
242
  }
27
- `, ae = f`
243
+ `, Ye = y`
28
244
  @keyframes pop-in {
29
245
  0% { opacity: 0; transform: translateY(16px) scale(0.95); }
30
246
  100% { opacity: 1; transform: translateY(0) scale(1); }
@@ -55,7 +271,7 @@ const ne = f`
55
271
  animation: none !important;
56
272
  }
57
273
  }
58
- `, oe = f`
274
+ `, Ge = y`
59
275
  .msg { max-width: 85%; padding: 12px 16px; border-radius: 14px; font-size: 15px; }
60
276
  .msg.bot {
61
277
  background: var(--wral-semantic-surface-default, #FFFFFF);
@@ -77,7 +293,7 @@ const ne = f`
77
293
  .msg .sub { display: block; font-size: 13px; color: var(--wral-semantic-fg-muted, #64748B); margin-top: 4px; }
78
294
  .msg.user .sub { color: rgba(255, 255, 255, 0.75); }
79
295
  .msg.error { border-left: 3px solid var(--wral-base-red-on-light, #D1232A); }
80
- `, le = f`
296
+ `, Ke = y`
81
297
  .options { display: flex; flex-wrap: wrap; gap: 8px; align-self: flex-start; max-width: 92%; padding: 2px 0 6px; }
82
298
  .chip {
83
299
  font-family: var(--wral-base-font-ui, 'IBM Plex Sans Condensed', sans-serif);
@@ -91,7 +307,7 @@ const ne = f`
91
307
  .chip:hover { background: var(--wral-base-secondary-1, #2594E3); color: #FFFFFF; }
92
308
  .chip:focus-visible { outline: 2px solid var(--wral-base-secondary-1, #2594E3); outline-offset: 2px; }
93
309
  .chip:active { transform: scale(0.97); }
94
- `, de = f`
310
+ `, Qe = y`
95
311
  .form-card {
96
312
  align-self: stretch;
97
313
  background: var(--wral-semantic-surface-default, #FFFFFF);
@@ -156,7 +372,7 @@ const ne = f`
156
372
  .btn-ghost:hover { border-color: var(--wral-base-secondary-1, #2594E3); }
157
373
  .btn-ghost:active { transform: scale(0.97); }
158
374
  .btn-ghost:focus-visible { outline: 2px solid var(--wral-base-secondary-1, #2594E3); outline-offset: 2px; }
159
- `, ce = f`
375
+ `, Je = y`
160
376
  .login-card { padding: 28px 26px; }
161
377
  .login-card h2 {
162
378
  font-family: var(--wral-base-font-display, 'IBM Plex Sans Condensed', sans-serif);
@@ -243,7 +459,7 @@ const ne = f`
243
459
  .anon-costs .x { flex-shrink: 0; font-weight: 700; color: var(--wral-base-red-on-light, #D1232A); }
244
460
  .anon-actions { display: flex; flex-direction: column; gap: 10px; }
245
461
  .anon-actions .btn-ghost { width: 100%; }
246
- `, ue = f`
462
+ `, Ze = y`
247
463
  .review-list { margin: 0; padding: 0; list-style: none; font-size: 14px; }
248
464
  .review-list li {
249
465
  display: grid; grid-template-columns: 130px 1fr; gap: 10px;
@@ -275,7 +491,7 @@ const ne = f`
275
491
  color: var(--wral-base-primary-1, #001D68);
276
492
  }
277
493
  @media (max-width: 540px) { .review-list li { grid-template-columns: 1fr; gap: 2px; } }
278
- `, pe = f`
494
+ `, Xe = y`
279
495
  .upload-row { display: flex; align-items: center; gap: 10px; padding: 7px 0; font-size: 13.5px; }
280
496
  .upload-row .name { flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
281
497
  .upload-row .state { font-size: 12px; color: var(--wral-semantic-fg-subtle, #64748B); }
@@ -291,7 +507,7 @@ const ne = f`
291
507
  border-radius: 999px; padding: 3px 12px; cursor: pointer;
292
508
  }
293
509
  .retry-chip:focus-visible { outline: 2px solid var(--wral-base-secondary-1, #2594E3); outline-offset: 2px; }
294
- `, he = f`
510
+ `, et = y`
295
511
  .confirm-card {
296
512
  align-self: stretch;
297
513
  background: var(--wral-base-primary-1, #001D68);
@@ -341,7 +557,7 @@ const ne = f`
341
557
  .c-again:hover { background: rgba(255, 255, 255, 0.12); }
342
558
  .c-again:focus-visible { outline: 2px solid var(--wral-base-secondary-2, #50A9E8); outline-offset: 2px; }
343
559
  .c-again:active { transform: scale(0.97); }
344
- `, fe = f`
560
+ `, tt = y`
345
561
  .journey {
346
562
  align-self: stretch;
347
563
  background: var(--wral-semantic-surface-default, #FFFFFF);
@@ -382,7 +598,7 @@ const ne = f`
382
598
  color: var(--wral-base-primary-1, #001D68); margin-bottom: 2px;
383
599
  }
384
600
  .j-body .j-d { font-size: 13.5px; color: var(--wral-semantic-fg-muted, #475569); line-height: 1.55; }
385
- `, ge = f`
601
+ `, rt = y`
386
602
  .bottom-bar {
387
603
  position: sticky; bottom: 0; z-index: 20;
388
604
  background: var(--wral-semantic-surface-default, #FFFFFF);
@@ -395,74 +611,74 @@ const ne = f`
395
611
  }
396
612
  .bottom-bar .note { margin-left: auto; font-size: 12px; color: var(--wral-semantic-fg-subtle, #64748B); }
397
613
  @media (max-width: 540px) { .bottom-bar .note { display: none; } }
398
- `, me = [ne, ae, oe, le, de, ce, ue, pe, he, fe, ge];
399
- function h(r, e, { noAnim: t = !1, error: s = !1 } = {}) {
400
- return a`
401
- <div class="msg bot ${t ? "no-anim" : ""} ${s ? "error" : ""}">
402
- <span class="lead">${r}</span>
403
- ${e ? a`<span class="sub">${e}</span>` : c}
614
+ `, st = [Ve, Ye, Ge, Ke, Qe, Je, Ze, Xe, et, tt, rt];
615
+ function g(s, e, { noAnim: t = !1, error: r = !1 } = {}) {
616
+ return c`
617
+ <div class="msg bot ${t ? "no-anim" : ""} ${r ? "error" : ""}">
618
+ <span class="lead">${s}</span>
619
+ ${e ? c`<span class="sub">${e}</span>` : f}
404
620
  </div>
405
621
  `;
406
622
  }
407
- function $(r, { noAnim: e = !1 } = {}) {
408
- return a`<div class="msg user ${e ? "no-anim" : ""}">${r}</div>`;
623
+ function F(s, { noAnim: e = !1 } = {}) {
624
+ return c`<div class="msg user ${e ? "no-anim" : ""}">${s}</div>`;
409
625
  }
410
- function E() {
411
- return a`<div class="msg bot typing"><span></span><span></span><span></span></div>`;
626
+ function j() {
627
+ return c`<div class="msg bot typing"><span></span><span></span><span></span></div>`;
412
628
  }
413
- function be(r) {
414
- return r ? a`<span class="flag-pill ${r}">${r === "urgent" ? "Urgent" : "Moderate"}</span>` : c;
629
+ function it(s) {
630
+ return s ? c`<span class="flag-pill ${s}">${s === "urgent" ? "Urgent" : "Moderate"}</span>` : f;
415
631
  }
416
- function ye() {
417
- return a`
632
+ function nt() {
633
+ return c`
418
634
  <svg viewBox="0 0 24 24" fill="none" stroke="#FFFFFF" stroke-width="3"
419
635
  stroke-linecap="round" stroke-linejoin="round" width="20" height="20"
420
636
  aria-hidden="true"><path d="M20 6L9 17l-5-5"/></svg>
421
637
  `;
422
638
  }
423
- const we = 15e3;
424
- class x extends Error {
639
+ const ot = 15e3;
640
+ class I extends Error {
425
641
  constructor(e, t) {
426
642
  super(`api-forms request failed with status ${e}`), this.status = e, this.body = t;
427
643
  }
428
644
  }
429
- const P = Object.freeze({ enabled: !1, humanCheck: null });
430
- function xe({
431
- baseUrl: r,
645
+ const de = Object.freeze({ enabled: !1, humanCheck: null });
646
+ function at({
647
+ baseUrl: s,
432
648
  fetchFn: e = (...i) => fetch(...i),
433
649
  xhrFactory: t = () => new XMLHttpRequest(),
434
- getAuthHeaders: s
650
+ getAuthHeaders: r
435
651
  }) {
436
- const i = String(r || "").replace(/\/+$/, "");
437
- let n = P, o = null;
438
- async function l(d, { method: u = "GET", body: g, auth: y = !1, timeoutMs: p } = {}) {
439
- const k = { Accept: "application/json" };
440
- y && Object.assign(k, o ? { Authorization: `Bearer ${o}` } : await s()), g !== void 0 && (k["Content-Type"] = "application/json");
652
+ const i = String(s || "").replace(/\/+$/, "");
653
+ let n = de, o = null;
654
+ async function a(l, { method: d = "GET", body: p, auth: u = !1, timeoutMs: h } = {}) {
655
+ const b = { Accept: "application/json" };
656
+ u && Object.assign(b, o ? { Authorization: `Bearer ${o}` } : await r()), p !== void 0 && (b["Content-Type"] = "application/json");
441
657
  let w;
442
658
  try {
443
- w = await e(`${i}${d}`, {
444
- method: u,
445
- headers: k,
446
- ...p ? { signal: AbortSignal.timeout(p) } : {},
447
- ...g !== void 0 ? { body: JSON.stringify(g) } : {}
659
+ w = await e(`${i}${l}`, {
660
+ method: d,
661
+ headers: b,
662
+ ...h ? { signal: AbortSignal.timeout(h) } : {},
663
+ ...p !== void 0 ? { body: JSON.stringify(p) } : {}
448
664
  });
449
- } catch (_) {
450
- throw Object.assign(new x(0, null), { cause: _ });
665
+ } catch (P) {
666
+ throw Object.assign(new I(0, null), { cause: P });
451
667
  }
452
- let m = null;
668
+ let _ = null;
453
669
  try {
454
- m = await w.json();
670
+ _ = await w.json();
455
671
  } catch {
456
672
  }
457
673
  if (!w.ok)
458
- throw new x(w.status, m);
459
- return m;
674
+ throw new I(w.status, _);
675
+ return _;
460
676
  }
461
677
  return {
462
678
  /** @returns {Promise<Array>} published form documents */
463
679
  listForms: async () => {
464
- const d = await l("/v1/forms", { timeoutMs: we });
465
- return n = d?.anonymous?.enabled === !0 ? { enabled: !0, humanCheck: d.anonymous.humanCheck || null } : P, (d?.forms || []).filter((u) => u?.formId && u?.start && Array.isArray(u?.nodes));
680
+ const l = await a("/v1/forms", { timeoutMs: ot });
681
+ return n = l?.anonymous?.enabled === !0 ? { enabled: !0, humanCheck: l.anonymous.humanCheck || null } : de, (l?.forms || []).filter((d) => d?.formId && d?.start && Array.isArray(d?.nodes));
466
682
  },
467
683
  /**
468
684
  * What the server advertised on the last listForms.
@@ -474,66 +690,91 @@ function xe({
474
690
  * calls present it until endAnonSession(). Unauthenticated by design.
475
691
  * @returns {Promise<{expiresIn: number}>}
476
692
  */
477
- createAnonSession: async ({ formId: d, requestId: u, humanToken: g }) => {
478
- const y = await l("/v1/anon/sessions", {
693
+ createAnonSession: async ({ formId: l, requestId: d, humanToken: p }) => {
694
+ const u = await a("/v1/anon/sessions", {
479
695
  method: "POST",
480
- body: { formId: d, requestId: u, ...g ? { humanToken: g } : {} }
696
+ body: { formId: l, requestId: d, ...p ? { humanToken: p } : {} }
481
697
  });
482
- if (o = y?.token || null, !o)
483
- throw new x(502, { message: "The anonymous session had no token" });
484
- return { expiresIn: y.expiresIn };
698
+ if (o = u?.token || null, !o)
699
+ throw new I(502, { message: "The anonymous session had no token" });
700
+ return { expiresIn: u.expiresIn };
485
701
  },
486
702
  /** Drop the anonymous session so identity headers apply again. */
487
703
  endAnonSession: () => {
488
704
  o = null;
489
705
  },
490
706
  /** @returns {Promise<Array<{assetId,url,method,expires,assetUrl}>>} */
491
- createUploads: async (d) => {
492
- const { uploads: u } = await l("/v1/uploads", { method: "POST", body: d, auth: !0 });
493
- return u || [];
707
+ createUploads: async (l) => {
708
+ const { uploads: d } = await a("/v1/uploads", { method: "POST", body: l, auth: !0 });
709
+ return d || [];
494
710
  },
495
711
  /**
496
712
  * PUT one file to its presigned URL. XHR (not fetch) so upload
497
713
  * progress is observable. Resolves on 2xx; rejects with
498
714
  * ApiError(status) otherwise. Returns { promise, abort }.
499
715
  */
500
- uploadFile: ({ url: d, file: u, contentType: g, onProgress: y = () => {
716
+ uploadFile: ({ url: l, file: d, contentType: p, onProgress: u = () => {
501
717
  } }) => {
502
- const p = t();
503
- return { promise: new Promise((w, m) => {
504
- p.open("PUT", d), p.setRequestHeader("Content-Type", g || u.type), p.upload && (p.upload.onprogress = (_) => {
505
- y({ loaded: _.loaded, total: _.total || u.size });
506
- }), p.onload = () => {
507
- p.status >= 200 && p.status < 300 ? w({ status: p.status }) : m(new x(p.status, null));
508
- }, p.onerror = () => m(new x(0, null)), p.onabort = () => m(new x(0, { aborted: !0 })), p.send(u);
509
- }), abort: () => p.abort() };
718
+ const h = t();
719
+ return { promise: new Promise((w, _) => {
720
+ h.open("PUT", l), h.setRequestHeader("Content-Type", p || d.type), h.upload && (h.upload.onprogress = (P) => {
721
+ u({ loaded: P.loaded, total: P.total || d.size });
722
+ }), h.onload = () => {
723
+ h.status >= 200 && h.status < 300 ? w({ status: h.status }) : _(new I(h.status, null));
724
+ }, h.onerror = () => _(new I(0, null)), h.onabort = () => _(new I(0, { aborted: !0 })), h.send(d);
725
+ }), abort: () => h.abort() };
510
726
  },
511
727
  /** @returns {Promise<{requestId,reference,confirmation,routing}>} */
512
- putRequest: async (d, u) => await l(`/v1/requests/${d}`, { method: "PUT", body: u, auth: !0 })
728
+ putRequest: async (l, d) => await a(`/v1/requests/${l}`, { method: "PUT", body: d, auth: !0 })
729
+ };
730
+ }
731
+ const ue = 60 * 1e3;
732
+ async function lt({ read: s, refresh: e, now: t = Date.now }) {
733
+ const r = (n) => {
734
+ const { token: o, expiry: a } = s() || {};
735
+ return o && Number(a) - n > t() ? o : null;
513
736
  };
737
+ let i = r(ue);
738
+ if (!i) {
739
+ try {
740
+ await e();
741
+ } catch {
742
+ }
743
+ i = r(ue) || r(0);
744
+ }
745
+ if (!i)
746
+ throw Object.assign(new Error("Please sign in again to continue."), { status: 401, body: null });
747
+ return { Authorization: `Bearer ${i}` };
514
748
  }
515
- function ve() {
516
- const { config: r, storage: e } = Q();
749
+ function ct() {
750
+ const { config: s, storage: e } = Se();
517
751
  let t = null;
518
752
  return {
519
- isAuthenticated: () => ie(),
520
- signedInEmail: () => e.get(I.userEmail) || null,
521
- getAuthHeaders: () => se(r, e),
753
+ isAuthenticated: () => ze(),
754
+ signedInEmail: () => e.get(S.userEmail) || null,
755
+ /* The ID token, so api-forms can record the verified email (../lib/id-token.mjs). */
756
+ getAuthHeaders: () => lt({
757
+ read: () => ({
758
+ token: e.get(S.idToken),
759
+ expiry: e.get(S.idTokenExpiry)
760
+ }),
761
+ refresh: () => te()
762
+ }),
522
763
  /**
523
764
  * Email step. Keeps the challenge user in memory for verifyCode.
524
765
  * @returns {{challengeRequired?: boolean, authenticated?: boolean}}
525
766
  */
526
- sendCode: async (s) => {
527
- const i = await Z(
528
- r,
767
+ sendCode: async (r) => {
768
+ const i = await Re(
529
769
  s,
770
+ r,
530
771
  e,
531
- ee,
532
- te,
533
- re,
534
- D,
535
- z,
536
- B
772
+ Me,
773
+ De,
774
+ Pe,
775
+ Z,
776
+ X,
777
+ ee
537
778
  );
538
779
  return t = i.cognitoUser || null, {
539
780
  challengeRequired: !!i.challengeRequired,
@@ -544,118 +785,197 @@ function ve() {
544
785
  * Code step; refreshes immediately after verify so the session
545
786
  * starts with a full lifetime (house pattern).
546
787
  */
547
- verifyCode: async (s) => {
788
+ verifyCode: async (r) => {
548
789
  if (!t)
549
790
  throw new Error("Please enter your email again to get a new code.");
550
791
  try {
551
- await J(
792
+ await Te(
552
793
  t,
553
- s,
794
+ r,
554
795
  e,
555
- D,
556
- z,
557
- B
796
+ Z,
797
+ X,
798
+ ee
558
799
  );
559
800
  } catch {
560
801
  throw new Error("Invalid or expired code. Please request a new one and try again.");
561
802
  }
562
- return await X(), { success: !0 };
803
+ return await te(), { success: !0 };
563
804
  },
564
805
  /** Local sign-out only ("use a different email"). */
565
806
  signOut: () => {
566
- t = null, G().clear();
807
+ t = null, Ce().clear();
567
808
  },
568
809
  /**
569
810
  * Detect a login completed in ANOTHER tab (the storage event
570
811
  * never fires in the tab that wrote). Returns an unsubscribe.
571
812
  */
572
- onCrossTabLogin: (s) => {
813
+ onCrossTabLogin: (r) => {
573
814
  const i = (n) => {
574
- (n.key === I.accessToken || n.key === I.idToken) && s();
815
+ (n.key === S.accessToken || n.key === S.idToken) && r();
575
816
  };
576
817
  return window.addEventListener("storage", i), () => window.removeEventListener("storage", i);
577
818
  }
578
819
  };
579
820
  }
580
- function ke({ baseUrl: r }) {
581
- const e = ve();
582
- return { ...xe({ baseUrl: r, getAuthHeaders: e.getAuthHeaders }), ...e };
821
+ function dt({ baseUrl: s }) {
822
+ const e = ct();
823
+ return { ...at({ baseUrl: s, getAuthHeaders: e.getAuthHeaders }), ...e };
824
+ }
825
+ function x(s, e) {
826
+ return (s?.nodes || []).find((t) => t.id === e);
583
827
  }
584
- function b(r, e) {
585
- return (r?.nodes || []).find((t) => t.id === e);
828
+ function N(s) {
829
+ return s?.form ? { formId: s.form, path: [...s.path || []] } : null;
586
830
  }
587
- function V(r, e = []) {
831
+ function q(s, e = []) {
588
832
  const t = [];
589
- let s = r?.start;
833
+ let r = s?.start;
590
834
  for (const n of e) {
591
- const o = b(r, s);
835
+ const o = x(s, r);
592
836
  if (!o)
593
- return { nodeId: null, node: null, flags: t, error: { step: n, reason: `unknown node: ${s}` } };
837
+ return { nodeId: null, node: null, flags: t, error: { step: n, reason: `unknown node: ${r}` } };
594
838
  if (o.type === "terminal" || o.type === "redirect")
595
839
  return { nodeId: null, node: null, flags: t, error: { step: n, reason: `steps continue past ${o.type}` } };
596
- if (n.nodeId !== s || n.kind !== o.type)
597
- return { nodeId: null, node: null, flags: t, error: { step: n, reason: `step does not match node ${s}` } };
840
+ if (n.nodeId !== r || n.kind !== o.type)
841
+ return { nodeId: null, node: null, flags: t, error: { step: n, reason: `step does not match node ${r}` } };
598
842
  if (o.type === "choice") {
599
- const l = (o.options || []).find((d) => d.id === n.optionId);
600
- if (!l)
843
+ const a = (o.options || []).find((l) => l.id === n.optionId);
844
+ if (!a)
601
845
  return { nodeId: null, node: null, flags: t, error: { step: n, reason: `unknown option: ${n.optionId}` } };
602
- t.push(...l.flags || []), s = l.next;
846
+ if (N(a))
847
+ return { nodeId: null, node: null, flags: t, error: { step: n, reason: `steps continue past a hand-off: ${n.optionId}` } };
848
+ t.push(...a.flags || []), r = a.next;
603
849
  continue;
604
850
  }
605
- s = o.next;
851
+ r = o.next;
606
852
  }
607
- const i = b(r, s);
608
- return i ? { nodeId: s, node: i, flags: H(t), error: null } : { nodeId: null, node: null, flags: t, error: { step: null, reason: `unknown node: ${s}` } };
853
+ const i = x(s, r);
854
+ return i ? { nodeId: r, node: i, flags: Ae(t), error: null } : { nodeId: null, node: null, flags: t, error: { step: null, reason: `unknown node: ${r}` } };
609
855
  }
610
- function _e(r, e = []) {
856
+ function ut(s, e = []) {
611
857
  const t = [];
612
- for (const s of e) {
613
- if (s.kind !== "collect") continue;
614
- const i = b(r, s.nodeId);
858
+ for (const r of e) {
859
+ if (r.kind !== "collect") continue;
860
+ const i = x(s, r.nodeId);
615
861
  t.push(...i?.fields || []);
616
862
  }
617
863
  return t;
618
864
  }
619
- function $e(r = []) {
865
+ function pt(s = []) {
620
866
  const e = {};
621
- for (const t of r)
867
+ for (const t of s)
622
868
  t.kind === "collect" && Object.assign(e, t.values || {});
623
869
  return e;
624
870
  }
625
- function Fe(r = []) {
626
- return r.filter((e) => e.kind === "choice").map((e) => `${e.nodeId}:${e.optionId}`);
871
+ function ht(s = []) {
872
+ return s.filter((e) => e.kind === "choice").map((e) => `${e.nodeId}:${e.optionId}`);
627
873
  }
628
- function Y(r, e = []) {
874
+ function ke(s, e = []) {
629
875
  const t = [];
630
- for (const s of e) {
631
- if (s.kind !== "choice") continue;
632
- const n = (b(r, s.nodeId)?.options || []).find((o) => o.id === s.optionId);
876
+ for (const r of e) {
877
+ if (r.kind !== "choice") continue;
878
+ const n = (x(s, r.nodeId)?.options || []).find((o) => o.id === r.optionId);
633
879
  t.push(...n?.flags || []);
634
880
  }
635
- return H(t);
881
+ return Ae(t);
882
+ }
883
+ function ft(s = []) {
884
+ return s.includes("urgent") ? "urgent" : s.includes("moderate") ? "moderate" : null;
885
+ }
886
+ function Ae(s) {
887
+ return [...new Set(s)];
888
+ }
889
+ function mt(s, e = []) {
890
+ const t = [];
891
+ for (const i of e) {
892
+ const [n, o] = String(i).split(":"), a = x(s, n), l = a?.type === "choice" ? (a.options || []).find((d) => d.id === o) : null;
893
+ if (!l)
894
+ return { steps: [], error: `unknown preset step: ${i}` };
895
+ t.push({ nodeId: n, kind: "choice", optionId: o, label: l.label, preset: !0 });
896
+ }
897
+ const { error: r } = q(s, t);
898
+ return r ? { steps: [], error: r.reason } : { steps: t, error: null };
899
+ }
900
+ function gt(s, e) {
901
+ const t = N(e);
902
+ if (!t) return { form: null, steps: [], error: "not a hand-off" };
903
+ const r = (s || []).find((o) => o.formId === t.formId);
904
+ if (!r) return { form: null, steps: [], error: `unknown form: ${t.formId}` };
905
+ const { steps: i, error: n } = mt(r, t.path);
906
+ return n ? { form: null, steps: [], error: n } : { form: r, steps: i, error: null };
907
+ }
908
+ function bt(s, e, t, r) {
909
+ return {
910
+ form: s,
911
+ steps: e,
912
+ option: { nodeId: t.id, optionId: r.id, label: r.label }
913
+ };
914
+ }
915
+ function yt(s = []) {
916
+ return s.every((e) => e.preset === !0);
917
+ }
918
+ function wt(s, e, t) {
919
+ if (!Array.isArray(s) || !s.length) return [];
920
+ const r = [];
921
+ for (let i = 0; i < s.length; i++) {
922
+ const n = s[i], o = (e || []).find((u) => u.formId === n?.formId);
923
+ if (!o) return [];
924
+ const { node: a, error: l } = q(o, n.steps || []);
925
+ if (l || a?.id !== n.option?.nodeId) return [];
926
+ const d = (a.options || []).find((u) => u.id === n.option.optionId), p = i + 1 < s.length ? s[i + 1].formId : t;
927
+ if (N(d)?.formId !== p) return [];
928
+ r.push({ form: o, steps: n.steps || [], option: n.option });
929
+ }
930
+ return r;
636
931
  }
637
- function Ie(r = []) {
638
- return r.includes("urgent") ? "urgent" : r.includes("moderate") ? "moderate" : null;
932
+ function xt({ attr: s = null, search: e = "" } = {}) {
933
+ const t = String(s ?? "").trim();
934
+ if (t) return t;
935
+ try {
936
+ return new URLSearchParams(e || "").get("flow")?.trim() || null;
937
+ } catch {
938
+ return null;
939
+ }
639
940
  }
640
- function H(r) {
641
- return [...new Set(r)];
941
+ function vt(s, e) {
942
+ return e && (s || []).find((t) => t.formId === e) || null;
642
943
  }
643
- const Ee = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}(:\d{2})?(\.\d+)?(Z|[+-]\d{2}:\d{2})?$/, M = {
944
+ function _t(s, e) {
945
+ return !e || s?.form?.formId === e ? !0 : (s?.origins || []).some((t) => t.form?.formId === e);
946
+ }
947
+ const $t = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}(:\d{2})?(\.\d+)?(Z|[+-]\d{2}:\d{2})?$/, pe = {
644
948
  text: 500,
645
949
  textarea: 5e3,
646
950
  url: 2048
647
- };
648
- function Se(r, e) {
649
- if (e == null || e === "" || r.kind === "location" && Ae(e))
650
- return r.required ? `Please fill in: ${r.label.toLowerCase()}.` : null;
651
- switch (r.kind) {
951
+ }, kt = "Please confirm the rights statement so we can use what you send.";
952
+ function Fe(s, { mediaCount: e = 0 } = {}) {
953
+ return s.kind === "consent" && s.requiredIf === "media" ? e > 0 : !!s.required;
954
+ }
955
+ function At(s, e) {
956
+ try {
957
+ return new RegExp(s, "u").test(e);
958
+ } catch {
959
+ return !0;
960
+ }
961
+ }
962
+ function Ft(s) {
963
+ return s.key === "zip" ? "Please enter a five-digit zip code." : `Please check the format of ${s.label.toLowerCase()}.`;
964
+ }
965
+ function It(s, e, { mediaCount: t = 0 } = {}) {
966
+ const r = Fe(s, { mediaCount: t });
967
+ if (s.kind === "consent")
968
+ return e === !0 || !r ? null : kt;
969
+ if (e == null || e === "" || s.kind === "location" && Et(e))
970
+ return r ? `Please fill in: ${s.label.toLowerCase()}.` : null;
971
+ switch (s.kind) {
652
972
  case "text":
653
973
  case "textarea": {
654
- const s = r.maxLength || M[r.kind];
655
- return typeof e != "string" ? `Please enter text for ${r.label.toLowerCase()}.` : e.length > s ? `Please keep ${r.label.toLowerCase()} under ${s} characters.` : null;
974
+ const n = s.maxLength || pe[s.kind];
975
+ return typeof e != "string" ? `Please enter text for ${s.label.toLowerCase()}.` : e.length > n ? `Please keep ${s.label.toLowerCase()} under ${n} characters.` : s.kind === "text" && s.pattern && !At(s.pattern, e) ? Ft(s) : null;
656
976
  }
657
977
  case "url": {
658
- if (typeof e != "string" || e.length > M.url)
978
+ if (typeof e != "string" || e.length > pe.url)
659
979
  return "Please enter a valid link.";
660
980
  try {
661
981
  return new URL(e), null;
@@ -664,110 +984,108 @@ function Se(r, e) {
664
984
  }
665
985
  }
666
986
  case "datetime":
667
- return Ee.test(String(e)) ? null : "Please pick a date and time.";
987
+ return $t.test(String(e)) ? null : "Please pick a date and time.";
668
988
  case "select":
669
- return (r.options || []).map((i) => i.id).includes(e) ? null : `Please choose one of the options for ${r.label.toLowerCase()}.`;
670
- case "consent":
671
- return e === !0 ? null : "Please confirm the rights statement so we can use what you send.";
989
+ return (s.options || []).map((o) => o.id).includes(e) ? null : `Please choose one of the options for ${s.label.toLowerCase()}.`;
672
990
  case "location":
673
- return Ce(r, e);
991
+ return St(s, e);
674
992
  case "media":
675
993
  return null;
676
994
  default:
677
- return `Unsupported field: ${r.kind}`;
995
+ return `Unsupported field: ${s.kind}`;
678
996
  }
679
997
  }
680
- function Ae(r) {
681
- return r == null ? !0 : typeof r != "object" ? !1 : !r.county && !r.where && !(Array.isArray(r.gps) && r.gps.length);
998
+ function Et(s) {
999
+ return s == null ? !0 : typeof s != "object" ? !1 : !s.county && !s.where && !(Array.isArray(s.gps) && s.gps.length);
682
1000
  }
683
- function Ce(r, e) {
684
- return typeof e != "object" || Array.isArray(e) ? "Please tell us where this was." : e.county !== void 0 && (typeof e.county != "string" || e.county.length > 100) ? "Please choose a county." : e.where !== void 0 && (typeof e.where != "string" || e.where.length > 500) ? "Please shorten the location description." : e.gps !== void 0 && !(Array.isArray(e.gps) && e.gps.length === 2 && e.gps.every((s) => typeof s == "number" && Number.isFinite(s))) ? "Location coordinates look wrong; try re-sharing your location." : r.required && !e.county && !e.where ? `Please fill in: ${r.label.toLowerCase()}.` : null;
1001
+ function St(s, e) {
1002
+ return typeof e != "object" || Array.isArray(e) ? "Please tell us where this was." : e.county !== void 0 && (typeof e.county != "string" || e.county.length > 100) ? "Please choose a county." : e.where !== void 0 && (typeof e.where != "string" || e.where.length > 500) ? "Please shorten the location description." : e.gps !== void 0 && !(Array.isArray(e.gps) && e.gps.length === 2 && e.gps.every((r) => typeof r == "number" && Number.isFinite(r))) ? "Location coordinates look wrong; try re-sharing your location." : s.required && !e.county && !e.where ? `Please fill in: ${s.label.toLowerCase()}.` : null;
685
1003
  }
686
- function O(r, e = {}) {
687
- const t = {};
688
- for (const s of r) {
689
- if (s.kind === "media") continue;
690
- const i = Se(s, e[s.key]);
691
- i && (t[s.key] = i);
692
- }
693
- return { ok: Object.keys(t).length === 0, errors: t };
1004
+ function he(s, e = {}, { mediaCount: t = 0 } = {}) {
1005
+ const r = {};
1006
+ for (const i of s) {
1007
+ if (i.kind === "media") continue;
1008
+ const n = It(i, e[i.key], { mediaCount: t });
1009
+ n && (r[i.key] = n);
1010
+ }
1011
+ return { ok: Object.keys(r).length === 0, errors: r };
694
1012
  }
695
- function C(r = [], e = {}, { required: t = !1 } = {}) {
1013
+ function Y(s = [], e = {}, { required: t = !1 } = {}) {
696
1014
  const {
697
- maxFiles: s = 5,
1015
+ maxFiles: r = 5,
698
1016
  maxFileBytes: i = 512 * 1024 * 1024,
699
1017
  allowedTypes: n = []
700
1018
  } = e, o = [];
701
- return t && r.length === 0 && o.push({ reason: "required", message: "Please attach at least one photo or video." }), r.length > s && o.push({
1019
+ return t && s.length === 0 && o.push({ reason: "required", message: "Please attach at least one photo or video." }), s.length > r && o.push({
702
1020
  reason: "count",
703
- message: `This form accepts at most ${s} ${s === 1 ? "file" : "files"}.`
704
- }), r.forEach((l, d) => {
705
- n.length && !n.includes(l.type) && o.push({
706
- index: d,
1021
+ message: `This form accepts at most ${r} ${r === 1 ? "file" : "files"}.`
1022
+ }), s.forEach((a, l) => {
1023
+ n.length && !n.includes(a.type) && o.push({
1024
+ index: l,
707
1025
  reason: "type",
708
- message: `${l.name || "A file"} is a type this form does not accept.`
709
- }), l.size > i && o.push({
710
- index: d,
1026
+ message: `${a.name || "A file"} is a type this form does not accept.`
1027
+ }), a.size > i && o.push({
1028
+ index: l,
711
1029
  reason: "size",
712
- message: `${l.name || "A file"} is larger than this form allows.`
1030
+ message: `${a.name || "A file"} is larger than this form allows.`
713
1031
  });
714
1032
  }), { ok: o.length === 0, errors: o };
715
1033
  }
716
- function U({ formId: r, requestId: e, files: t }) {
1034
+ function fe({ formId: s, requestId: e, files: t }) {
717
1035
  return {
718
- formId: r,
1036
+ formId: s,
719
1037
  requestId: e,
720
- files: t.map((s) => ({ contentType: s.type, size: s.size }))
1038
+ files: t.map((r) => ({ contentType: r.type, size: r.size }))
721
1039
  };
722
1040
  }
723
- function Te({ form: r, steps: e, media: t = [] }) {
724
- const s = _e(r, e), i = $e(e), n = {};
725
- for (const o of s) {
1041
+ function Ct({ form: s, steps: e, media: t = [] }) {
1042
+ const r = ut(s, e), i = pt(e), n = {};
1043
+ for (const o of r) {
726
1044
  if (o.kind === "media") continue;
727
- const l = i[o.key];
728
- if (!(l == null || l === "") && !(o.kind === "consent" && l !== !0)) {
1045
+ const a = i[o.key];
1046
+ if (!(a == null || a === "") && !(o.kind === "consent" && (a !== !0 || o.requiredIf === "media" && !t.length))) {
729
1047
  if (o.kind === "location") {
730
- const d = {};
731
- l.county && (d.county = l.county), l.where && (d.where = l.where), Array.isArray(l.gps) && l.gps.length === 2 && (d.gps = l.gps), Object.keys(d).length && (n[o.key] = d);
1048
+ const l = {};
1049
+ a.county && (l.county = a.county), a.where && (l.where = a.where), Array.isArray(a.gps) && a.gps.length === 2 && (l.gps = a.gps), Object.keys(l).length && (n[o.key] = l);
732
1050
  continue;
733
1051
  }
734
- n[o.key] = l;
1052
+ n[o.key] = a;
735
1053
  }
736
1054
  }
737
1055
  return {
738
- formId: r.formId,
739
- flowVersion: r.flowVersion,
740
- path: Fe(e),
1056
+ formId: s.formId,
1057
+ flowVersion: s.flowVersion,
1058
+ path: ht(e),
741
1059
  answers: n,
742
- media: t.map(({ assetId: o, type: l }) => ({ assetId: o, type: l }))
1060
+ media: t.map(({ assetId: o, type: a }) => ({ assetId: o, type: a }))
743
1061
  };
744
1062
  }
745
- function q(r, e) {
746
- if (r === 429)
1063
+ function me(s, e) {
1064
+ if (s === 429)
747
1065
  return {
748
1066
  kind: "throttled",
749
1067
  message: e?.message || "You have reached the submission limit; please try again later.",
750
1068
  limit: e?.limit,
751
1069
  retryAfter: e?.retryAfter
752
1070
  };
753
- if (r === 401)
1071
+ if (s === 401)
754
1072
  return { kind: "auth", message: "Please sign in again to continue." };
755
- if (r === 403)
1073
+ if (s === 403)
756
1074
  return { kind: "forbidden", message: e?.message || "This submission belongs to another account." };
757
- if (r === 404)
1075
+ if (s === 404)
758
1076
  return { kind: "unknown-form", message: "This form is no longer available." };
759
- if (r === 409)
1077
+ if (s === 409)
760
1078
  return {
761
1079
  kind: "stale",
762
1080
  message: e?.message || "The form changed while you were filling it out; please review and resubmit."
763
1081
  };
764
- if (r === 400 && e?.code === "media-not-verified")
1082
+ if (s === 400 && e?.code === "media-not-verified")
765
1083
  return {
766
1084
  kind: "media",
767
1085
  message: e.message || "An attached file is missing or does not match this submission.",
768
1086
  assetId: e.assetId
769
1087
  };
770
- if (r === 400 && Array.isArray(e)) {
1088
+ if (s === 400 && Array.isArray(e)) {
771
1089
  const t = e[0] || {};
772
1090
  return {
773
1091
  kind: "validation",
@@ -775,54 +1093,58 @@ function q(r, e) {
775
1093
  fieldKey: String(t.instancePath || "").split("/").filter(Boolean)[0] || null
776
1094
  };
777
1095
  }
778
- return r === 0 ? { kind: "network", message: "We could not reach WRAL; check your connection and try again." } : {
1096
+ return s === 0 ? { kind: "network", message: "We could not reach WRAL; check your connection and try again." } : {
779
1097
  kind: "server",
780
1098
  message: "Something went wrong on our end; please try again."
781
1099
  };
782
1100
  }
783
- const Re = 34, De = 44;
784
- function L(r, e) {
785
- const t = String(r);
1101
+ const Tt = 34, Rt = 44;
1102
+ function ge(s, e) {
1103
+ const t = String(s);
786
1104
  return t.length > e ? `${t.slice(0, e)}…` : t;
787
1105
  }
788
- function ze(r) {
789
- return !r || typeof r != "object" ? "" : [r.county, r.where].filter(Boolean).join(", ");
1106
+ function Mt(s, e) {
1107
+ const t = (s.options || []).find((r) => r.id === e);
1108
+ return t ? t.label : e;
1109
+ }
1110
+ function Dt(s) {
1111
+ return !s || typeof s != "object" ? "" : [s.county, s.where].filter(Boolean).join(", ");
790
1112
  }
791
- function Be(r, e = {}, t = []) {
792
- const s = [];
793
- for (const i of r) {
1113
+ function Pt(s, e = {}, t = []) {
1114
+ const r = [];
1115
+ for (const i of s) {
794
1116
  if (i.kind === "consent") continue;
795
1117
  if (i.kind === "media") {
796
- t.length && s.push(`${t.length} ${t.length === 1 ? "file" : "files"}`);
1118
+ t.length && r.push(`${t.length} ${t.length === 1 ? "file" : "files"}`);
797
1119
  continue;
798
1120
  }
799
- const n = i.kind === "location" ? ze(e[i.key]) : e[i.key];
800
- n == null || n === "" || (i.kind === "textarea" ? s.push(`"${L(n, De)}"`) : s.push(L(n, Re)));
1121
+ const n = i.kind === "location" ? Dt(e[i.key]) : i.kind === "select" ? Mt(i, e[i.key]) : e[i.key];
1122
+ n == null || n === "" || (i.kind === "textarea" ? r.push(`"${ge(n, Rt)}"`) : r.push(ge(n, Tt)));
801
1123
  }
802
- return s.join(" · ") || "Details provided";
1124
+ return r.join(" · ") || "Details provided";
803
1125
  }
804
- function Pe(r, e = [], t = null) {
805
- const s = [];
1126
+ function zt(s, e = [], t = null) {
1127
+ const r = [];
806
1128
  for (const n of e) {
807
- const o = b(r, n.nodeId);
808
- n.kind === "choice" && o && s.push({ k: (o.prompt || "").replace(/\?$/, ""), v: n.label || n.optionId }), n.kind === "collect" && s.push({ k: "Details", v: n.summary || "Details provided" }), n.kind === "gate" && (n.anonymous ? s.push({ k: "Contact", v: "Anonymous — we will have no way to reach you" }) : (n.email || t) && s.push({ k: "Verified email", v: n.email || t }));
1129
+ const o = x(s, n.nodeId);
1130
+ n.kind === "choice" && o && r.push({ k: (o.prompt || "").replace(/\?$/, ""), v: n.label || n.optionId }), n.kind === "collect" && r.push({ k: "Details", v: n.summary || "Details provided" }), n.kind === "gate" && (n.anonymous ? r.push({ k: "Contact", v: "Anonymous — we will have no way to reach you" }) : (n.email || t) && r.push({ k: "Verified email", v: n.email || t }));
809
1131
  }
810
- const i = Ie(Y(r, e));
811
- return i && s.push({ k: "Priority", v: i === "urgent" ? "Urgent" : "Moderate", pill: i }), s;
1132
+ const i = ft(ke(s, e));
1133
+ return i && r.push({ k: "Priority", v: i === "urgent" ? "Urgent" : "Moderate", pill: i }), r;
812
1134
  }
813
- function Me(r, e = []) {
814
- const t = r?.confirmation || {};
1135
+ function Bt(s, e = []) {
1136
+ const t = s?.confirmation || {};
815
1137
  return {
816
1138
  title: t.title || "Report received.",
817
1139
  body: t.body || "Your report is in the review queue.",
818
1140
  urgentNote: e.includes("urgent") ? t.urgentNote : void 0
819
1141
  };
820
1142
  }
821
- function Oe(r, e) {
1143
+ function Ot(s, e) {
822
1144
  const t = e === "failed" ? " The notification is queued for a delivery retry." : "";
823
- return r?.startsWith("studio+email:") ? `Sent to the Studio review queue; the desk is emailed.${t}` : r?.startsWith("studio:") ? "Sent to the Studio review queue." : r?.startsWith("jsm:") ? `A ticket is opened for tech support with your details as fields, not prose.${t}` : r?.startsWith("email:") ? `Emailed to the owning desk with a link to your report.${t}` : "Routed to the right team.";
1145
+ return s?.startsWith("studio+email:") ? `Sent to the Studio review queue; the desk is emailed.${t}` : s?.startsWith("studio:") ? "Sent to the Studio review queue." : s?.startsWith("jsm:") ? `A ticket is opened for tech support with your details as fields, not prose.${t}` : s?.startsWith("email:") ? `Emailed to the owning desk with a link to your report.${t}` : "Routed to the right team.";
824
1146
  }
825
- function Ue({ routing: r = {}, flags: e = [], reference: t = "", anonymous: s = !1 }) {
1147
+ function Ut({ routing: s = {}, flags: e = [], reference: t = "", anonymous: r = !1 }) {
826
1148
  const i = e.includes("urgent");
827
1149
  return [
828
1150
  {
@@ -831,12 +1153,12 @@ function Ue({ routing: r = {}, flags: e = [], reference: t = "", anonymous: s =
831
1153
  },
832
1154
  {
833
1155
  title: "Routed",
834
- body: Oe(r.destination, r.state),
1156
+ body: Ot(s.destination, s.state),
835
1157
  pill: i ? "Urgent · pinned first" : void 0
836
1158
  },
837
1159
  {
838
1160
  title: "Reviewed",
839
- body: s ? "An editor reviews it in the Report It queue: accept and promote it uncredited, reject, or re-route." : "An editor reviews it in the Report It queue: accept and promote with your credit, reject, or re-route."
1161
+ body: r ? "An editor reviews it in the Report It queue: accept and promote it uncredited, reject, or re-route." : "An editor reviews it in the Report It queue: accept and promote with your credit, reject, or re-route."
840
1162
  },
841
1163
  {
842
1164
  title: "Monitored",
@@ -848,63 +1170,76 @@ function Ue({ routing: r = {}, flags: e = [], reference: t = "", anonymous: s =
848
1170
  }
849
1171
  ];
850
1172
  }
851
- const R = "wral-report-it:draft:v1", K = 1;
852
- function qe(r, e) {
1173
+ const J = "wral-report-it:draft:v1", Ie = 1;
1174
+ function Lt(s, e) {
853
1175
  try {
854
- r.setItem(R, JSON.stringify({ ...e, v: K, savedAt: Date.now() }));
1176
+ s.setItem(J, JSON.stringify({ ...e, v: Ie, savedAt: Date.now() }));
855
1177
  } catch {
856
1178
  }
857
1179
  }
858
- function Le(r) {
1180
+ function Nt(s) {
859
1181
  try {
860
- const e = r.getItem(R);
1182
+ const e = s.getItem(J);
861
1183
  if (!e) return null;
862
1184
  const t = JSON.parse(e);
863
- return t?.v !== K ? null : t;
1185
+ return t?.v !== Ie ? null : t;
864
1186
  } catch {
865
1187
  return null;
866
1188
  }
867
1189
  }
868
- function j(r) {
1190
+ function be(s) {
869
1191
  try {
870
- r.removeItem(R);
1192
+ s.removeItem(J);
871
1193
  } catch {
872
1194
  }
873
1195
  }
874
- function je({ apiOrigin: r, form: e, steps: t, requestId: s = null, mediaMeta: i = {} }) {
1196
+ function qt({
1197
+ apiOrigin: s,
1198
+ form: e,
1199
+ steps: t,
1200
+ requestId: r = null,
1201
+ mediaMeta: i = {},
1202
+ origins: n = []
1203
+ }) {
875
1204
  return {
876
- apiOrigin: r,
1205
+ apiOrigin: s,
877
1206
  formId: e.formId,
878
1207
  flowVersion: e.flowVersion,
879
- requestId: s,
1208
+ requestId: r,
880
1209
  steps: t,
881
- media: i
1210
+ media: i,
1211
+ origins: n.map(({ form: o, steps: a, option: l }) => ({
1212
+ formId: o.formId,
1213
+ steps: a,
1214
+ option: l
1215
+ }))
882
1216
  };
883
1217
  }
884
- function Ne(r, e, { apiOrigin: t } = {}) {
885
- if (!r) return { status: "discarded" };
886
- if (t && r.apiOrigin && r.apiOrigin !== t)
887
- return { status: "discarded" };
888
- const s = (e || []).find((o) => o.formId === r.formId);
1218
+ function Ht(s, e, { apiOrigin: t } = {}) {
889
1219
  if (!s) return { status: "discarded" };
890
- const { error: i } = V(s, r.steps || []);
1220
+ if (t && s.apiOrigin && s.apiOrigin !== t)
1221
+ return { status: "discarded" };
1222
+ const r = (e || []).find((o) => o.formId === s.formId);
1223
+ if (!r) return { status: "discarded" };
1224
+ const { error: i } = q(r, s.steps || []);
891
1225
  if (i) return { status: "discarded" };
892
1226
  const n = {};
893
- for (const [o, l] of Object.entries(r.media || {}))
894
- l?.length && (n[o] = l.map((d) => ({ ...d, lost: !0 })));
1227
+ for (const [o, a] of Object.entries(s.media || {}))
1228
+ a?.length && (n[o] = a.map((l) => ({ ...l, lost: !0 })));
895
1229
  return {
896
- status: r.flowVersion === s.flowVersion ? "ok" : "review-required",
897
- form: s,
898
- steps: r.steps || [],
899
- requestId: r.requestId || null,
900
- lostMedia: n
1230
+ status: s.flowVersion === r.flowVersion ? "ok" : "review-required",
1231
+ form: r,
1232
+ steps: s.steps || [],
1233
+ requestId: s.requestId || null,
1234
+ lostMedia: n,
1235
+ origins: wt(s.origins, e, r.formId)
901
1236
  };
902
1237
  }
903
- function F(r = []) {
1238
+ function z(s = []) {
904
1239
  return {
905
1240
  stage: "idle",
906
1241
  resumeStage: null,
907
- files: r.map((e) => ({
1242
+ files: s.map((e) => ({
908
1243
  name: e.name,
909
1244
  type: e.type,
910
1245
  size: e.size,
@@ -920,82 +1255,82 @@ function F(r = []) {
920
1255
  error: null
921
1256
  };
922
1257
  }
923
- function We(r, e) {
1258
+ function jt(s, e) {
924
1259
  switch (e.type) {
925
1260
  case "START":
926
- return { ...r, stage: r.files.length ? "minting" : "requesting", error: null };
1261
+ return { ...s, stage: s.files.length ? "minting" : "requesting", error: null };
927
1262
  case "AUTH_REQUIRED":
928
- return { ...r, resumeStage: r.stage === "auth" ? r.resumeStage : r.stage, stage: "auth" };
1263
+ return { ...s, resumeStage: s.stage === "auth" ? s.resumeStage : s.stage, stage: "auth" };
929
1264
  case "AUTH_OK":
930
- return { ...r, stage: r.resumeStage || "idle", resumeStage: null };
1265
+ return { ...s, stage: s.resumeStage || "idle", resumeStage: null };
931
1266
  case "MINTED": {
932
- const t = r.files.map((s, i) => ({
933
- ...s,
934
- assetId: e.uploads[i]?.assetId ?? s.assetId,
935
- url: e.uploads[i]?.url ?? s.url,
936
- assetUrl: e.uploads[i]?.assetUrl ?? s.assetUrl,
1267
+ const t = s.files.map((r, i) => ({
1268
+ ...r,
1269
+ assetId: e.uploads[i]?.assetId ?? r.assetId,
1270
+ url: e.uploads[i]?.url ?? r.url,
1271
+ assetUrl: e.uploads[i]?.assetUrl ?? r.assetUrl,
937
1272
  status: "uploading",
938
1273
  progress: 0,
939
1274
  error: null
940
1275
  }));
941
- return { ...r, stage: "uploading", files: t };
1276
+ return { ...s, stage: "uploading", files: t };
942
1277
  }
943
1278
  case "FILE_PROGRESS":
944
- return v(r, e.i, (t) => ({
1279
+ return T(s, e.i, (t) => ({
945
1280
  ...t,
946
1281
  progress: e.total ? e.loaded / e.total : 0
947
1282
  }));
948
1283
  case "FILE_DONE": {
949
- const t = v(r, e.i, (s) => ({ ...s, status: "done", progress: 1 }));
950
- return Ve(t);
1284
+ const t = T(s, e.i, (r) => ({ ...r, status: "done", progress: 1 }));
1285
+ return Wt(t);
951
1286
  }
952
1287
  case "FILE_FAIL":
953
- return { ...v(r, e.i, (s) => ({
954
- ...s,
1288
+ return { ...T(s, e.i, (r) => ({
1289
+ ...r,
955
1290
  status: "failed",
956
1291
  error: e.error || "upload failed"
957
1292
  })), stage: "uploading-error" };
958
1293
  case "RETRY_FILE":
959
- return { ...v(r, e.i, (s) => ({
960
- ...s,
1294
+ return { ...T(s, e.i, (r) => ({
1295
+ ...r,
961
1296
  status: "uploading",
962
1297
  progress: 0,
963
1298
  error: null
964
1299
  })), stage: "uploading" };
965
1300
  case "REMINT_FILE":
966
- return { ...v(r, e.i, (s) => ({
967
- ...s,
1301
+ return { ...T(s, e.i, (r) => ({
1302
+ ...r,
968
1303
  assetId: e.upload.assetId,
969
1304
  url: e.upload.url,
970
- assetUrl: e.upload.assetUrl ?? s.assetUrl,
1305
+ assetUrl: e.upload.assetUrl ?? r.assetUrl,
971
1306
  status: "uploading",
972
1307
  progress: 0,
973
1308
  error: null
974
1309
  })), stage: "uploading" };
975
1310
  case "REQUEST_START":
976
- return { ...r, stage: "requesting", error: null };
1311
+ return { ...s, stage: "requesting", error: null };
977
1312
  case "REQUEST_OK":
978
- return { ...r, stage: "done", result: e.result, error: null };
1313
+ return { ...s, stage: "done", result: e.result, error: null };
979
1314
  case "REQUEST_FAIL":
980
- return { ...r, stage: "requesting-error", error: e.error };
1315
+ return { ...s, stage: "requesting-error", error: e.error };
981
1316
  case "RESET":
982
- return F([]);
1317
+ return z([]);
983
1318
  default:
984
- return r;
1319
+ return s;
985
1320
  }
986
1321
  }
987
- function v(r, e, t) {
988
- const s = r.files.map((i, n) => n === e ? t(i) : i);
989
- return { ...r, files: s };
1322
+ function T(s, e, t) {
1323
+ const r = s.files.map((i, n) => n === e ? t(i) : i);
1324
+ return { ...s, files: r };
990
1325
  }
991
- function Ve(r) {
992
- const e = r.files.every((s) => s.status === "done"), t = r.files.some((s) => s.status === "failed");
993
- return e ? { ...r, stage: "requesting" } : t ? { ...r, stage: "uploading-error" } : r;
1326
+ function Wt(s) {
1327
+ const e = s.files.every((r) => r.status === "done"), t = s.files.some((r) => r.status === "failed");
1328
+ return e ? { ...s, stage: "requesting" } : t ? { ...s, stage: "uploading-error" } : s;
994
1329
  }
995
- function N(r) {
996
- return r.files.map((e, t) => ({ ...e, i: t })).filter((e) => e.status === "failed");
1330
+ function ye(s) {
1331
+ return s.files.map((e, t) => ({ ...e, i: t })).filter((e) => e.status === "failed");
997
1332
  }
998
- const Ye = [
1333
+ const Vt = [
999
1334
  "Wake",
1000
1335
  "Durham",
1001
1336
  "Orange",
@@ -1012,24 +1347,27 @@ const Ye = [
1012
1347
  "Moore",
1013
1348
  "Sampson",
1014
1349
  "Other / outside the area"
1015
- ], W = "(919) 821-8600", He = "https://www.wral.com/my-wral/", Ke = Object.freeze([
1350
+ ], we = "(919) 821-8600", Yt = "https://www.wral.com/my-wral/", Gt = Object.freeze([
1016
1351
  "We cannot come back to you for the detail that often turns a tip into a story.",
1017
1352
  "We cannot credit you if we use your photos or video.",
1018
1353
  "If you lose your reference number, we cannot look it up for you."
1019
1354
  ]);
1020
- function Qe(r) {
1021
- const e = String(r).replace(/\D/g, "");
1355
+ function Kt(s) {
1356
+ const e = String(s).replace(/\D/g, "");
1022
1357
  return `tel:+1${e.length === 11 && e.startsWith("1") ? e.slice(1) : e}`;
1023
1358
  }
1024
- const Ge = "https://api.wral.com/forms", Je = 480, Xe = 2, S = "Welcome to Report It. What would you like to send us?", A = "A few quick questions route your report to the right team.", Ze = 2500;
1025
- class at extends T {
1026
- static styles = me;
1359
+ const Qt = "https://api.wral.com/forms", Jt = 480, Zt = 2, Ee = "What would you like to send to WRAL?", W = `Welcome to Report It. ${Ee}`, V = "A few quick questions route your report to the right team.", Xt = 2500, er = "I took or own this material and give WRAL permission to use it on air and online with credit to me.";
1360
+ class ar extends G {
1361
+ static styles = st;
1027
1362
  static properties = {
1028
1363
  api: { type: String },
1364
+ flow: { type: String },
1029
1365
  _phase: { state: !0 },
1030
1366
  _forms: { state: !0 },
1031
1367
  _form: { state: !0 },
1032
1368
  _steps: { state: !0 },
1369
+ _origins: { state: !0 },
1370
+ _handoffError: { state: !0 },
1033
1371
  _typing: { state: !0 },
1034
1372
  _loadingSlow: { state: !0 },
1035
1373
  _cardValues: { state: !0 },
@@ -1040,36 +1378,36 @@ class at extends T {
1040
1378
  _notice: { state: !0 },
1041
1379
  _result: { state: !0 }
1042
1380
  };
1381
+ #c = null;
1043
1382
  #l = null;
1044
- #a = null;
1045
1383
  #u = null;
1046
1384
  #t = null;
1047
1385
  #r = {};
1048
1386
  #s = {};
1049
- #i = /* @__PURE__ */ new Map();
1387
+ #n = /* @__PURE__ */ new Map();
1050
1388
  #y = null;
1051
1389
  #p = null;
1052
1390
  #w = !1;
1053
1391
  #d = null;
1054
- #I = 0;
1392
+ #F = 0;
1055
1393
  constructor() {
1056
- super(), this.api = Ge, this._phase = "loading", this._forms = [], this._form = null, this._steps = [], this._typing = !1, this._loadingSlow = !1, this._cardValues = {}, this._fieldErrors = {}, this._gate = { stage: null, email: "", error: "", loading: !1 }, this._submit = F([]), this._banner = null, this._notice = null, this._result = null;
1394
+ super(), this.api = Qt, this.flow = null, this._phase = "loading", this._forms = [], this._form = null, this._steps = [], this._origins = [], this._handoffError = !1, this._typing = !1, this._loadingSlow = !1, this._cardValues = {}, this._fieldErrors = {}, this._gate = { stage: null, email: "", error: "", loading: !1 }, this._submit = z([]), this._banner = null, this._notice = null, this._result = null;
1057
1395
  }
1058
1396
  get client() {
1059
- return this.#l ? this.#l : ((!this.#a || this.#u !== this.api) && (this.#a = ke({ baseUrl: this.api }), this.#u = this.api), this.#a);
1397
+ return this.#c ? this.#c : ((!this.#l || this.#u !== this.api) && (this.#l = dt({ baseUrl: this.api }), this.#u = this.api), this.#l);
1060
1398
  }
1061
1399
  set client(e) {
1062
- this.#l = e || null, this.isConnected && this.#x();
1400
+ this.#c = e || null, this.isConnected && this.#x();
1063
1401
  }
1064
1402
  connectedCallback() {
1065
1403
  super.connectedCallback(), this.#x();
1066
1404
  }
1067
1405
  disconnectedCallback() {
1068
1406
  super.disconnectedCallback(), clearTimeout(this.#y), clearTimeout(this.#p), this.#d?.();
1069
- for (const { abort: e } of this.#i.values()) e?.();
1070
- this.#i.clear();
1407
+ for (const { abort: e } of this.#n.values()) e?.();
1408
+ this.#n.clear();
1071
1409
  }
1072
- get #z() {
1410
+ get #O() {
1073
1411
  try {
1074
1412
  return matchMedia("(prefers-reduced-motion: reduce)").matches;
1075
1413
  } catch {
@@ -1091,7 +1429,7 @@ class at extends T {
1091
1429
  * submission is enabled on this deployment, and a form whose desk needs
1092
1430
  * a way to reach the viewer opts out with allowAnonymous: false.
1093
1431
  */
1094
- get #B() {
1432
+ get #U() {
1095
1433
  return this.client.anonymousCapability?.().enabled === !0 && this._form?.allowAnonymous !== !1;
1096
1434
  }
1097
1435
  /* Derived from the gate step, so a reload restores the choice. */
@@ -1100,13 +1438,13 @@ class at extends T {
1100
1438
  }
1101
1439
  // ── Loading + draft restore ─────────────────────────────────────
1102
1440
  async #x() {
1103
- const e = ++this.#I, t = () => e === this.#I;
1441
+ const e = ++this.#F, t = () => e === this.#F;
1104
1442
  this._phase = "loading", this._banner = null, this._loadingSlow = !1, clearTimeout(this.#p), this.#p = setTimeout(() => {
1105
1443
  this._loadingSlow = !0;
1106
- }, Ze);
1107
- let s;
1444
+ }, Xt);
1445
+ let r;
1108
1446
  try {
1109
- s = await this.client.listForms();
1447
+ r = await this.client.listForms();
1110
1448
  } catch {
1111
1449
  t() && (this._phase = "load-error");
1112
1450
  return;
@@ -1114,85 +1452,144 @@ class at extends T {
1114
1452
  t() && (clearTimeout(this.#p), this._loadingSlow = !1);
1115
1453
  }
1116
1454
  if (!t()) return;
1117
- this._forms = s;
1118
- const i = Ne(Le(this.#h), this._forms, { apiOrigin: this.api });
1119
- if (i.status === "ok" || i.status === "review-required") {
1120
- this._form = i.form, this._steps = i.steps, this.#t = i.requestId, this.#s = i.lostMedia || {}, i.status === "review-required" ? this._notice = "This form changed since your last visit — please review your answers." : Object.keys(this.#s).length && (this._notice = "Welcome back — your answers were saved, but attachments need to be re-attached."), this.#o({ animate: !1 });
1455
+ this._forms = r;
1456
+ const i = xt({ attr: this.flow, search: globalThis.location?.search }), n = Ht(Nt(this.#h), this._forms, { apiOrigin: this.api });
1457
+ if ((n.status === "ok" || n.status === "review-required") && _t(n, i)) {
1458
+ this._form = n.form, this._steps = n.steps, this._origins = n.origins || [], this.#t = n.requestId, this.#s = n.lostMedia || {}, n.status === "review-required" ? this._notice = "This form changed since your last visit — please review your answers." : Object.keys(this.#s).length && (this._notice = "Welcome back — your answers were saved, but attachments need to be re-attached."), this.#i({ animate: !1 });
1459
+ return;
1460
+ }
1461
+ const o = vt(this._forms, i);
1462
+ if (o) {
1463
+ this.#I(o);
1121
1464
  return;
1122
1465
  }
1123
1466
  this._phase = "pick";
1124
1467
  }
1125
- #c() {
1468
+ #o() {
1126
1469
  if (!this._form) return;
1127
1470
  const e = {};
1128
- for (const [t, s] of Object.entries(this.#r))
1129
- s.length && (e[t] = s.map(({ name: i, type: n, size: o }) => ({ name: i, type: n, size: o })));
1130
- qe(this.#h, je({
1471
+ for (const [t, r] of Object.entries(this.#r))
1472
+ r.length && (e[t] = r.map(({ name: i, type: n, size: o }) => ({ name: i, type: n, size: o })));
1473
+ Lt(this.#h, qt({
1131
1474
  apiOrigin: this.api,
1132
1475
  form: this._form,
1133
1476
  steps: this._steps,
1134
1477
  requestId: this.#t,
1135
- mediaMeta: e
1478
+ mediaMeta: e,
1479
+ origins: this._origins
1136
1480
  }));
1137
1481
  }
1138
1482
  // ── Walk mechanics ──────────────────────────────────────────────
1139
- #o({ animate: e = !0 } = {}) {
1140
- this._phase = "walk", this._cardValues = {}, this._fieldErrors = {}, this._gate = { stage: null, email: "", error: "", loading: !1 }, e && !this.#z ? (this._typing = !0, clearTimeout(this.#y), this.#y = setTimeout(() => {
1483
+ #i({ animate: e = !0 } = {}) {
1484
+ this._phase = "walk", this._cardValues = {}, this._fieldErrors = {}, this._gate = { stage: null, email: "", error: "", loading: !1 }, e && !this.#O ? (this._typing = !0, clearTimeout(this.#y), this.#y = setTimeout(() => {
1141
1485
  this._typing = !1;
1142
- }, Je)) : this._typing = !1;
1486
+ }, Jt)) : this._typing = !1;
1143
1487
  }
1144
1488
  get #v() {
1145
- return this._form ? V(this._form, this._steps) : { node: null };
1489
+ return this._form ? q(this._form, this._steps) : { node: null };
1146
1490
  }
1147
- #P(e) {
1148
- this._form = e, this._steps = [], this.#t = null, this.#r = {}, this.#s = {}, this._notice = null, this.#c(), this.#o();
1491
+ #I(e) {
1492
+ this._form = e, this._steps = [], this._origins = [], this._handoffError = !1, this.#t = null, this.#r = {}, this.#s = {}, this._notice = null, this.#o(), this.#i();
1149
1493
  }
1150
- #g(e) {
1151
- this._steps = [...this._steps, e], this.#c(), this.#o();
1494
+ #m(e) {
1495
+ this._steps = [...this._steps, e], this.#o(), this.#i();
1152
1496
  }
1153
- #M() {
1497
+ #L(e, t) {
1498
+ if (N(t)) {
1499
+ this.#N(e, t);
1500
+ return;
1501
+ }
1502
+ this._handoffError = !1, this.#m({
1503
+ nodeId: e.id,
1504
+ kind: "choice",
1505
+ optionId: t.id,
1506
+ label: t.label
1507
+ });
1508
+ }
1509
+ /*
1510
+ * Switch to the form a hand-off option names, replaying its preset
1511
+ * steps there. The form being left becomes an origin (see
1512
+ * ../lib/handoff.mjs); its attachments are parked with it in memory so
1513
+ * Back can return them. A target that is missing or no longer matches
1514
+ * its preset path is a config mistake: say so and stay put.
1515
+ */
1516
+ #N(e, t) {
1517
+ const { form: r, steps: i, error: n } = gt(this._forms, t);
1518
+ if (n) {
1519
+ this._handoffError = !0;
1520
+ return;
1521
+ }
1522
+ this._handoffError = !1, this._origins = [...this._origins, {
1523
+ ...bt(this._form, this._steps, e, t),
1524
+ media: this.#r,
1525
+ lostMedia: this.#s
1526
+ }], this._form = r, this._steps = i, this.#t = null, this.#r = {}, this.#s = {}, this._notice = null, this.#o(), this.#i();
1527
+ }
1528
+ /* Back past a hand-off: the originating form, on the choice card. */
1529
+ #q() {
1530
+ const e = this._origins.at(-1);
1531
+ this._origins = this._origins.slice(0, -1), this._form = e.form, this._steps = e.steps, this.#t = null, this.#r = e.media || {}, this.#s = e.lostMedia || {}, this._handoffError = !1, this.#o(), this.#i({ animate: !1 });
1532
+ }
1533
+ #H() {
1154
1534
  if (this._phase === "done" || this._phase === "submitting") return;
1155
1535
  if (this._phase === "review") {
1156
- this.#o({ animate: !1 });
1536
+ this.#i({ animate: !1 });
1537
+ return;
1538
+ }
1539
+ if (this._origins.length && yt(this._steps)) {
1540
+ this.#q();
1157
1541
  return;
1158
1542
  }
1159
1543
  if (!this._steps.length) {
1160
- this.#k();
1544
+ this.#_();
1161
1545
  return;
1162
1546
  }
1163
1547
  const e = this._steps.at(-1);
1164
- this._steps = this._steps.slice(0, -1), e.kind === "collect" && (this._cardValues = { ...e.values }), this.#c(), this.#o({ animate: !1 });
1548
+ this._steps = this._steps.slice(0, -1), e.kind === "collect" && (this._cardValues = { ...e.values }), this.#o(), this.#i({ animate: !1 });
1165
1549
  }
1166
- #k() {
1167
- this.client.endAnonSession?.(), this._form = null, this._steps = [], this.#t = null, this.#r = {}, this.#s = {}, this._result = null, this._banner = null, this._notice = null, this._submit = F([]), j(this.#h), this._phase = "pick";
1550
+ #_() {
1551
+ this.client.endAnonSession?.(), this._form = null, this._steps = [], this._origins = [], this._handoffError = !1, this.#t = null, this.#r = {}, this.#s = {}, this._result = null, this._banner = null, this._notice = null, this._submit = z([]), be(this.#h), this._phase = "pick";
1168
1552
  }
1169
1553
  // ── Collect card ────────────────────────────────────────────────
1170
- #_(e, t) {
1554
+ #$(e, t) {
1171
1555
  this._cardValues = { ...this._cardValues, [e]: t };
1172
1556
  }
1173
- #O(e) {
1174
- const t = e.fields || [], { ok: s, errors: i } = O(t, this._cardValues), n = t.find((d) => d.kind === "media");
1557
+ /* Files attached on the given collect cards (a files-only consent counts them). */
1558
+ #E(e) {
1559
+ let t = 0;
1560
+ for (const r of new Set(e)) t += (this.#r[r] || []).length;
1561
+ return t;
1562
+ }
1563
+ /* Files attached so far on this walk, the card being filled in included. */
1564
+ #S(e) {
1565
+ const t = this._steps.filter((r) => r.kind === "collect").map((r) => r.nodeId);
1566
+ return this.#E([...t, e]);
1567
+ }
1568
+ #j(e) {
1569
+ const t = e.fields || [], { ok: r, errors: i } = he(t, this._cardValues, {
1570
+ mediaCount: this.#S(e.id)
1571
+ }), n = t.find((l) => l.kind === "media");
1175
1572
  let o = !0;
1176
1573
  if (n) {
1177
- const d = this.#r[e.id] || [], u = C(d, this._form.budget, {
1574
+ const l = this.#r[e.id] || [], d = Y(l, this._form.budget, {
1178
1575
  required: !!n.required
1179
1576
  });
1180
- u.ok ? d.length && (this.#s = { ...this.#s, [e.id]: [] }) : (o = !1, i[n.key] = u.errors[0].message);
1577
+ d.ok ? l.length && (this.#s = { ...this.#s, [e.id]: [] }) : (o = !1, i[n.key] = d.errors[0].message);
1181
1578
  }
1182
- if (!s || !o) {
1579
+ if (!r || !o) {
1183
1580
  this._fieldErrors = i;
1184
1581
  return;
1185
1582
  }
1186
- const l = this.#r[e.id] || [];
1187
- this.#g({
1583
+ const a = this.#r[e.id] || [];
1584
+ this.#m({
1188
1585
  nodeId: e.id,
1189
1586
  kind: "collect",
1190
1587
  values: { ...this._cardValues },
1191
- summary: Be(t, this._cardValues, l)
1588
+ summary: Pt(t, this._cardValues, a)
1192
1589
  });
1193
1590
  }
1194
1591
  // ── Gate ────────────────────────────────────────────────────────
1195
- async #E() {
1592
+ async #C() {
1196
1593
  if (!(this._gate.stage || this.#w)) {
1197
1594
  this.#w = !0;
1198
1595
  try {
@@ -1202,11 +1599,11 @@ class at extends T {
1202
1599
  this.#w = !1;
1203
1600
  }
1204
1601
  this._gate.stage === "email" && this.client.onCrossTabLogin && !this.#d && (this.#d = this.client.onCrossTabLogin(() => {
1205
- this.#d?.(), this.#d = null, this._gate = { stage: null, email: "", error: "", loading: !1 }, this.#E();
1602
+ this.#d?.(), this.#d = null, this._gate = { stage: null, email: "", error: "", loading: !1 }, this.#C();
1206
1603
  }));
1207
1604
  }
1208
1605
  }
1209
- async #$() {
1606
+ async #k() {
1210
1607
  const e = this._gate.email.trim();
1211
1608
  if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(e)) {
1212
1609
  this._gate = { ...this._gate, error: "Please enter a valid email address." };
@@ -1224,10 +1621,10 @@ class at extends T {
1224
1621
  };
1225
1622
  }
1226
1623
  }
1227
- async #S(e) {
1624
+ async #T(e) {
1228
1625
  this._gate = { ...this._gate, error: "", loading: !0 };
1229
1626
  try {
1230
- await this.client.verifyCode(e), this.#A(this._gate.email);
1627
+ await this.client.verifyCode(e), this.#R(this._gate.email);
1231
1628
  } catch (t) {
1232
1629
  this._gate = {
1233
1630
  ...this._gate,
@@ -1236,184 +1633,186 @@ class at extends T {
1236
1633
  };
1237
1634
  }
1238
1635
  }
1239
- #A(e) {
1636
+ #R(e) {
1240
1637
  if (this._gate = { stage: null, email: "", error: "", loading: !1 }, this._submit.stage === "auth") {
1241
- this.#e({ type: "AUTH_OK" }), this._phase = "submitting", this.#n();
1638
+ this.#e({ type: "AUTH_OK" }), this._phase = "submitting", this.#a();
1242
1639
  return;
1243
1640
  }
1244
1641
  const { node: t } = this.#v;
1245
- t?.type === "gate" && this.#g({ nodeId: t.id, kind: "gate", email: e });
1642
+ t?.type === "gate" && this.#m({ nodeId: t.id, kind: "gate", email: e });
1246
1643
  }
1247
- #U() {
1644
+ #W() {
1248
1645
  this.client.signOut?.(), this._gate = { stage: "email", email: "", error: "", loading: !1 };
1249
1646
  }
1250
1647
  // ── Anonymous route ─────────────────────────────────────────────
1251
- #q() {
1648
+ #V() {
1252
1649
  this._gate = { ...this._gate, stage: "anon-confirm", error: "" };
1253
1650
  }
1254
- #L() {
1651
+ #Y() {
1255
1652
  this._gate = { ...this._gate, stage: "email", error: "" };
1256
1653
  }
1257
1654
  /*
1258
1655
  * Records the choice only. The session is minted at submit, against
1259
1656
  * the requestId, so an abandoned form leaves nothing behind.
1260
1657
  */
1261
- #j() {
1658
+ #G() {
1262
1659
  const { node: e } = this.#v;
1263
- e?.type === "gate" && (this._gate = { stage: null, email: "", error: "", loading: !1 }, this.#g({ nodeId: e.id, kind: "gate", anonymous: !0 }));
1660
+ e?.type === "gate" && (this._gate = { stage: null, email: "", error: "", loading: !1 }, this.#m({ nodeId: e.id, kind: "gate", anonymous: !0 }));
1264
1661
  }
1265
- async #C() {
1662
+ async #M() {
1266
1663
  try {
1267
1664
  return await this.client.createAnonSession({
1268
1665
  formId: this._form.formId,
1269
1666
  requestId: this.#t
1270
1667
  }), !0;
1271
1668
  } catch (e) {
1272
- return this._banner = q(e?.status ?? 0, e?.body ?? null), !1;
1669
+ return this._banner = me(e?.status ?? 0, e?.body ?? null), !1;
1273
1670
  }
1274
1671
  }
1275
1672
  /* An anonymous session outliving the upload run re-mints in place; there
1276
1673
  * is no identity to send back to the sign-in card. */
1277
- async #N() {
1278
- if (await this.#C()) {
1279
- this.#e({ type: "AUTH_OK" }), this._phase = "submitting", this.#n();
1674
+ async #K() {
1675
+ if (await this.#M()) {
1676
+ this.#e({ type: "AUTH_OK" }), this._phase = "submitting", this.#a();
1280
1677
  return;
1281
1678
  }
1282
1679
  this.#e({ type: "REQUEST_FAIL", error: this._banner });
1283
1680
  }
1284
1681
  // ── Submit pipeline ─────────────────────────────────────────────
1285
- get #m() {
1682
+ get #g() {
1286
1683
  const e = [];
1287
1684
  for (const t of this._steps)
1288
1685
  if (t.kind === "collect")
1289
- for (const s of this.#r[t.nodeId] || [])
1290
- e.push(s);
1686
+ for (const r of this.#r[t.nodeId] || [])
1687
+ e.push(r);
1291
1688
  return e;
1292
1689
  }
1293
1690
  #e(e) {
1294
- this._submit = We(this._submit, e);
1691
+ this._submit = jt(this._submit, e);
1295
1692
  }
1296
- async #W() {
1693
+ async #Q() {
1297
1694
  this._banner = null;
1298
1695
  for (let e = 0; e < this._steps.length; e++) {
1299
1696
  const t = this._steps[e];
1300
1697
  if (t.kind !== "collect") continue;
1301
- const s = b(this._form, t.nodeId), { ok: i, errors: n } = O(s?.fields || [], t.values), o = (s?.fields || []).find((d) => d.kind === "media");
1698
+ const r = x(this._form, t.nodeId), i = this._steps.slice(0, e + 1).filter((d) => d.kind === "collect").map((d) => d.nodeId), { ok: n, errors: o } = he(r?.fields || [], t.values, {
1699
+ mediaCount: this.#E(i)
1700
+ }), a = (r?.fields || []).find((d) => d.kind === "media");
1302
1701
  let l = !0;
1303
- if (o) {
1304
- const d = this.#r[t.nodeId] || [], u = C(d, this._form.budget, {
1305
- required: !!o.required
1702
+ if (a) {
1703
+ const d = this.#r[t.nodeId] || [], p = Y(d, this._form.budget, {
1704
+ required: !!a.required
1306
1705
  });
1307
- u.ok || (l = !1, n[o.key] = u.errors[0].message);
1706
+ p.ok || (l = !1, o[a.key] = p.errors[0].message);
1308
1707
  }
1309
- if (!i || !l) {
1310
- this._steps = this._steps.slice(0, e), this._cardValues = { ...t.values }, this._fieldErrors = n, this.#c(), this.#o({ animate: !1 });
1708
+ if (!n || !l) {
1709
+ this._steps = this._steps.slice(0, e), this._cardValues = { ...t.values }, this._fieldErrors = o, this.#o(), this.#i({ animate: !1 });
1311
1710
  return;
1312
1711
  }
1313
1712
  }
1314
- if (this.#t = this.#t || crypto.randomUUID(), this.#c(), this.#f) {
1315
- if (!await this.#C()) return;
1713
+ if (this.#t = this.#t || crypto.randomUUID(), this.#o(), this.#f) {
1714
+ if (!await this.#M()) return;
1316
1715
  } else
1317
1716
  this.client.endAnonSession?.();
1318
- if (this._submit = F(this.#m), this._phase = "submitting", this.#f) {
1319
- this.#e({ type: "START" }), this.#n();
1717
+ if (this._submit = z(this.#g), this._phase = "submitting", this.#f) {
1718
+ this.#e({ type: "START" }), this.#a();
1320
1719
  return;
1321
1720
  }
1322
1721
  if (!await this.client.isAuthenticated()) {
1323
1722
  this.#e({ type: "START" }), this.#e({ type: "AUTH_REQUIRED" }), this._gate = { stage: "email", email: "", error: "", loading: !1 };
1324
1723
  return;
1325
1724
  }
1326
- this.#e({ type: "START" }), this.#n();
1725
+ this.#e({ type: "START" }), this.#a();
1327
1726
  }
1328
- async #n() {
1727
+ async #a() {
1329
1728
  const e = this._submit.stage;
1330
- if (e === "minting") return this.#V();
1331
- if (e === "uploading") return this.#T();
1332
- if (e === "requesting") return this.#K();
1729
+ if (e === "minting") return this.#J();
1730
+ if (e === "uploading") return this.#D();
1731
+ if (e === "requesting") return this.#ee();
1333
1732
  }
1334
- async #V() {
1733
+ async #J() {
1335
1734
  try {
1336
- const e = await this.client.createUploads(U({
1735
+ const e = await this.client.createUploads(fe({
1337
1736
  formId: this._form.formId,
1338
1737
  requestId: this.#t,
1339
- files: this.#m
1738
+ files: this.#g
1340
1739
  }));
1341
- this.#e({ type: "MINTED", uploads: e }), this.#n();
1740
+ this.#e({ type: "MINTED", uploads: e }), this.#a();
1342
1741
  } catch (e) {
1343
- this.#F(e);
1742
+ this.#A(e);
1344
1743
  }
1345
1744
  }
1346
- #T() {
1347
- const e = this._submit.files, t = this.#i.size;
1348
- let s = 0;
1349
- for (let i = 0; i < e.length && t + s < Xe; i++)
1350
- e[i].status !== "uploading" || this.#i.has(i) || (s += 1, this.#Y(i));
1745
+ #D() {
1746
+ const e = this._submit.files, t = this.#n.size;
1747
+ let r = 0;
1748
+ for (let i = 0; i < e.length && t + r < Zt; i++)
1749
+ e[i].status !== "uploading" || this.#n.has(i) || (r += 1, this.#Z(i));
1351
1750
  }
1352
- #Y(e) {
1353
- const t = this._submit.files[e], s = this.#m[e], { promise: i, abort: n } = this.client.uploadFile({
1751
+ #Z(e) {
1752
+ const t = this._submit.files[e], r = this.#g[e], { promise: i, abort: n } = this.client.uploadFile({
1354
1753
  url: t.url,
1355
- file: s,
1754
+ file: r,
1356
1755
  contentType: t.type,
1357
- onProgress: ({ loaded: o, total: l }) => {
1358
- this.#e({ type: "FILE_PROGRESS", i: e, loaded: o, total: l });
1756
+ onProgress: ({ loaded: o, total: a }) => {
1757
+ this.#e({ type: "FILE_PROGRESS", i: e, loaded: o, total: a });
1359
1758
  }
1360
1759
  });
1361
- this.#i.set(e, { abort: n }), i.then(() => {
1362
- this.#i.delete(e), this.#e({ type: "FILE_DONE", i: e }), this.#n();
1760
+ this.#n.set(e, { abort: n }), i.then(() => {
1761
+ this.#n.delete(e), this.#e({ type: "FILE_DONE", i: e }), this.#a();
1363
1762
  }).catch((o) => {
1364
- this.#i.delete(e), this.#e({
1763
+ this.#n.delete(e), this.#e({
1365
1764
  type: "FILE_FAIL",
1366
1765
  i: e,
1367
1766
  error: o?.status === 403 ? "expired" : "failed"
1368
1767
  });
1369
1768
  });
1370
1769
  }
1371
- async #H(e) {
1770
+ async #X(e) {
1372
1771
  if (this._submit.files[e].error === "expired")
1373
1772
  try {
1374
- const [s] = await this.client.createUploads(U({
1773
+ const [r] = await this.client.createUploads(fe({
1375
1774
  formId: this._form.formId,
1376
1775
  requestId: this.#t,
1377
- files: [this.#m[e]]
1776
+ files: [this.#g[e]]
1378
1777
  }));
1379
- this.#e({ type: "REMINT_FILE", i: e, upload: s });
1380
- } catch (s) {
1381
- this.#F(s);
1778
+ this.#e({ type: "REMINT_FILE", i: e, upload: r });
1779
+ } catch (r) {
1780
+ this.#A(r);
1382
1781
  return;
1383
1782
  }
1384
1783
  else
1385
1784
  this.#e({ type: "RETRY_FILE", i: e });
1386
- this.#T();
1785
+ this.#D();
1387
1786
  }
1388
- async #K() {
1787
+ async #ee() {
1389
1788
  try {
1390
- const e = this._submit.files.map(({ assetId: s, type: i }) => ({ assetId: s, type: i })), t = await this.client.putRequest(this.#t, Te({
1789
+ const e = this._submit.files.map(({ assetId: r, type: i }) => ({ assetId: r, type: i })), t = await this.client.putRequest(this.#t, Ct({
1391
1790
  form: this._form,
1392
1791
  steps: this._steps,
1393
1792
  media: e
1394
1793
  }));
1395
- this.#e({ type: "REQUEST_OK", result: t }), this._result = t, j(this.#h), this.client.endAnonSession?.(), this._phase = "done";
1794
+ this.#e({ type: "REQUEST_OK", result: t }), this._result = t, be(this.#h), this.client.endAnonSession?.(), this._phase = "done";
1396
1795
  } catch (e) {
1397
- this.#F(e);
1796
+ this.#A(e);
1398
1797
  }
1399
1798
  }
1400
- #F(e) {
1401
- const t = q(e?.status ?? 0, e?.body ?? null);
1799
+ #A(e) {
1800
+ const t = me(e?.status ?? 0, e?.body ?? null);
1402
1801
  if (t.kind === "auth") {
1403
1802
  if (this.#e({ type: "AUTH_REQUIRED" }), this.#f) {
1404
- this.#N();
1803
+ this.#K();
1405
1804
  return;
1406
1805
  }
1407
1806
  this._gate = { stage: "email", email: "", error: "", loading: !1 };
1408
1807
  return;
1409
1808
  }
1410
1809
  if (t.kind === "stale") {
1411
- this._banner = t, this.#e({ type: "REQUEST_FAIL", error: t }), this.#Q();
1810
+ this._banner = t, this.#e({ type: "REQUEST_FAIL", error: t }), this.#te();
1412
1811
  return;
1413
1812
  }
1414
1813
  this._banner = t, this.#e({ type: "REQUEST_FAIL", error: t });
1415
1814
  }
1416
- async #Q() {
1815
+ async #te() {
1417
1816
  try {
1418
1817
  this._forms = await this.client.listForms();
1419
1818
  const e = this._forms.find((t) => t.formId === this._form.formId);
@@ -1421,156 +1820,185 @@ class at extends T {
1421
1820
  } catch {
1422
1821
  }
1423
1822
  }
1424
- #G() {
1425
- this._banner = null, this.#e({ type: "REQUEST_START" }), this.#n();
1823
+ #re() {
1824
+ this._banner = null, this.#e({ type: "REQUEST_START" }), this.#a();
1426
1825
  }
1427
1826
  // ── Render ──────────────────────────────────────────────────────
1428
1827
  render() {
1429
- return a`
1828
+ return c`
1430
1829
  <div class="chat" aria-live="polite">
1431
- ${this.#J()}
1830
+ ${this.#se()}
1432
1831
  </div>
1433
- ${this.#ce()}
1832
+ ${this.#ge()}
1434
1833
  `;
1435
1834
  }
1436
- #J() {
1835
+ #se() {
1437
1836
  switch (this._phase) {
1438
1837
  case "loading":
1439
- return a`${h(S, this._loadingSlow ? "Loading the form list…" : A)}
1440
- ${E()}`;
1838
+ return c`${g(W, this._loadingSlow ? "Loading the form list…" : V)}
1839
+ ${j()}`;
1441
1840
  case "load-error":
1442
- return a`
1443
- ${h("We could not load the forms.", "Check your connection and try again.", { error: !0 })}
1841
+ return c`
1842
+ ${g("We could not load the forms.", "Check your connection and try again.", { error: !0 })}
1444
1843
  <div class="options">
1445
1844
  <button type="button" class="chip" @click=${() => this.#x()}>Try again</button>
1446
1845
  </div>
1447
1846
  `;
1448
1847
  case "pick":
1449
- return this.#X();
1848
+ return this.#ie();
1450
1849
  case "walk":
1451
- return a`${this.#b()}${this._typing ? E() : this.#Z()}`;
1850
+ return c`${this.#b()}${this._typing ? j() : this.#ne()}`;
1452
1851
  case "review":
1453
- return a`${this.#b()}${this.#D()}`;
1852
+ return c`${this.#b()}${this.#B()}`;
1454
1853
  case "submitting":
1455
- return a`${this.#b()}${this.#le()}`;
1854
+ return c`${this.#b()}${this.#fe()}`;
1456
1855
  case "done":
1457
- return a`${this.#b()}${this.#de()}`;
1856
+ return c`${this.#b()}${this.#me()}`;
1458
1857
  default:
1459
- return c;
1858
+ return f;
1460
1859
  }
1461
1860
  }
1462
- #X() {
1463
- const e = this._forms;
1464
- return a`
1465
- ${h(S, A, { noAnim: !0 })}
1466
- <div class="options" role="group" aria-label="What would you like to send us?">
1467
- ${e.map((t, s) => a`
1468
- <button type="button" class="chip" style="animation-delay: ${60 + s * 50}ms"
1469
- @click=${() => this.#P(t)}>${t.title}</button>
1861
+ #ie() {
1862
+ const e = this._forms.filter((t) => t.listed !== !1);
1863
+ return c`
1864
+ ${g(W, V, { noAnim: !0 })}
1865
+ <div class="options" role="group" aria-label=${Ee}>
1866
+ ${e.map((t, r) => c`
1867
+ <button type="button" class="chip" style="animation-delay: ${60 + r * 50}ms"
1868
+ @click=${() => this.#I(t)}>${t.title}</button>
1470
1869
  `)}
1471
1870
  </div>
1472
1871
  `;
1473
1872
  }
1873
+ /*
1874
+ * One conversation across hand-offs: the entry choice is the first
1875
+ * form's title, each origin replays its steps and the hand-off option
1876
+ * the viewer picked, and preset steps read as the viewer's own answers
1877
+ * (minus one that merely repeats the hand-off option).
1878
+ */
1474
1879
  #b() {
1475
1880
  const e = [];
1476
- this._form && (e.push(h(S, A, { noAnim: !0 })), e.push($(this._form.title, { noAnim: !0 }))), this._notice && e.push(h(this._notice, "", { noAnim: !0 }));
1477
- for (const t of this._steps) {
1478
- const s = b(this._form, t.nodeId);
1479
- s?.prompt && e.push(h(s.prompt, s.help, { noAnim: !0 })), s?.type === "gate" && e.push(t.anonymous ? h(
1881
+ if (!this._form) return e;
1882
+ const t = this._origins[0]?.form || this._form;
1883
+ e.push(g(W, V, { noAnim: !0 })), e.push(F(t.title, { noAnim: !0 })), this._notice && e.push(g(this._notice, "", { noAnim: !0 }));
1884
+ let r = null;
1885
+ for (const i of this._origins) {
1886
+ e.push(...this.#P(i.form, i.steps, r));
1887
+ const n = x(i.form, i.option.nodeId);
1888
+ n?.prompt && e.push(g(n.prompt, n.help, { noAnim: !0 })), r = i.option.label || i.option.optionId, e.push(F(r, { noAnim: !0 }));
1889
+ }
1890
+ return e.push(...this.#P(this._form, this._steps, r)), e;
1891
+ }
1892
+ #P(e, t, r = null) {
1893
+ const i = [];
1894
+ for (const n of t) {
1895
+ if (n.preset) {
1896
+ const a = n.label || n.optionId;
1897
+ a !== r && i.push(F(a, { noAnim: !0 }));
1898
+ continue;
1899
+ }
1900
+ const o = x(e, n.nodeId);
1901
+ o?.prompt && i.push(g(o.prompt, o.help, { noAnim: !0 })), o?.type === "gate" && i.push(n.anonymous ? g(
1480
1902
  "Last step: how can we reach you?",
1481
1903
  "You chose to send this anonymously.",
1482
1904
  { noAnim: !0 }
1483
- ) : h(
1905
+ ) : g(
1484
1906
  "Last step: verify your email so we can follow up.",
1485
1907
  "One address, one code. No password needed.",
1486
1908
  { noAnim: !0 }
1487
- )), t.kind === "choice" && e.push($(t.label || t.optionId, { noAnim: !0 })), t.kind === "collect" && e.push($(t.summary || "Details provided", { noAnim: !0 })), t.kind === "gate" && e.push($(t.anonymous ? "Send anonymously" : t.email, { noAnim: !0 }));
1909
+ )), n.kind === "choice" && i.push(F(n.label || n.optionId, { noAnim: !0 })), n.kind === "collect" && i.push(F(n.summary || "Details provided", { noAnim: !0 })), n.kind === "gate" && i.push(F(n.anonymous ? "Send anonymously" : n.email, { noAnim: !0 }));
1488
1910
  }
1489
- return e;
1911
+ return i;
1490
1912
  }
1491
- #Z() {
1913
+ #ne() {
1492
1914
  const { node: e, error: t } = this.#v;
1493
- return t || !e ? h("Something went sideways with this form.", "Please start over.", { error: !0 }) : e.type === "choice" ? this.#ee(e) : e.type === "collect" ? this.#te(e) : e.type === "gate" ? this.#R(e) : e.type === "redirect" ? this.#oe(e) : e.type === "terminal" ? this.#D() : c;
1915
+ return t || !e ? g("Something went sideways with this form.", "Please start over.", { error: !0 }) : e.type === "choice" ? this.#oe(e) : e.type === "collect" ? this.#ae(e) : e.type === "gate" ? this.#z(e) : e.type === "redirect" ? this.#he(e) : e.type === "terminal" ? this.#B() : f;
1494
1916
  }
1495
- #ee(e) {
1496
- return a`
1497
- ${h(e.prompt, e.help)}
1917
+ #oe(e) {
1918
+ return c`
1919
+ ${g(e.prompt, e.help)}
1920
+ ${this._handoffError ? g("We could not load the forms.", "Check your connection and try again.", { error: !0 }) : f}
1498
1921
  <div class="options" role="group" aria-label=${e.prompt || "Choose one"}>
1499
- ${(e.options || []).map((t, s) => a`
1500
- <button type="button" class="chip" style="animation-delay: ${60 + s * 50}ms"
1501
- @click=${() => this.#g({
1502
- nodeId: e.id,
1503
- kind: "choice",
1504
- optionId: t.id,
1505
- label: t.label
1506
- })}>${t.label}</button>
1922
+ ${(e.options || []).map((t, r) => c`
1923
+ <button type="button" class="chip" style="animation-delay: ${60 + r * 50}ms"
1924
+ @click=${() => this.#L(e, t)}>${t.label}</button>
1507
1925
  `)}
1508
1926
  </div>
1509
1927
  `;
1510
1928
  }
1511
- #te(e) {
1929
+ /*
1930
+ * A real <form>, so browsers offer the viewer's saved name, phone and
1931
+ * address for the autocomplete-tagged fields, and Enter continues.
1932
+ * novalidate: the card validates itself (native url checks would
1933
+ * otherwise block the submit silently).
1934
+ */
1935
+ #ae(e) {
1512
1936
  const t = e.fields || [];
1513
- return a`
1514
- ${h(e.prompt, e.help)}
1515
- <div class="form-card">
1516
- ${t.map((s) => this.#re(e, s))}
1517
- <button type="button" class="btn-primary" @click=${() => this.#O(e)}>
1518
- Continue
1519
- </button>
1520
- </div>
1937
+ return c`
1938
+ ${g(e.prompt, e.help)}
1939
+ <form class="form-card" autocomplete="on" novalidate
1940
+ @submit=${(r) => {
1941
+ r.preventDefault(), this.#j(e);
1942
+ }}>
1943
+ ${t.map((r) => this.#le(e, r))}
1944
+ <button type="submit" class="btn-primary">Continue</button>
1945
+ </form>
1521
1946
  `;
1522
1947
  }
1523
- #re(e, t) {
1524
- const s = this._cardValues[t.key], i = this._fieldErrors[t.key], n = !t.required && t.kind !== "consent" ? a` <span class="opt">optional</span>` : c, o = t.kind === "consent" ? c : a`
1525
- <label for="f-${t.key}">${t.label}${n}</label>
1948
+ #le(e, t) {
1949
+ const r = this.#S(e.id);
1950
+ if (t.kind === "consent" && t.requiredIf === "media" && r === 0)
1951
+ return f;
1952
+ const i = this._cardValues[t.key], n = this._fieldErrors[t.key], o = !Fe(t, { mediaCount: r }) && t.kind !== "consent" ? c` <span class="opt">optional</span>` : f, a = t.kind === "consent" ? f : c`
1953
+ <label for="f-${t.key}">${t.label}${o}</label>
1526
1954
  `;
1527
- return a`
1955
+ return c`
1528
1956
  <div class="field">
1529
- ${o}
1530
- ${this.#se(e, t, s)}
1531
- ${i ? a`<div class="err" role="alert">${i}</div>` : c}
1957
+ ${a}
1958
+ ${this.#ce(e, t, i)}
1959
+ ${n ? c`<div class="err" role="alert">${n}</div>` : f}
1532
1960
  </div>
1533
1961
  `;
1534
1962
  }
1535
- #se(e, t, s) {
1536
- const i = (n) => (o) => this.#_(n, o.target.value);
1963
+ #ce(e, t, r) {
1964
+ const i = (n) => (o) => this.#$(n, o.target.value);
1537
1965
  switch (t.kind) {
1538
1966
  case "text":
1539
- return a`<input type="text" id="f-${t.key}" .value=${s || ""}
1967
+ return c`<input type="text" id="f-${t.key}" name=${t.key} .value=${r || ""}
1968
+ inputmode=${ce(t.inputMode)} autocomplete=${ce(t.autocomplete)}
1540
1969
  placeholder=${t.placeholder || ""} @input=${i(t.key)}>`;
1541
1970
  case "url":
1542
- return a`<input type="url" id="f-${t.key}" .value=${s || ""}
1971
+ return c`<input type="url" id="f-${t.key}" .value=${r || ""}
1543
1972
  placeholder=${t.placeholder || ""} @input=${i(t.key)}>`;
1544
1973
  case "textarea":
1545
- return a`<textarea id="f-${t.key}" .value=${s || ""}
1974
+ return c`<textarea id="f-${t.key}" .value=${r || ""}
1546
1975
  placeholder=${t.placeholder || ""} @input=${i(t.key)}></textarea>`;
1547
1976
  case "datetime":
1548
- return a`<input type="datetime-local" id="f-${t.key}" .value=${s || ""}
1977
+ return c`<input type="datetime-local" id="f-${t.key}" .value=${r || ""}
1549
1978
  @input=${i(t.key)}>`;
1550
1979
  case "select":
1551
- return a`
1980
+ return c`
1552
1981
  <select id="f-${t.key}" @change=${i(t.key)}>
1553
1982
  <option value="">Choose one</option>
1554
- ${(t.options || []).map((n) => a`
1555
- <option value=${n.id} ?selected=${s === n.id}>${n.label}</option>
1983
+ ${(t.options || []).map((n) => c`
1984
+ <option value=${n.id} ?selected=${r === n.id}>${n.label}</option>
1556
1985
  `)}
1557
1986
  </select>
1558
1987
  `;
1559
1988
  case "location":
1560
- return this.#ie(t, s || {});
1989
+ return this.#de(t, r || {});
1561
1990
  case "consent":
1562
- return a`
1991
+ return c`
1563
1992
  <div class="consent-row">
1564
- <input type="checkbox" id="f-${t.key}" .checked=${s === !0}
1565
- @change=${(n) => this.#_(t.key, n.target.checked)}>
1993
+ <input type="checkbox" id="f-${t.key}" .checked=${r === !0}
1994
+ @change=${(n) => this.#$(t.key, n.target.checked)}>
1566
1995
  <label for="f-${t.key}" style="all: unset; cursor: pointer;">
1567
- I took or own this material and give WRAL permission to use it
1568
- on air and online with credit to me.
1996
+ ${t.text || er}
1569
1997
  </label>
1570
1998
  </div>
1571
1999
  `;
1572
2000
  case "media":
1573
- return a`
2001
+ return c`
1574
2002
  <wral-report-media
1575
2003
  .files=${this.#r[e.id] || []}
1576
2004
  .lostMeta=${this.#s[e.id] || []}
@@ -1582,16 +2010,16 @@ class at extends T {
1582
2010
  }}></wral-report-media>
1583
2011
  `;
1584
2012
  default:
1585
- return c;
2013
+ return f;
1586
2014
  }
1587
2015
  }
1588
- #ie(e, t) {
1589
- const s = e.counties || Ye, i = (n) => this.#_(e.key, { ...t, ...n });
1590
- return a`
2016
+ #de(e, t) {
2017
+ const r = e.counties || Vt, i = (n) => this.#$(e.key, { ...t, ...n });
2018
+ return c`
1591
2019
  <select id="f-${e.key}" aria-label="County"
1592
2020
  @change=${(n) => i({ county: n.target.value || void 0 })}>
1593
2021
  <option value="">Choose a county</option>
1594
- ${s.map((n) => a`
2022
+ ${r.map((n) => c`
1595
2023
  <option value=${n} ?selected=${t.county === n}>${n}</option>
1596
2024
  `)}
1597
2025
  </select>
@@ -1602,25 +2030,25 @@ class at extends T {
1602
2030
  @input=${(n) => i({ where: n.target.value || void 0 })}>
1603
2031
  `;
1604
2032
  }
1605
- #R(e) {
1606
- this.#E();
1607
- const t = this._gate, s = h(
2033
+ #z(e) {
2034
+ this.#C();
2035
+ const t = this._gate, r = g(
1608
2036
  "Last step: verify your email so we can follow up.",
1609
2037
  "One address, one code. No password needed."
1610
2038
  );
1611
- return t.stage ? t.stage === "signedin" ? a`
1612
- ${s}
2039
+ return t.stage ? t.stage === "signedin" ? c`
2040
+ ${r}
1613
2041
  <div class="form-card">
1614
2042
  <p style="margin: 0 0 12px; font-size: 14.5px;">
1615
2043
  You are signed in as <strong>${t.email || "your My WRAL account"}</strong> on this device.
1616
2044
  </p>
1617
2045
  <button type="button" class="btn-primary"
1618
- @click=${() => this.#A(t.email)}>Continue</button>
2046
+ @click=${() => this.#R(t.email)}>Continue</button>
1619
2047
  <button type="button" class="btn-ghost"
1620
- @click=${() => this.#U()}>Use a different email</button>
2048
+ @click=${() => this.#W()}>Use a different email</button>
1621
2049
  </div>
1622
- ` : t.stage === "email" ? a`
1623
- ${s}
2050
+ ` : t.stage === "email" ? c`
2051
+ ${r}
1624
2052
  <div class="form-card login-card">
1625
2053
  <h2>Sign in or create account</h2>
1626
2054
  <p class="login-sub">
@@ -1634,12 +2062,12 @@ class at extends T {
1634
2062
  this._gate = { ...t, email: i.target.value };
1635
2063
  }}
1636
2064
  @keydown=${(i) => {
1637
- i.key === "Enter" && this.#$();
2065
+ i.key === "Enter" && this.#k();
1638
2066
  }}>
1639
2067
  </div>
1640
- ${t.error ? a`<div class="err" role="alert">${t.error}</div>` : c}
2068
+ ${t.error ? c`<div class="err" role="alert">${t.error}</div>` : f}
1641
2069
  <button type="button" class="login-btn" ?disabled=${t.loading}
1642
- @click=${() => this.#$()}>
2070
+ @click=${() => this.#k()}>
1643
2071
  ${t.loading ? "Sending…" : "Continue with email"}
1644
2072
  </button>
1645
2073
  <div class="login-why">
@@ -1648,13 +2076,13 @@ class at extends T {
1648
2076
  <li>We can follow up on your report</li>
1649
2077
  <li>Your contact information fills in automatically next time</li>
1650
2078
  <li>You are credited by name when we use your photos or video</li>
1651
- <li><a href=${He} target="_blank" rel="noopener">All other My WRAL account benefits</a></li>
2079
+ <li><a href=${Yt} target="_blank" rel="noopener">All other My WRAL account benefits</a></li>
1652
2080
  </ul>
1653
2081
  </div>
1654
- ${this._submit.stage === "auth" ? c : this.#ne()}
2082
+ ${this._submit.stage === "auth" ? f : this.#ue()}
1655
2083
  </div>
1656
- ` : t.stage === "anon-confirm" ? this.#ae(s) : a`
1657
- ${s}
2084
+ ` : t.stage === "anon-confirm" ? this.#pe(r) : c`
2085
+ ${r}
1658
2086
  <div class="form-card login-card">
1659
2087
  <h2>Enter verification code</h2>
1660
2088
  <p class="login-sub">We sent a 6-digit code to <strong>${t.email}</strong></p>
@@ -1667,48 +2095,48 @@ class at extends T {
1667
2095
  <div class="field">
1668
2096
  <label>Verification code</label>
1669
2097
  <wral-code-input
1670
- @code-complete=${(i) => this.#S(i.detail?.code ?? i.detail?.value ?? i.target.value)}>
2098
+ @code-complete=${(i) => this.#T(i.detail?.code ?? i.detail?.value ?? i.target.value)}>
1671
2099
  </wral-code-input>
1672
2100
  </div>
1673
- ${t.error ? a`<div class="err" role="alert">${t.error}</div>` : c}
2101
+ ${t.error ? c`<div class="err" role="alert">${t.error}</div>` : f}
1674
2102
  <button type="button" class="login-btn" ?disabled=${t.loading}
1675
2103
  @click=${() => {
1676
2104
  const i = this.renderRoot.querySelector("wral-code-input");
1677
- this.#S(i?.value || "");
2105
+ this.#T(i?.value || "");
1678
2106
  }}>
1679
2107
  ${t.loading ? "Checking…" : "Sign in"}
1680
2108
  </button>
1681
2109
  <p class="login-help">
1682
2110
  Didn’t receive a code? Check your spam folder or
1683
- <button type="button" @click=${() => this.#$()}>resend a new code</button>.
2111
+ <button type="button" @click=${() => this.#k()}>resend a new code</button>.
1684
2112
  </p>
1685
2113
  </div>
1686
- ` : a`${s}${E()}`;
2114
+ ` : c`${r}${j()}`;
1687
2115
  }
1688
2116
  /* Collapsed by default: findable for whoever needs it, never the
1689
2117
  * first thing a viewer reaches for. */
1690
- #ne() {
1691
- return a`
2118
+ #ue() {
2119
+ return c`
1692
2120
  <details class="login-alt">
1693
2121
  <summary>Other ways to send this</summary>
1694
2122
  <div class="alt-body">
1695
2123
  <p class="alt-row">
1696
2124
  Call the newsroom desk at
1697
- <a href=${Qe(W)}>${W}</a>.
2125
+ <a href=${Kt(we)}>${we}</a>.
1698
2126
  </p>
1699
- ${this.#B ? a`
2127
+ ${this.#U ? c`
1700
2128
  <p class="alt-row">
1701
2129
  <button type="button" class="alt-link"
1702
- @click=${() => this.#q()}>Send this anonymously</button>
2130
+ @click=${() => this.#V()}>Send this anonymously</button>
1703
2131
  — no follow-up, and no credit if we use your photos or video.
1704
2132
  </p>
1705
- ` : c}
2133
+ ` : f}
1706
2134
  </div>
1707
2135
  </details>
1708
2136
  `;
1709
2137
  }
1710
- #ae(e) {
1711
- return a`
2138
+ #pe(e) {
2139
+ return c`
1712
2140
  ${e}
1713
2141
  <div class="form-card login-card">
1714
2142
  <h2>Before you send anonymously</h2>
@@ -1716,22 +2144,22 @@ class at extends T {
1716
2144
  You can send this report without an account. Here is what it costs you.
1717
2145
  </p>
1718
2146
  <ul class="anon-costs">
1719
- ${Ke.map((t) => a`
2147
+ ${Gt.map((t) => c`
1720
2148
  <li><span class="x" aria-hidden="true">✕</span><span>${t}</span></li>
1721
2149
  `)}
1722
2150
  </ul>
1723
2151
  <div class="anon-actions">
1724
2152
  <button type="button" class="login-btn"
1725
- @click=${() => this.#L()}>Sign in instead</button>
2153
+ @click=${() => this.#Y()}>Sign in instead</button>
1726
2154
  <button type="button" class="btn-ghost"
1727
- @click=${() => this.#j()}>Continue anonymously</button>
2155
+ @click=${() => this.#G()}>Continue anonymously</button>
1728
2156
  </div>
1729
2157
  </div>
1730
2158
  `;
1731
2159
  }
1732
- #oe(e) {
2160
+ #he(e) {
1733
2161
  const t = e.redirect || {};
1734
- return a`
2162
+ return c`
1735
2163
  <div class="form-card">
1736
2164
  <p style="margin: 0 0 6px; font-weight: 600; font-size: 16px;
1737
2165
  color: var(--wral-base-primary-1, #001D68);
@@ -1748,33 +2176,33 @@ class at extends T {
1748
2176
  </div>
1749
2177
  `;
1750
2178
  }
1751
- #D() {
1752
- const e = Pe(this._form, this._steps);
1753
- return a`
1754
- ${h("Here is what you are sending.", "Check it over, then submit.")}
2179
+ #B() {
2180
+ const e = zt(this._form, this._steps);
2181
+ return c`
2182
+ ${g("Here is what you are sending.", "Check it over, then submit.")}
1755
2183
  <div class="form-card">
1756
2184
  <ul class="review-list">
1757
- ${e.map((t) => a`
2185
+ ${e.map((t) => c`
1758
2186
  <li>
1759
2187
  <span class="k">${t.k}</span>
1760
- <span>${t.pill ? be(t.pill) : t.v}</span>
2188
+ <span>${t.pill ? it(t.pill) : t.v}</span>
1761
2189
  </li>
1762
2190
  `)}
1763
2191
  </ul>
1764
- ${this._banner ? a`
2192
+ ${this._banner ? c`
1765
2193
  <div class="err" role="alert" style="margin-top: 12px;">${this._banner.message}</div>
1766
- ` : c}
2194
+ ` : f}
1767
2195
  <div style="margin-top: 16px;">
1768
- <button type="button" class="btn-primary" @click=${() => this.#W()}>
2196
+ <button type="button" class="btn-primary" @click=${() => this.#Q()}>
1769
2197
  Submit report
1770
2198
  </button>
1771
2199
  </div>
1772
2200
  </div>
1773
2201
  `;
1774
2202
  }
1775
- #le() {
2203
+ #fe() {
1776
2204
  const e = this._submit;
1777
- if (e.stage === "auth") return this.#R({ id: null, type: "gate" });
2205
+ if (e.stage === "auth") return this.#z({ id: null, type: "gate" });
1778
2206
  const t = {
1779
2207
  minting: "Preparing your uploads…",
1780
2208
  uploading: "Uploading your files…",
@@ -1782,77 +2210,77 @@ class at extends T {
1782
2210
  requesting: "Sending your report…",
1783
2211
  "requesting-error": this._banner?.message || "We could not send your report."
1784
2212
  }[e.stage] || "Working…";
1785
- return a`
1786
- ${h("Submitting your report.", t)}
2213
+ return c`
2214
+ ${g("Submitting your report.", t)}
1787
2215
  <div class="form-card">
1788
- ${e.files.map((s, i) => a`
2216
+ ${e.files.map((r, i) => c`
1789
2217
  <div class="upload-row">
1790
- <span class="name">${s.name}</span>
2218
+ <span class="name">${r.name}</span>
1791
2219
  <div class="upload-bar" role="progressbar"
1792
2220
  aria-valuemin="0" aria-valuemax="100"
1793
- aria-valuenow=${Math.round((s.status === "done" ? 1 : s.progress) * 100)}>
1794
- <div class="fill" style="width: ${(s.status === "done" ? 1 : s.progress) * 100}%"></div>
2221
+ aria-valuenow=${Math.round((r.status === "done" ? 1 : r.progress) * 100)}>
2222
+ <div class="fill" style="width: ${(r.status === "done" ? 1 : r.progress) * 100}%"></div>
1795
2223
  </div>
1796
- <span class="state ${s.status === "failed" ? "failed" : ""}">
1797
- ${s.status === "done" ? "Done" : s.status === "failed" ? "Failed" : "Uploading"}
2224
+ <span class="state ${r.status === "failed" ? "failed" : ""}">
2225
+ ${r.status === "done" ? "Done" : r.status === "failed" ? "Failed" : "Uploading"}
1798
2226
  </span>
1799
- ${s.status === "failed" ? a`
1800
- <button type="button" class="retry-chip" @click=${() => this.#H(i)}>
2227
+ ${r.status === "failed" ? c`
2228
+ <button type="button" class="retry-chip" @click=${() => this.#X(i)}>
1801
2229
  Retry
1802
2230
  </button>
1803
- ` : c}
2231
+ ` : f}
1804
2232
  </div>
1805
2233
  `)}
1806
- ${e.stage === "requesting-error" ? a`
2234
+ ${e.stage === "requesting-error" ? c`
1807
2235
  <div class="err" role="alert">${this._banner?.message || ""}</div>
1808
- ${this._banner?.retryAfter ? a`
2236
+ ${this._banner?.retryAfter ? c`
1809
2237
  <div class="file-note">You can try again in about
1810
2238
  ${Math.ceil(this._banner.retryAfter / 60)} minutes.</div>
1811
- ` : c}
2239
+ ` : f}
1812
2240
  <button type="button" class="btn-primary" style="margin-top: 8px;"
1813
- @click=${() => this.#G()}>Try again</button>
1814
- ` : c}
1815
- ${N(e).length && e.stage === "uploading-error" ? a`
2241
+ @click=${() => this.#re()}>Try again</button>
2242
+ ` : f}
2243
+ ${ye(e).length && e.stage === "uploading-error" ? c`
1816
2244
  <div class="err" role="alert">Retry the failed
1817
- ${N(e).length === 1 ? "file" : "files"} to continue.</div>
1818
- ` : c}
2245
+ ${ye(e).length === 1 ? "file" : "files"} to continue.</div>
2246
+ ` : f}
1819
2247
  </div>
1820
2248
  `;
1821
2249
  }
1822
- #de() {
1823
- const e = Y(this._form, this._steps), t = Me(this._result, e), s = Ue({
2250
+ #me() {
2251
+ const e = ke(this._form, this._steps), t = Bt(this._result, e), r = Ut({
1824
2252
  routing: this._result?.routing || {},
1825
2253
  flags: e,
1826
2254
  reference: this._result?.reference || "",
1827
2255
  anonymous: this.#f
1828
2256
  });
1829
- return a`
2257
+ return c`
1830
2258
  <div class="confirm-card">
1831
2259
  <div class="c-head">
1832
- <div class="c-check">${ye()}</div>
2260
+ <div class="c-check">${nt()}</div>
1833
2261
  <div>
1834
2262
  <div class="eyebrow">Report received</div>
1835
2263
  <h2>${t.title}</h2>
1836
2264
  </div>
1837
2265
  </div>
1838
2266
  <p>${t.body}</p>
1839
- ${t.urgentNote ? a`<p>${t.urgentNote}</p>` : c}
2267
+ ${t.urgentNote ? c`<p>${t.urgentNote}</p>` : f}
1840
2268
  <div class="refs">
1841
2269
  <span class="ref"><span class="rk">Reference</span>${this._result?.reference || ""}</span>
1842
2270
  </div>
1843
- <button type="button" class="c-again" @click=${() => this.#k()}>
2271
+ <button type="button" class="c-again" @click=${() => this.#_()}>
1844
2272
  Start a new report
1845
2273
  </button>
1846
2274
  </div>
1847
2275
  <div class="journey">
1848
2276
  <div class="j-eyebrow">Behind the scenes</div>
1849
2277
  <div class="j-title">What happens to your report now</div>
1850
- ${s.map((i, n) => a`
2278
+ ${r.map((i, n) => c`
1851
2279
  <div class="j-step">
1852
2280
  <div class="j-dot">${n + 1}</div>
1853
2281
  <div class="j-body">
1854
2282
  <div class="j-t">${i.title}
1855
- ${i.pill ? a` <span class="flag-pill urgent">${i.pill}</span>` : c}
2283
+ ${i.pill ? c` <span class="flag-pill urgent">${i.pill}</span>` : f}
1856
2284
  </div>
1857
2285
  <div class="j-d">${i.body}</div>
1858
2286
  </div>
@@ -1861,15 +2289,15 @@ class at extends T {
1861
2289
  </div>
1862
2290
  `;
1863
2291
  }
1864
- #ce() {
2292
+ #ge() {
1865
2293
  const e = this._phase === "submitting" || this._phase === "done" || this._phase === "loading" || this._phase === "load-error";
1866
- return a`
2294
+ return c`
1867
2295
  <div class="bottom-bar">
1868
2296
  <div class="inner">
1869
2297
  <button type="button" class="btn-ghost" ?disabled=${e || this._phase === "pick"}
1870
- @click=${() => this.#M()}>← Back</button>
2298
+ @click=${() => this.#H()}>← Back</button>
1871
2299
  <button type="button" class="btn-ghost" ?disabled=${this._phase === "submitting"}
1872
- @click=${() => this.#k()}>Start over</button>
2300
+ @click=${() => this.#_()}>Start over</button>
1873
2301
  <span class="note">Your report goes to a person on the right desk.</span>
1874
2302
  </div>
1875
2303
  </div>
@@ -1879,7 +2307,7 @@ class at extends T {
1879
2307
  this.renderRoot?.querySelector(".chat")?.lastElementChild?.scrollIntoView?.({ block: "nearest" });
1880
2308
  }
1881
2309
  }
1882
- class ot extends T {
2310
+ class lr extends G {
1883
2311
  static properties = {
1884
2312
  files: { attribute: !1 },
1885
2313
  lostMeta: { attribute: !1 },
@@ -1887,7 +2315,7 @@ class ot extends T {
1887
2315
  required: { type: Boolean },
1888
2316
  label: { type: String }
1889
2317
  };
1890
- static styles = f`
2318
+ static styles = y`
1891
2319
  :host { display: block; }
1892
2320
  input[type=file] { font-family: inherit; font-size: 14px; }
1893
2321
  .file-list { margin: 8px 0 0; padding: 0; list-style: none; font-size: 13.5px; }
@@ -1909,10 +2337,10 @@ class ot extends T {
1909
2337
  constructor() {
1910
2338
  super(), this.files = [], this.lostMeta = [], this.budget = {}, this.required = !1, this.label = "Photos or video";
1911
2339
  }
1912
- get #l() {
2340
+ get #c() {
1913
2341
  return (this.budget?.allowedTypes || []).join(",");
1914
2342
  }
1915
- #a(e) {
2343
+ #l(e) {
1916
2344
  this.dispatchEvent(new CustomEvent("files-changed", {
1917
2345
  detail: { files: e },
1918
2346
  bubbles: !0,
@@ -1921,76 +2349,76 @@ class ot extends T {
1921
2349
  }
1922
2350
  #u(e) {
1923
2351
  const t = [...e.target.files || []];
1924
- this.#a([...this.files || [], ...t]), e.target.value = "";
2352
+ this.#l([...this.files || [], ...t]), e.target.value = "";
1925
2353
  }
1926
2354
  #t(e) {
1927
2355
  const t = [...this.files];
1928
- t.splice(e, 1), this.#a(t);
2356
+ t.splice(e, 1), this.#l(t);
1929
2357
  }
1930
2358
  render() {
1931
- const e = this.files || [], { errors: t } = C(e, this.budget, { required: !1 });
1932
- return a`
2359
+ const e = this.files || [], { errors: t } = Y(e, this.budget, { required: !1 });
2360
+ return c`
1933
2361
  <input type="file" multiple
1934
- accept=${this.#l || c}
2362
+ accept=${this.#c || f}
1935
2363
  aria-label=${this.label}
1936
2364
  @change=${this.#u}>
1937
- ${e.length ? a`
2365
+ ${e.length ? c`
1938
2366
  <ul class="file-list">
1939
- ${e.map((s, i) => a`
2367
+ ${e.map((r, i) => c`
1940
2368
  <li>
1941
- <span>${s.name}</span>
1942
- <span class="size">${et(s.size)}</span>
2369
+ <span>${r.name}</span>
2370
+ <span class="size">${tr(r.size)}</span>
1943
2371
  <button type="button" class="remove"
1944
- aria-label="Remove ${s.name}"
2372
+ aria-label="Remove ${r.name}"
1945
2373
  @click=${() => this.#t(i)}>✕</button>
1946
2374
  </li>
1947
2375
  `)}
1948
2376
  </ul>
1949
- ` : c}
1950
- ${(this.lostMeta || []).length ? a`
2377
+ ` : f}
2378
+ ${(this.lostMeta || []).length ? c`
1951
2379
  <div class="lost">
1952
2380
  Please re-attach your ${this.lostMeta.length === 1 ? "file" : "files"}
1953
- (${this.lostMeta.map((s) => s.name).join(", ")}) —
2381
+ (${this.lostMeta.map((r) => r.name).join(", ")}) —
1954
2382
  attachments can't be saved between visits.
1955
2383
  </div>
1956
- ` : c}
1957
- ${t.map((s) => a`<div class="err">${s.message}</div>`)}
2384
+ ` : f}
2385
+ ${t.map((r) => c`<div class="err">${r.message}</div>`)}
1958
2386
  `;
1959
2387
  }
1960
2388
  }
1961
- function et(r) {
1962
- return Number.isFinite(r) ? r >= 1024 * 1024 ? `${(r / (1024 * 1024)).toFixed(1)} MB` : r >= 1024 ? `${Math.round(r / 1024)} KB` : `${r} B` : "";
2389
+ function tr(s) {
2390
+ return Number.isFinite(s) ? s >= 1024 * 1024 ? `${(s / (1024 * 1024)).toFixed(1)} MB` : s >= 1024 ? `${Math.round(s / 1024)} KB` : `${s} B` : "";
1963
2391
  }
1964
- const tt = (r, e, t, s) => {
2392
+ const rr = (s, e, t, r) => {
1965
2393
  const i = e.target.value.replace(/\D/g, "").slice(-1), n = [...t];
1966
- n[r] = i;
1967
- const o = n.join(""), l = n.every((d) => d !== "");
1968
- return s("code-change", { value: o, complete: l }), i && l && s("code-complete", { value: o }), n;
1969
- }, rt = (r, e, t, s) => {
2394
+ n[s] = i;
2395
+ const o = n.join(""), a = n.every((l) => l !== "");
2396
+ return r("code-change", { value: o, complete: a }), i && a && r("code-complete", { value: o }), n;
2397
+ }, sr = (s, e, t, r) => {
1970
2398
  if (e.key === "Backspace") {
1971
2399
  const i = [...t];
1972
- !i[r] && r > 0 ? i[r - 1] = "" : i[r] && (i[r] = "");
2400
+ !i[s] && s > 0 ? i[s - 1] = "" : i[s] && (i[s] = "");
1973
2401
  const n = i.join("");
1974
- return s("code-change", { value: n, complete: !1 }), i;
2402
+ return r("code-change", { value: n, complete: !1 }), i;
1975
2403
  }
1976
2404
  return t;
1977
- }, st = (r, e, t) => {
1978
- r.preventDefault();
1979
- const s = r.clipboardData.getData("text").replace(/\D/g, "").slice(0, 6);
1980
- if (s.length === 0) return e;
2405
+ }, ir = (s, e, t) => {
2406
+ s.preventDefault();
2407
+ const r = s.clipboardData.getData("text").replace(/\D/g, "").slice(0, 6);
2408
+ if (r.length === 0) return e;
1981
2409
  const i = [...e];
1982
- for (let l = 0; l < s.length && l < 6; l++)
1983
- i[l] = s[l];
1984
- const n = i.join(""), o = i.every((l) => l !== "");
1985
- return t("code-change", { value: n, complete: o }), s.length === 6 && t("code-complete", { value: n }), i;
2410
+ for (let a = 0; a < r.length && a < 6; a++)
2411
+ i[a] = r[a];
2412
+ const n = i.join(""), o = i.every((a) => a !== "");
2413
+ return t("code-change", { value: n, complete: o }), r.length === 6 && t("code-complete", { value: n }), i;
1986
2414
  };
1987
- class lt extends T {
2415
+ class cr extends G {
1988
2416
  static formAssociated = !0;
1989
2417
  static properties = {
1990
2418
  _values: { type: Array, state: !0 },
1991
2419
  disabled: { type: Boolean, reflect: !0 }
1992
2420
  };
1993
- static styles = f`
2421
+ static styles = y`
1994
2422
  :host {
1995
2423
  display: block;
1996
2424
  width: 100%;
@@ -2089,7 +2517,7 @@ class lt extends T {
2089
2517
  this.getInputs()[e]?.focus();
2090
2518
  }
2091
2519
  inputHandler(e, t) {
2092
- this._values = tt(
2520
+ this._values = rr(
2093
2521
  e,
2094
2522
  t,
2095
2523
  this._values,
@@ -2098,22 +2526,22 @@ class lt extends T {
2098
2526
  }
2099
2527
  keydownHandler(e, t) {
2100
2528
  if (t.key === "Backspace") {
2101
- const s = !this._values[e];
2102
- this._values = rt(
2529
+ const r = !this._values[e];
2530
+ this._values = sr(
2103
2531
  e,
2104
2532
  t,
2105
2533
  this._values,
2106
2534
  this.dispatchCustomEvent.bind(this)
2107
- ), s && e > 0 && this.focusInput(e - 1);
2535
+ ), r && e > 0 && this.focusInput(e - 1);
2108
2536
  }
2109
2537
  }
2110
2538
  pasteHandler(e) {
2111
- this._values = st(e, this._values, this.dispatchCustomEvent.bind(this));
2539
+ this._values = ir(e, this._values, this.dispatchCustomEvent.bind(this));
2112
2540
  }
2113
2541
  render() {
2114
- return a`
2542
+ return c`
2115
2543
  <div class="code-inputs">
2116
- ${[0, 1, 2, 3, 4, 5].map((e) => a`
2544
+ ${[0, 1, 2, 3, 4, 5].map((e) => c`
2117
2545
  <input
2118
2546
  type = "text"
2119
2547
  inputmode = "numeric"
@@ -2133,10 +2561,10 @@ class lt extends T {
2133
2561
  }
2134
2562
  }
2135
2563
  export {
2136
- lt as W,
2137
- ot as a,
2138
- at as b,
2139
- ve as c,
2140
- xe as d,
2141
- ke as e
2564
+ cr as W,
2565
+ lr as a,
2566
+ ar as b,
2567
+ ct as c,
2568
+ at as d,
2569
+ dt as e
2142
2570
  };