@sphoro/bugcatch-web-sdk 0.19.0 → 0.21.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +54 -1
- package/dist/bugcatch-call.umd.js +1 -1
- package/dist/bugcatch-core.es.js +652 -497
- package/dist/bugcatch-core.es.js.map +1 -1
- package/dist/bugcatch-panel.es.js +1307 -964
- package/dist/bugcatch-panel.es.js.map +1 -1
- package/dist/bugcatch-panel.umd.js +291 -158
- package/dist/bugcatch-panel.umd.js.map +1 -1
- package/dist/bugcatch.standalone.umd.js +284 -151
- package/dist/bugcatch.standalone.umd.js.map +1 -1
- package/dist/bugcatch.umd.js +8 -8
- package/dist/bugcatch.umd.js.map +1 -1
- package/package.json +1 -1
- package/src/feedback.js +94 -0
- package/src/identity.js +1 -1
- package/src/index.d.ts +65 -6
- package/src/index.js +111 -7
- package/src/panel/call.js +3 -2
- package/src/panel/compose.js +8 -4
- package/src/panel/feedback.js +205 -0
- package/src/panel/icons.js +6 -0
- package/src/panel/index.js +91 -12
- package/src/panel/rate-due.js +155 -0
- package/src/panel/rating.js +87 -0
- package/src/panel/signin.js +1 -1
- package/src/panel/styles.js +75 -0
- package/src/panel/thread.js +3 -72
- package/src/widget.js +14 -1
package/dist/bugcatch-core.es.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
var
|
|
1
|
+
var ke = (t) => {
|
|
2
2
|
throw TypeError(t);
|
|
3
3
|
};
|
|
4
|
-
var xt = (t, e, n) => e.has(t) ||
|
|
5
|
-
var
|
|
4
|
+
var xt = (t, e, n) => e.has(t) || ke("Cannot " + n);
|
|
5
|
+
var ve = (t, e, n) => e.has(t) ? ke("Cannot add the same private member more than once") : e instanceof WeakSet ? e.add(t) : e.set(t, n);
|
|
6
6
|
var x = (t, e, n) => (xt(t, e, "access private method"), n);
|
|
7
|
-
const
|
|
7
|
+
const ee = "[REDACTED]", kt = /* @__PURE__ */ new Set([
|
|
8
8
|
"auth",
|
|
9
9
|
"bearer",
|
|
10
10
|
"session",
|
|
@@ -28,7 +28,7 @@ const Q = "[REDACTED]", kt = /* @__PURE__ */ new Set([
|
|
|
28
28
|
"privatekey",
|
|
29
29
|
"accesskey",
|
|
30
30
|
"authorization"
|
|
31
|
-
],
|
|
31
|
+
], Ct = /* @__PURE__ */ new Set(["key", "code", "state", "nonce", "salt", "hash"]), Ne = [
|
|
32
32
|
/eyJ[\w-]{8,}\.[\w-]{8,}\.[\w-]+/g,
|
|
33
33
|
// JWT
|
|
34
34
|
/(?:AKIA|ASIA|AROA|AIDA|AGPA|ANPA|ANVA|APKA)[0-9A-Z]{16}/g,
|
|
@@ -51,7 +51,7 @@ const Q = "[REDACTED]", kt = /* @__PURE__ */ new Set([
|
|
|
51
51
|
// GitLab
|
|
52
52
|
/shp(?:at|ss|ca|pa)_[A-Za-z0-9]{32}/g
|
|
53
53
|
// Shopify
|
|
54
|
-
],
|
|
54
|
+
], It = /\bBearer\s+[\w.~+/=-]{8,}/gi, St = /^([A-Za-z][A-Za-z0-9+.-]*:\/\/)([^/?#@]+)@/;
|
|
55
55
|
function Ue(t) {
|
|
56
56
|
try {
|
|
57
57
|
return decodeURIComponent(t.replace(/\+/g, " "));
|
|
@@ -70,42 +70,42 @@ function $t(t, e) {
|
|
|
70
70
|
if (!n) return !1;
|
|
71
71
|
if (kt.has(n)) return !0;
|
|
72
72
|
for (const i of vt) if (n.includes(i)) return !0;
|
|
73
|
-
return
|
|
73
|
+
return Ct.has(n) ? Et(Ue(e)) : !1;
|
|
74
74
|
}
|
|
75
|
-
function
|
|
75
|
+
function oe(t) {
|
|
76
76
|
return t.split("&").map((e) => {
|
|
77
77
|
const n = e.indexOf("=");
|
|
78
78
|
if (n === -1) return e;
|
|
79
79
|
const i = e.slice(0, n), r = e.slice(n + 1);
|
|
80
|
-
return r && $t(i, r) ? `${i}=${
|
|
80
|
+
return r && $t(i, r) ? `${i}=${ee}` : e;
|
|
81
81
|
}).join("&");
|
|
82
82
|
}
|
|
83
|
-
function
|
|
83
|
+
function De(t) {
|
|
84
84
|
let e = t;
|
|
85
85
|
for (const n of Ne)
|
|
86
|
-
n.lastIndex = 0, e = e.replace(n,
|
|
86
|
+
n.lastIndex = 0, e = e.replace(n, ee);
|
|
87
87
|
return e;
|
|
88
88
|
}
|
|
89
|
-
function
|
|
89
|
+
function Pe(t) {
|
|
90
90
|
if (t == null) return t;
|
|
91
91
|
let e = String(t);
|
|
92
92
|
if (!e) return e;
|
|
93
|
-
e = e.replace(St, `$1${
|
|
93
|
+
e = e.replace(St, `$1${ee}@`);
|
|
94
94
|
const n = e.indexOf("#");
|
|
95
95
|
let i = n === -1 ? e : e.slice(0, n), r = n === -1 ? "" : e.slice(n);
|
|
96
96
|
const o = i.indexOf("?");
|
|
97
|
-
if (o !== -1 && (i = i.slice(0, o + 1) +
|
|
97
|
+
if (o !== -1 && (i = i.slice(0, o + 1) + oe(i.slice(o + 1))), r.length > 1) {
|
|
98
98
|
const a = r.slice(1), s = a.indexOf("?");
|
|
99
|
-
s !== -1 ? r = `#${a.slice(0, s + 1)}${
|
|
99
|
+
s !== -1 ? r = `#${a.slice(0, s + 1)}${oe(a.slice(s + 1))}` : a.includes("=") && (r = `#${oe(a)}`);
|
|
100
100
|
}
|
|
101
|
-
return
|
|
101
|
+
return De(i + r);
|
|
102
102
|
}
|
|
103
103
|
function Tt(t) {
|
|
104
104
|
if (t == null) return t;
|
|
105
105
|
let e = String(t);
|
|
106
|
-
return e && (e = e.replace(/[A-Za-z][A-Za-z0-9+.-]{0,30}:\/\/[^\s"'<>)\]]+/g, (n) =>
|
|
106
|
+
return e && (e = e.replace(/[A-Za-z][A-Za-z0-9+.-]{0,30}:\/\/[^\s"'<>)\]]+/g, (n) => Pe(n)), e = e.replace(It, `Bearer ${ee}`), De(e));
|
|
107
107
|
}
|
|
108
|
-
function
|
|
108
|
+
function F(t) {
|
|
109
109
|
const e = [];
|
|
110
110
|
return {
|
|
111
111
|
push(n) {
|
|
@@ -120,10 +120,10 @@ function z(t) {
|
|
|
120
120
|
}
|
|
121
121
|
};
|
|
122
122
|
}
|
|
123
|
-
const
|
|
123
|
+
const Ce = ["log", "info", "warn", "error", "debug"];
|
|
124
124
|
function At(t, { levels: e = ["warn", "error", "log", "info"] } = {}) {
|
|
125
125
|
const n = {};
|
|
126
|
-
for (const i of
|
|
126
|
+
for (const i of Ce)
|
|
127
127
|
n[i] = console[i], e.includes(i) && (console[i] = (...r) => {
|
|
128
128
|
try {
|
|
129
129
|
t.push({
|
|
@@ -136,25 +136,25 @@ function At(t, { levels: e = ["warn", "error", "log", "info"] } = {}) {
|
|
|
136
136
|
n[i].apply(console, r);
|
|
137
137
|
});
|
|
138
138
|
return () => {
|
|
139
|
-
for (const i of
|
|
139
|
+
for (const i of Ce) console[i] = n[i];
|
|
140
140
|
};
|
|
141
141
|
}
|
|
142
142
|
function jt(t, { slowMs: e = 2e3 } = {}) {
|
|
143
143
|
const n = window.fetch, i = XMLHttpRequest.prototype.open, r = XMLHttpRequest.prototype.send;
|
|
144
144
|
return n && (window.fetch = async function(...a) {
|
|
145
|
-
var h, f,
|
|
146
|
-
const s = performance.now(), c = typeof a[0] == "string" ? a[0] : (h = a[0]) == null ? void 0 : h.url, l = ((f = a[1]) == null ? void 0 : f.method) || (typeof a[0] == "object" ? (
|
|
145
|
+
var h, f, u;
|
|
146
|
+
const s = performance.now(), c = typeof a[0] == "string" ? a[0] : (h = a[0]) == null ? void 0 : h.url, l = ((f = a[1]) == null ? void 0 : f.method) || (typeof a[0] == "object" ? (u = a[0]) == null ? void 0 : u.method : "GET") || "GET";
|
|
147
147
|
try {
|
|
148
|
-
const
|
|
149
|
-
return
|
|
150
|
-
} catch (
|
|
151
|
-
throw
|
|
148
|
+
const d = await n.apply(this, a);
|
|
149
|
+
return re(t, { url: c, method: l, status: d.status, ms: Math.round(performance.now() - s), slowMs: e }), d;
|
|
150
|
+
} catch (d) {
|
|
151
|
+
throw re(t, { url: c, method: l, status: 0, error: String((d == null ? void 0 : d.message) || d), ms: Math.round(performance.now() - s), slowMs: e }), d;
|
|
152
152
|
}
|
|
153
153
|
}), XMLHttpRequest.prototype.open = function(a, s, ...c) {
|
|
154
154
|
return this.__bc = { method: a, url: s, started: 0 }, i.call(this, a, s, ...c);
|
|
155
155
|
}, XMLHttpRequest.prototype.send = function(...a) {
|
|
156
156
|
return this.__bc && (this.__bc.started = performance.now(), this.addEventListener("loadend", () => {
|
|
157
|
-
|
|
157
|
+
re(t, {
|
|
158
158
|
url: this.__bc.url,
|
|
159
159
|
method: this.__bc.method,
|
|
160
160
|
status: this.status,
|
|
@@ -166,7 +166,7 @@ function jt(t, { slowMs: e = 2e3 } = {}) {
|
|
|
166
166
|
n && (window.fetch = n), XMLHttpRequest.prototype.open = i, XMLHttpRequest.prototype.send = r;
|
|
167
167
|
};
|
|
168
168
|
}
|
|
169
|
-
function
|
|
169
|
+
function re(t, { url: e, method: n, status: i, ms: r, error: o, slowMs: a }) {
|
|
170
170
|
try {
|
|
171
171
|
t.push({
|
|
172
172
|
// Scrubbed before it is buffered, not before it is sent: a credential
|
|
@@ -175,7 +175,7 @@ function oe(t, { url: e, method: n, status: i, ms: r, error: o, slowMs: a }) {
|
|
|
175
175
|
// then truncate — truncating first would split a token into something
|
|
176
176
|
// no pattern recognises, and the fragment would still be a fragment of
|
|
177
177
|
// a live credential.
|
|
178
|
-
url:
|
|
178
|
+
url: Pe(String(e)).slice(0, 500),
|
|
179
179
|
method: n,
|
|
180
180
|
status: i,
|
|
181
181
|
ms: r,
|
|
@@ -207,7 +207,7 @@ function Ot(t) {
|
|
|
207
207
|
window.removeEventListener("error", e), window.removeEventListener("unhandledrejection", n);
|
|
208
208
|
};
|
|
209
209
|
}
|
|
210
|
-
async function
|
|
210
|
+
async function ae() {
|
|
211
211
|
const t = _e();
|
|
212
212
|
try {
|
|
213
213
|
if (navigator.getBattery) {
|
|
@@ -269,8 +269,8 @@ function He(t) {
|
|
|
269
269
|
return String(t);
|
|
270
270
|
}
|
|
271
271
|
}
|
|
272
|
-
const
|
|
273
|
-
function
|
|
272
|
+
const yi = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><path d="M4 11.5a7.5 7 0 0 1 7.5-7h1a7.5 7 0 0 1 0 14H9l-4.2 2.6a.5.5 0 0 1-.76-.5l.5-3.1A7 7 0 0 1 4 11.5z"/><path d="M8.5 11.5h.01M12 11.5h.01M15.5 11.5h.01" stroke-width="2.6"/></svg>', Mt = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.2" stroke-linecap="round" stroke-linejoin="round"><path d="M6 9.5l6 6 6-6"/></svg>', Rt = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="4.2"/><path d="M12 2.6v2.2M12 19.2v2.2M2.6 12h2.2M19.2 12h2.2M5.4 5.4l1.6 1.6M17 17l1.6 1.6M18.6 5.4L17 7M7 17l-1.6 1.6"/></svg>', Lt = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><path d="M20 13.4A8.2 8.2 0 1 1 10.6 4a6.6 6.6 0 0 0 9.4 9.4z"/></svg>', Kt = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><rect x="2.8" y="4.4" width="18.4" height="12.6" rx="2.2"/><path d="M8.6 20.2h6.8"/><path d="M12 4.4v12.6"/><path d="M12 7.2a3.6 3.6 0 0 1 0 7.2z" fill="currentColor" stroke="none"/></svg>', ze = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="9"/><path d="M12 7.5v5.2M12 16.3h.01"/></svg>', Fe = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M6 6l12 12M18 6L6 18"/></svg>', Nt = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round"><path d="M5 12.8l4.6 4.4L19 7"/></svg>', Xe = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="9"/><path d="M12 11v5.5M12 7.7h.01"/></svg>', Ut = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M10.3 4.2a2 2 0 0 1 3.4 0l7.6 13.1a2 2 0 0 1-1.7 3H4.4a2 2 0 0 1-1.7-3z"/><path d="M12 9.5v4.2M12 17h.01"/></svg>';
|
|
273
|
+
function qe(t, e) {
|
|
274
274
|
console.warn(`[BugCatch] ${t}`, ...e ? [e] : []);
|
|
275
275
|
const n = new Error("[BugCatch] part of the widget could not be loaded — check the connection and try again.");
|
|
276
276
|
return e && (n.cause = e), n;
|
|
@@ -282,20 +282,20 @@ function We(t) {
|
|
|
282
282
|
})), e);
|
|
283
283
|
}
|
|
284
284
|
const Ie = We(() => import("./bugcatch-panel.es.js").catch((t) => {
|
|
285
|
-
throw
|
|
286
|
-
})),
|
|
287
|
-
throw
|
|
288
|
-
})),
|
|
289
|
-
info:
|
|
285
|
+
throw qe("the report panel could not be loaded.", t);
|
|
286
|
+
})), X = We(() => import("./bugcatch-call.es.js").catch((t) => {
|
|
287
|
+
throw qe("the calling code could not be loaded.", t);
|
|
288
|
+
})), Dt = {
|
|
289
|
+
info: Xe,
|
|
290
290
|
success: Nt,
|
|
291
291
|
warning: Ut,
|
|
292
292
|
critical: ze
|
|
293
293
|
};
|
|
294
|
-
function
|
|
294
|
+
function Pt(t, { where: e, onDismiss: n }) {
|
|
295
295
|
const i = document.createElement("div");
|
|
296
296
|
i.className = `notice tone-${t.tone} at-${e}`, i.setAttribute("role", "status");
|
|
297
297
|
const r = document.createElement("span");
|
|
298
|
-
r.className = "notice-ico", r.setAttribute("aria-hidden", "true"), r.innerHTML =
|
|
298
|
+
r.className = "notice-ico", r.setAttribute("aria-hidden", "true"), r.innerHTML = Dt[t.tone] || Xe;
|
|
299
299
|
const o = document.createElement("div");
|
|
300
300
|
o.className = "notice-text";
|
|
301
301
|
const a = document.createElement("strong");
|
|
@@ -309,26 +309,26 @@ function Dt(t, { where: e, onDismiss: n }) {
|
|
|
309
309
|
}
|
|
310
310
|
if (i.append(r, o), t.dismissible && n) {
|
|
311
311
|
const s = document.createElement("button");
|
|
312
|
-
s.type = "button", s.className = "notice-x", s.setAttribute("aria-label", "Dismiss this notice"), s.innerHTML =
|
|
312
|
+
s.type = "button", s.className = "notice-x", s.setAttribute("aria-label", "Dismiss this notice"), s.innerHTML = Fe, s.addEventListener("click", () => n(t)), i.append(s);
|
|
313
313
|
}
|
|
314
314
|
return i;
|
|
315
315
|
}
|
|
316
|
-
const Je = "#0e0e10",
|
|
316
|
+
const Je = "#0e0e10", ce = "#ffffff";
|
|
317
317
|
function Ye(t) {
|
|
318
318
|
const e = _t(t);
|
|
319
|
-
if (!e) return
|
|
319
|
+
if (!e) return ce;
|
|
320
320
|
const [n, i, r] = e.map((a) => {
|
|
321
321
|
const s = a / 255;
|
|
322
322
|
return s <= 0.03928 ? s / 12.92 : ((s + 0.055) / 1.055) ** 2.4;
|
|
323
323
|
});
|
|
324
|
-
return 0.2126 * n + 0.7152 * i + 0.0722 * r > 0.179 ? Je :
|
|
324
|
+
return 0.2126 * n + 0.7152 * i + 0.0722 * r > 0.179 ? Je : ce;
|
|
325
325
|
}
|
|
326
326
|
function _t(t) {
|
|
327
327
|
const e = String(t || "").trim();
|
|
328
328
|
let n = /^#([0-9a-f]{3})$/i.exec(e);
|
|
329
329
|
return n ? [...n[1]].map((i) => parseInt(i + i, 16)) : (n = /^#([0-9a-f]{6})$/i.exec(e), n ? [0, 2, 4].map((i) => parseInt(n[1].slice(i, i + 2), 16)) : (n = /^rgba?\(\s*(\d+)[\s,]+(\d+)[\s,]+(\d+)/i.exec(e), n ? [n[1], n[2], n[3]].map(Number) : null));
|
|
330
330
|
}
|
|
331
|
-
const
|
|
331
|
+
const Se = {
|
|
332
332
|
"bottom-right": "bottom:20px;right:20px;",
|
|
333
333
|
"bottom-left": "bottom:20px;left:20px;",
|
|
334
334
|
"top-right": "top:20px;right:20px;",
|
|
@@ -352,7 +352,7 @@ function zt(t) {
|
|
|
352
352
|
} catch {
|
|
353
353
|
}
|
|
354
354
|
}
|
|
355
|
-
const
|
|
355
|
+
const Be = `
|
|
356
356
|
--bc-bg: #151517;
|
|
357
357
|
--bc-elevated: #1c1c1f;
|
|
358
358
|
--bc-fg: #f3f2ef;
|
|
@@ -370,7 +370,7 @@ const Se = `
|
|
|
370
370
|
--bc-brand-mark: #a59cff;
|
|
371
371
|
--bc-shadow: 0 0 0 1px rgba(255,255,255,.08), 0 30px 70px -20px rgba(0,0,0,.8), 0 8px 20px -8px rgba(0,0,0,.5);
|
|
372
372
|
--bc-shadow-sm: 0 0 0 1px rgba(255,255,255,.07), 0 1px 2px rgba(0,0,0,.4);
|
|
373
|
-
--bc-accent-soft: color-mix(in srgb, var(--bc-accent) 14%, var(--bc-bg));`,
|
|
373
|
+
--bc-accent-soft: color-mix(in srgb, var(--bc-accent) 14%, var(--bc-bg));`, Ft = (t) => `
|
|
374
374
|
:host { all: initial; }
|
|
375
375
|
:host {
|
|
376
376
|
--bc-accent: ${t || "var(--bc-fg)"};
|
|
@@ -422,10 +422,10 @@ const Se = `
|
|
|
422
422
|
--bc-fs-lg: 15px;
|
|
423
423
|
--bc-pad: 18px;
|
|
424
424
|
}
|
|
425
|
-
:host(.bc-dark) {${
|
|
425
|
+
:host(.bc-dark) {${Be}
|
|
426
426
|
}
|
|
427
427
|
@media (prefers-color-scheme: dark) {
|
|
428
|
-
:host(.bc-auto) {${
|
|
428
|
+
:host(.bc-auto) {${Be}
|
|
429
429
|
}
|
|
430
430
|
}
|
|
431
431
|
|
|
@@ -655,21 +655,21 @@ button:focus-visible, a:focus-visible, select:focus-visible, [tabindex]:focus-vi
|
|
|
655
655
|
.loadfail button[data-act="retry"] { text-decoration: underline; text-underline-offset: 2px; }
|
|
656
656
|
.loadfail button svg { font-size: 13px; margin: 0; }
|
|
657
657
|
`;
|
|
658
|
-
function
|
|
658
|
+
function Xt(t) {
|
|
659
659
|
const e = document.createElement("div");
|
|
660
660
|
e.setAttribute("data-bugcatch", "widget");
|
|
661
|
-
let n = Ht() ||
|
|
662
|
-
e.className =
|
|
661
|
+
let n = Ht() || qt(t.config.theme);
|
|
662
|
+
e.className = Ee(n);
|
|
663
663
|
const i = e.attachShadow({ mode: "open" }), r = document.createElement("style");
|
|
664
|
-
r.textContent =
|
|
665
|
-
const o =
|
|
666
|
-
a.className = `dock ${o.includes("right") ? "at-right" : "at-left"}` + (o.startsWith("top") ? " at-top" : ""), a.style.cssText =
|
|
664
|
+
r.textContent = Ft(t.config.accent || null), i.appendChild(r);
|
|
665
|
+
const o = Se[t.config.widgetPosition] ? t.config.widgetPosition : "bottom-right", a = document.createElement("div");
|
|
666
|
+
a.className = `dock ${o.includes("right") ? "at-right" : "at-left"}` + (o.startsWith("top") ? " at-top" : ""), a.style.cssText = Se[o];
|
|
667
667
|
const s = {
|
|
668
668
|
current: () => n,
|
|
669
|
-
label: () => P.find((
|
|
669
|
+
label: () => P.find((w) => w.value === n).label,
|
|
670
670
|
cycle() {
|
|
671
|
-
const
|
|
672
|
-
return n =
|
|
671
|
+
const w = P[(P.findIndex((C) => C.value === n) + 1) % P.length];
|
|
672
|
+
return n = w.value, e.className = Ee(n), zt(n), w;
|
|
673
673
|
}
|
|
674
674
|
}, c = document.createElement("button");
|
|
675
675
|
c.className = "launcher", c.type = "button", c.innerHTML = `<span class="ico" aria-hidden="true"><span class="when-closed"><span class="orb"></span></span><span class="when-open">${Mt}</span></span><span>Report a bug</span>`, c.setAttribute("aria-haspopup", "dialog"), c.setAttribute("aria-expanded", "false");
|
|
@@ -679,94 +679,106 @@ function Ft(t) {
|
|
|
679
679
|
l.close();
|
|
680
680
|
return;
|
|
681
681
|
}
|
|
682
|
-
l =
|
|
682
|
+
l = f();
|
|
683
683
|
});
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
let
|
|
684
|
+
let h = "report";
|
|
685
|
+
function f() {
|
|
686
|
+
let w = h;
|
|
687
|
+
h = "report", E(), k();
|
|
688
|
+
let C = null, m = !1;
|
|
687
689
|
const B = () => {
|
|
688
|
-
|
|
689
|
-
},
|
|
690
|
-
close: () =>
|
|
691
|
-
destroy: () =>
|
|
690
|
+
m = !0, c.removeAttribute("aria-busy"), l = null;
|
|
691
|
+
}, A = {
|
|
692
|
+
close: () => C ? C.close() : B(),
|
|
693
|
+
destroy: () => C ? C.destroy() : B(),
|
|
694
|
+
// Asked again while it is on its way, or once it is open.
|
|
695
|
+
setMode: (I) => {
|
|
696
|
+
var O;
|
|
697
|
+
C ? (O = C.setMode) == null || O.call(C, I) : w = I;
|
|
698
|
+
}
|
|
692
699
|
};
|
|
693
|
-
return c.setAttribute("aria-busy", "true"), Ie(t.config.chunkBase).then(({ openPanel:
|
|
694
|
-
|
|
700
|
+
return c.setAttribute("aria-busy", "true"), Ie(t.config.chunkBase).then(({ openPanel: I }) => {
|
|
701
|
+
m || (c.removeAttribute("aria-busy"), a.classList.add("over"), c.setAttribute("aria-expanded", "true"), C = I({
|
|
695
702
|
root: i,
|
|
696
703
|
host: e,
|
|
697
704
|
dock: a,
|
|
698
705
|
client: t,
|
|
699
|
-
preloadCall:
|
|
706
|
+
preloadCall: b,
|
|
700
707
|
themeControls: s,
|
|
708
|
+
mode: w,
|
|
701
709
|
onClose: () => {
|
|
702
710
|
l = null, a.classList.remove("over"), c.setAttribute("aria-expanded", "false");
|
|
703
711
|
}
|
|
704
712
|
}));
|
|
705
713
|
}, () => {
|
|
706
|
-
|
|
707
|
-
}),
|
|
714
|
+
m || (B(), S());
|
|
715
|
+
}), A;
|
|
708
716
|
}
|
|
709
|
-
const
|
|
717
|
+
const u = () => {
|
|
710
718
|
Ie(t.config.chunkBase).catch(() => {
|
|
711
719
|
});
|
|
712
720
|
};
|
|
713
|
-
for (const
|
|
714
|
-
c.addEventListener(
|
|
715
|
-
const d =
|
|
716
|
-
function
|
|
717
|
-
|
|
721
|
+
for (const w of ["pointerenter", "touchstart", "focus"])
|
|
722
|
+
c.addEventListener(w, u, { once: !0, passive: !0 });
|
|
723
|
+
const d = $e(u);
|
|
724
|
+
function b() {
|
|
725
|
+
X(t.config.chunkBase).catch(() => {
|
|
718
726
|
});
|
|
719
727
|
}
|
|
720
|
-
let
|
|
721
|
-
function
|
|
722
|
-
|
|
723
|
-
c.focus(), l || (l =
|
|
724
|
-
}),
|
|
725
|
-
c.focus(),
|
|
726
|
-
}), a.prepend(
|
|
728
|
+
let y = null;
|
|
729
|
+
function S() {
|
|
730
|
+
E(), y = document.createElement("div"), y.className = "msg err loadfail", y.setAttribute("role", "alert"), y.innerHTML = `${ze}<span>The report form didn't load. Check your connection and try again.</span><button type="button" data-act="retry">Try again</button><button type="button" data-act="dismiss" aria-label="Dismiss">${Fe}</button>`, y.querySelector('[data-act="retry"]').addEventListener("click", () => {
|
|
731
|
+
c.focus(), l || (l = f());
|
|
732
|
+
}), y.querySelector('[data-act="dismiss"]').addEventListener("click", () => {
|
|
733
|
+
c.focus(), E();
|
|
734
|
+
}), a.prepend(y);
|
|
727
735
|
}
|
|
728
|
-
function
|
|
729
|
-
|
|
736
|
+
function E() {
|
|
737
|
+
y == null || y.remove(), y = null;
|
|
730
738
|
}
|
|
731
|
-
let
|
|
732
|
-
function
|
|
733
|
-
|
|
739
|
+
let $ = null;
|
|
740
|
+
function g(w) {
|
|
741
|
+
k(), $ = Pt(w, {
|
|
734
742
|
where: "launcher",
|
|
735
|
-
onDismiss: (
|
|
736
|
-
t.dismissAnnouncement(
|
|
743
|
+
onDismiss: (C) => {
|
|
744
|
+
t.dismissAnnouncement(C), c.focus(), k();
|
|
737
745
|
}
|
|
738
|
-
}),
|
|
746
|
+
}), y ? y.after($) : a.prepend($);
|
|
739
747
|
}
|
|
740
|
-
function
|
|
741
|
-
|
|
748
|
+
function k() {
|
|
749
|
+
$ == null || $.remove(), $ = null;
|
|
742
750
|
}
|
|
743
|
-
const
|
|
744
|
-
} :
|
|
745
|
-
t.announcements().then((
|
|
746
|
-
const
|
|
747
|
-
|
|
751
|
+
const v = t.config.announcements === !1 ? () => {
|
|
752
|
+
} : $e(() => {
|
|
753
|
+
t.announcements().then((w) => {
|
|
754
|
+
const C = w.find((m) => m.placement === "launcher");
|
|
755
|
+
C && !l && e.isConnected && g(C);
|
|
748
756
|
}).catch(() => {
|
|
749
757
|
});
|
|
750
758
|
});
|
|
751
759
|
return a.append(c), i.appendChild(a), document.body.appendChild(e), t.widgetControls = {
|
|
752
|
-
open: () => {
|
|
753
|
-
|
|
760
|
+
open: (w) => {
|
|
761
|
+
if (l) {
|
|
762
|
+
w && l.setMode(w);
|
|
763
|
+
return;
|
|
764
|
+
}
|
|
765
|
+
h = w || "report", c.click();
|
|
754
766
|
},
|
|
755
767
|
close: () => {
|
|
756
768
|
l == null || l.close();
|
|
757
769
|
},
|
|
758
770
|
isOpen: () => !!l
|
|
759
771
|
}, () => {
|
|
760
|
-
d(),
|
|
772
|
+
d(), v(), l == null || l.destroy(), e.remove(), t.widgetControls = null;
|
|
761
773
|
};
|
|
762
774
|
}
|
|
763
|
-
function
|
|
775
|
+
function qt(t) {
|
|
764
776
|
return t === "dark" || t === "light" ? t : "auto";
|
|
765
777
|
}
|
|
766
|
-
function
|
|
778
|
+
function Ee(t) {
|
|
767
779
|
return t === "dark" ? "bc-dark" : t === "light" ? "bc-light" : "bc-auto";
|
|
768
780
|
}
|
|
769
|
-
function
|
|
781
|
+
function $e(t) {
|
|
770
782
|
let e = () => {
|
|
771
783
|
};
|
|
772
784
|
const n = () => {
|
|
@@ -781,7 +793,7 @@ function Ee(t) {
|
|
|
781
793
|
return document.readyState === "complete" ? n() : (window.addEventListener("load", n, { once: !0 }), e = () => window.removeEventListener("load", n)), () => e();
|
|
782
794
|
}
|
|
783
795
|
const Wt = "Too many requests are being sent from here at the moment. Please try again in a minute.";
|
|
784
|
-
function
|
|
796
|
+
function K(t) {
|
|
785
797
|
return t || Wt;
|
|
786
798
|
}
|
|
787
799
|
const Jt = typeof window < "u" && window.fetch ? window.fetch.bind(window) : null, Yt = typeof XMLHttpRequest < "u" ? XMLHttpRequest.prototype.open : null, Vt = typeof XMLHttpRequest < "u" ? XMLHttpRequest.prototype.send : null, Zt = [
|
|
@@ -805,27 +817,27 @@ const Jt = typeof window < "u" && window.fetch ? window.fetch.bind(window) : nul
|
|
|
805
817
|
"application/vnd.openxmlformats-officedocument.wordprocessingml.document",
|
|
806
818
|
"application/vnd.ms-excel",
|
|
807
819
|
"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"
|
|
808
|
-
],
|
|
820
|
+
], Te = [
|
|
809
821
|
"image/png",
|
|
810
822
|
"image/jpeg",
|
|
811
823
|
"image/webp",
|
|
812
824
|
"video/webm",
|
|
813
825
|
"video/mp4"
|
|
814
|
-
],
|
|
826
|
+
], bi = () => {
|
|
815
827
|
var t;
|
|
816
828
|
return !!((t = navigator == null ? void 0 : navigator.mediaDevices) != null && t.getUserMedia && typeof MediaRecorder < "u");
|
|
817
|
-
},
|
|
829
|
+
}, xi = () => {
|
|
818
830
|
var t;
|
|
819
831
|
return !!((t = navigator == null ? void 0 : navigator.mediaDevices) != null && t.getDisplayMedia && typeof MediaRecorder < "u");
|
|
820
|
-
},
|
|
832
|
+
}, ki = () => {
|
|
821
833
|
var t;
|
|
822
834
|
return !!((t = navigator == null ? void 0 : navigator.mediaDevices) != null && t.getDisplayMedia);
|
|
823
835
|
};
|
|
824
|
-
function
|
|
836
|
+
function le(t, e = Zt) {
|
|
825
837
|
const n = String(t || "").split(";")[0].trim().toLowerCase();
|
|
826
838
|
return e.includes(n) ? n : null;
|
|
827
839
|
}
|
|
828
|
-
async function
|
|
840
|
+
async function vi() {
|
|
829
841
|
const t = await navigator.mediaDevices.getDisplayMedia({
|
|
830
842
|
video: { frameRate: 1 },
|
|
831
843
|
audio: !1
|
|
@@ -842,57 +854,57 @@ async function mi() {
|
|
|
842
854
|
t.getTracks().forEach((e) => e.stop());
|
|
843
855
|
}
|
|
844
856
|
}
|
|
845
|
-
async function
|
|
857
|
+
async function Ci({ maxMs: t = 12e4, onTick: e, onAutoStop: n } = {}) {
|
|
846
858
|
const i = await navigator.mediaDevices.getDisplayMedia({
|
|
847
859
|
video: { frameRate: 15 },
|
|
848
860
|
audio: !1
|
|
849
|
-
}), r = ["video/webm;codecs=vp9", "video/webm;codecs=vp8", "video/webm"].find((
|
|
850
|
-
o.ondataavailable = (
|
|
851
|
-
|
|
861
|
+
}), r = ["video/webm;codecs=vp9", "video/webm;codecs=vp8", "video/webm"].find((d) => MediaRecorder.isTypeSupported(d)) || "video/webm", o = new MediaRecorder(i, { mimeType: r, videoBitsPerSecond: 25e5 }), a = [];
|
|
862
|
+
o.ondataavailable = (d) => {
|
|
863
|
+
d.data.size && a.push(d.data);
|
|
852
864
|
}, o.start(1e3);
|
|
853
865
|
const s = Date.now(), c = setInterval(() => e == null ? void 0 : e(Math.floor((Date.now() - s) / 1e3)), 500), l = () => {
|
|
854
|
-
clearInterval(c), clearTimeout(
|
|
855
|
-
}, h = new Promise((
|
|
866
|
+
clearInterval(c), clearTimeout(u), i.getTracks().forEach((d) => d.stop());
|
|
867
|
+
}, h = new Promise((d) => {
|
|
856
868
|
o.onstop = () => {
|
|
857
|
-
l(),
|
|
869
|
+
l(), d(new Blob(a, { type: r }));
|
|
858
870
|
};
|
|
859
871
|
}), f = () => {
|
|
860
872
|
o.state !== "inactive" && o.stop(), n == null || n();
|
|
861
873
|
};
|
|
862
874
|
i.getVideoTracks()[0].addEventListener("ended", f);
|
|
863
|
-
const
|
|
875
|
+
const u = setTimeout(f, t);
|
|
864
876
|
return {
|
|
865
877
|
mime: r,
|
|
866
878
|
maxMs: t,
|
|
867
879
|
async stop() {
|
|
868
|
-
return clearTimeout(
|
|
880
|
+
return clearTimeout(u), o.state !== "inactive" && o.stop(), { blob: await h, mime: r, kind: "VIDEO" };
|
|
869
881
|
},
|
|
870
882
|
cancel() {
|
|
871
883
|
l(), o.state !== "inactive" && o.stop();
|
|
872
884
|
}
|
|
873
885
|
};
|
|
874
886
|
}
|
|
875
|
-
async function
|
|
876
|
-
const i = await navigator.mediaDevices.getUserMedia({ audio: !0 }), r = ["audio/webm;codecs=opus", "audio/webm", "audio/mp4", "audio/ogg"].find((
|
|
877
|
-
o.ondataavailable = (
|
|
878
|
-
|
|
887
|
+
async function Ii({ maxMs: t = 12e4, onTick: e, onAutoStop: n } = {}) {
|
|
888
|
+
const i = await navigator.mediaDevices.getUserMedia({ audio: !0 }), r = ["audio/webm;codecs=opus", "audio/webm", "audio/mp4", "audio/ogg"].find((d) => MediaRecorder.isTypeSupported(d)) || "", o = new MediaRecorder(i, r ? { mimeType: r } : void 0), a = [];
|
|
889
|
+
o.ondataavailable = (d) => {
|
|
890
|
+
d.data.size && a.push(d.data);
|
|
879
891
|
}, o.start(1e3);
|
|
880
892
|
const s = Date.now(), c = setInterval(() => e == null ? void 0 : e(Math.floor((Date.now() - s) / 1e3)), 500), l = () => {
|
|
881
|
-
clearInterval(c), clearTimeout(
|
|
882
|
-
}, h = new Promise((
|
|
893
|
+
clearInterval(c), clearTimeout(u), i.getTracks().forEach((d) => d.stop());
|
|
894
|
+
}, h = new Promise((d) => {
|
|
883
895
|
o.onstop = () => {
|
|
884
|
-
l(),
|
|
896
|
+
l(), d(new Blob(a, { type: o.mimeType || r }));
|
|
885
897
|
};
|
|
886
|
-
}),
|
|
898
|
+
}), u = setTimeout(() => {
|
|
887
899
|
o.state !== "inactive" && o.stop(), n == null || n();
|
|
888
900
|
}, t);
|
|
889
901
|
return {
|
|
890
902
|
mime: o.mimeType || r,
|
|
891
903
|
maxMs: t,
|
|
892
904
|
async stop() {
|
|
893
|
-
clearTimeout(
|
|
894
|
-
const
|
|
895
|
-
return { blob:
|
|
905
|
+
clearTimeout(u), o.state !== "inactive" && o.stop();
|
|
906
|
+
const d = await h;
|
|
907
|
+
return { blob: d, mime: d.type || o.mimeType || r, kind: "AUDIO" };
|
|
896
908
|
},
|
|
897
909
|
cancel() {
|
|
898
910
|
l(), o.state !== "inactive" && o.stop();
|
|
@@ -901,7 +913,7 @@ async function yi({ maxMs: t = 12e4, onTick: e, onAutoStop: n } = {}) {
|
|
|
901
913
|
}
|
|
902
914
|
async function Gt({ apiBase: t, apiKey: e, blob: n, mime: i, onProgress: r }) {
|
|
903
915
|
var l;
|
|
904
|
-
const o =
|
|
916
|
+
const o = le(i || n.type);
|
|
905
917
|
if (!o)
|
|
906
918
|
throw new Error(`[BugCatch] ${i || n.type || "that file"} can't be attached.`);
|
|
907
919
|
const a = await Jt(`${t}/ingest/presign`, {
|
|
@@ -915,7 +927,7 @@ async function Gt({ apiBase: t, apiKey: e, blob: n, mime: i, onProgress: r }) {
|
|
|
915
927
|
h = ((l = await a.json()) == null ? void 0 : l.message) || "";
|
|
916
928
|
} catch {
|
|
917
929
|
}
|
|
918
|
-
throw new Error(`[BugCatch] ${
|
|
930
|
+
throw new Error(`[BugCatch] ${K(typeof h == "string" ? h : "")}`);
|
|
919
931
|
}
|
|
920
932
|
if (!a.ok) throw new Error(`[BugCatch] could not start the upload (HTTP ${a.status}).`);
|
|
921
933
|
const { key: s, uploadUrl: c } = await a.json();
|
|
@@ -933,80 +945,80 @@ function Qt(t, e, n, i) {
|
|
|
933
945
|
)), a.onabort = () => o(new Error("[BugCatch] upload cancelled.")), Vt.call(a, e);
|
|
934
946
|
});
|
|
935
947
|
}
|
|
936
|
-
function
|
|
948
|
+
function Si(t) {
|
|
937
949
|
return t < 1024 ? `${t} B` : t < 1024 * 1024 ? `${(t / 1024).toFixed(0)} KB` : `${(t / 1024 / 1024).toFixed(1)} MB`;
|
|
938
950
|
}
|
|
939
|
-
function
|
|
951
|
+
function Bi(t) {
|
|
940
952
|
const e = Math.floor(t / 60), n = t % 60;
|
|
941
953
|
return `${e}:${String(n).padStart(2, "0")}`;
|
|
942
954
|
}
|
|
943
|
-
const
|
|
944
|
-
let
|
|
955
|
+
const V = "bugcatch.watch", Ae = [2e3, 5e3, 15e3, 3e4, 6e4], en = 5e3;
|
|
956
|
+
let H = null;
|
|
945
957
|
function tn(t) {
|
|
946
|
-
|
|
958
|
+
H = t || null;
|
|
947
959
|
}
|
|
948
|
-
const
|
|
949
|
-
function
|
|
950
|
-
return
|
|
960
|
+
const ge = () => H ? `${V}:${H}` : V;
|
|
961
|
+
function te() {
|
|
962
|
+
return H ? `?projectId=${encodeURIComponent(H)}` : "";
|
|
951
963
|
}
|
|
952
|
-
function
|
|
964
|
+
function T() {
|
|
953
965
|
try {
|
|
954
966
|
const t = window.localStorage;
|
|
955
|
-
return (t == null ? void 0 : t.getItem(
|
|
967
|
+
return (t == null ? void 0 : t.getItem(ge())) || (t == null ? void 0 : t.getItem(V)) || null;
|
|
956
968
|
} catch {
|
|
957
969
|
return null;
|
|
958
970
|
}
|
|
959
971
|
}
|
|
960
|
-
function
|
|
972
|
+
function de(t) {
|
|
961
973
|
var e;
|
|
962
974
|
if (t)
|
|
963
975
|
try {
|
|
964
|
-
(e = window.localStorage) == null || e.setItem(
|
|
976
|
+
(e = window.localStorage) == null || e.setItem(ge(), t);
|
|
965
977
|
} catch {
|
|
966
978
|
}
|
|
967
979
|
}
|
|
968
|
-
function
|
|
980
|
+
function N() {
|
|
969
981
|
var t, e;
|
|
970
982
|
try {
|
|
971
|
-
(t = window.localStorage) == null || t.removeItem(
|
|
983
|
+
(t = window.localStorage) == null || t.removeItem(ge()), (e = window.localStorage) == null || e.removeItem(V);
|
|
972
984
|
} catch {
|
|
973
985
|
}
|
|
974
986
|
Ze();
|
|
975
987
|
}
|
|
976
|
-
const
|
|
988
|
+
const Z = "bugcatch.unread";
|
|
977
989
|
function nn(t) {
|
|
978
990
|
return [(t == null ? void 0 : t.bugId) || "report", (t == null ? void 0 : t.kind) || "status", (t == null ? void 0 : t.at) || ""].join("|");
|
|
979
991
|
}
|
|
980
|
-
function
|
|
992
|
+
function z() {
|
|
981
993
|
var t;
|
|
982
994
|
try {
|
|
983
|
-
const e = (t = window.localStorage) == null ? void 0 : t.getItem(
|
|
995
|
+
const e = (t = window.localStorage) == null ? void 0 : t.getItem(Z), n = e ? JSON.parse(e) : [];
|
|
984
996
|
return Array.isArray(n) ? n.filter((i) => i && typeof i.id == "string") : [];
|
|
985
997
|
} catch {
|
|
986
998
|
return [];
|
|
987
999
|
}
|
|
988
1000
|
}
|
|
989
|
-
function
|
|
1001
|
+
function ne(t) {
|
|
990
1002
|
var e, n;
|
|
991
1003
|
try {
|
|
992
|
-
t.length ? (e = window.localStorage) == null || e.setItem(
|
|
1004
|
+
t.length ? (e = window.localStorage) == null || e.setItem(Z, JSON.stringify(t)) : (n = window.localStorage) == null || n.removeItem(Z);
|
|
993
1005
|
} catch {
|
|
994
1006
|
}
|
|
995
1007
|
}
|
|
996
1008
|
function on(t) {
|
|
997
|
-
const e = { ...t, id: nn(t) }, n =
|
|
998
|
-
return n.push(e),
|
|
1009
|
+
const e = { ...t, id: nn(t) }, n = z().filter((i) => i.id !== e.id);
|
|
1010
|
+
return n.push(e), ne(n.slice(-20)), e;
|
|
999
1011
|
}
|
|
1000
1012
|
function rn(t) {
|
|
1001
|
-
const e =
|
|
1002
|
-
return
|
|
1013
|
+
const e = z().filter((n) => n.id !== t);
|
|
1014
|
+
return ne(e), e;
|
|
1003
1015
|
}
|
|
1004
1016
|
function an(t) {
|
|
1005
|
-
const e =
|
|
1006
|
-
return
|
|
1017
|
+
const e = z().filter((n) => n.bugId !== t);
|
|
1018
|
+
return ne(e), e;
|
|
1007
1019
|
}
|
|
1008
1020
|
function Ze() {
|
|
1009
|
-
return
|
|
1021
|
+
return ne([]), [];
|
|
1010
1022
|
}
|
|
1011
1023
|
function sn(t, e) {
|
|
1012
1024
|
let n = t, i = n.indexOf(`
|
|
@@ -1030,30 +1042,30 @@ function sn(t, e) {
|
|
|
1030
1042
|
return n;
|
|
1031
1043
|
}
|
|
1032
1044
|
async function cn({ apiBase: t }) {
|
|
1033
|
-
const e =
|
|
1045
|
+
const e = T();
|
|
1034
1046
|
if (!e) return { reporter: null, reports: [] };
|
|
1035
|
-
const n = await fetch(`${t}/ingest/watch/reports${
|
|
1047
|
+
const n = await fetch(`${t}/ingest/watch/reports${te()}`, {
|
|
1036
1048
|
headers: { Authorization: `Bearer ${e}` }
|
|
1037
1049
|
});
|
|
1038
1050
|
if (n.status === 401)
|
|
1039
|
-
return
|
|
1051
|
+
return N(), { reporter: null, reports: [] };
|
|
1040
1052
|
if (!n.ok) throw new Error(`[BugCatch] could not load your reports (HTTP ${n.status})`);
|
|
1041
1053
|
return n.json();
|
|
1042
1054
|
}
|
|
1043
1055
|
async function ln({ apiBase: t, bugId: e }) {
|
|
1044
|
-
const n =
|
|
1056
|
+
const n = T();
|
|
1045
1057
|
if (!n) return null;
|
|
1046
|
-
const i = await fetch(`${t}/ingest/watch/reports/${encodeURIComponent(e)}${
|
|
1058
|
+
const i = await fetch(`${t}/ingest/watch/reports/${encodeURIComponent(e)}${te()}`, {
|
|
1047
1059
|
headers: { Authorization: `Bearer ${n}` }
|
|
1048
1060
|
});
|
|
1049
1061
|
if (i.status === 401)
|
|
1050
|
-
return
|
|
1062
|
+
return N(), null;
|
|
1051
1063
|
if (i.status === 404) return null;
|
|
1052
1064
|
if (!i.ok) throw new Error(`[BugCatch] could not load that report (HTTP ${i.status})`);
|
|
1053
1065
|
return i.json();
|
|
1054
1066
|
}
|
|
1055
|
-
async function
|
|
1056
|
-
const r =
|
|
1067
|
+
async function dn({ apiBase: t, bugId: e, body: n, attachments: i }) {
|
|
1068
|
+
const r = T();
|
|
1057
1069
|
if (!r) throw new Error("[BugCatch] nothing filed from this browser yet.");
|
|
1058
1070
|
const o = await fetch(
|
|
1059
1071
|
`${t}/ingest/watch/reports/${encodeURIComponent(e)}/messages`,
|
|
@@ -1067,7 +1079,7 @@ async function un({ apiBase: t, bugId: e, body: n, attachments: i }) {
|
|
|
1067
1079
|
}
|
|
1068
1080
|
);
|
|
1069
1081
|
if (o.status === 401)
|
|
1070
|
-
throw
|
|
1082
|
+
throw N(), new Error("[BugCatch] this browser can no longer prove it filed that report.");
|
|
1071
1083
|
if (!o.ok) {
|
|
1072
1084
|
let a = "";
|
|
1073
1085
|
try {
|
|
@@ -1075,11 +1087,11 @@ async function un({ apiBase: t, bugId: e, body: n, attachments: i }) {
|
|
|
1075
1087
|
a = Array.isArray(s.message) ? s.message.join(", ") : s.message || "";
|
|
1076
1088
|
} catch {
|
|
1077
1089
|
}
|
|
1078
|
-
throw o.status === 429 ? new Error(
|
|
1090
|
+
throw o.status === 429 ? new Error(K(a)) : new Error(a || `[BugCatch] could not send that (HTTP ${o.status}).`);
|
|
1079
1091
|
}
|
|
1080
1092
|
return o.json();
|
|
1081
1093
|
}
|
|
1082
|
-
async function
|
|
1094
|
+
async function un({ apiBase: t, apiKey: e, projectId: n }) {
|
|
1083
1095
|
const i = { agent: !1, live: !1 };
|
|
1084
1096
|
try {
|
|
1085
1097
|
const r = await fetch(
|
|
@@ -1117,14 +1129,14 @@ async function hn({ apiBase: t, apiKey: e, token: n, payload: i, watchToken: r }
|
|
|
1117
1129
|
} catch {
|
|
1118
1130
|
}
|
|
1119
1131
|
const s = new Error(
|
|
1120
|
-
o.status === 429 ?
|
|
1132
|
+
o.status === 429 ? K(a) : a || `[BugCatch] the call could not be started (HTTP ${o.status}).`
|
|
1121
1133
|
);
|
|
1122
1134
|
throw s.status = o.status, s;
|
|
1123
1135
|
}
|
|
1124
1136
|
return o.json();
|
|
1125
1137
|
}
|
|
1126
|
-
async function
|
|
1127
|
-
const n =
|
|
1138
|
+
async function je({ apiBase: t, bugId: e }) {
|
|
1139
|
+
const n = T();
|
|
1128
1140
|
if (!n) return !1;
|
|
1129
1141
|
try {
|
|
1130
1142
|
const i = await fetch(
|
|
@@ -1139,14 +1151,14 @@ async function Ae({ apiBase: t, bugId: e }) {
|
|
|
1139
1151
|
}
|
|
1140
1152
|
}
|
|
1141
1153
|
async function fn({ apiBase: t, bugId: e }) {
|
|
1142
|
-
const n =
|
|
1154
|
+
const n = T();
|
|
1143
1155
|
if (!n) throw new Error("[BugCatch] nothing filed from this browser yet.");
|
|
1144
1156
|
const i = await fetch(
|
|
1145
1157
|
`${t}/ingest/watch/reports/${encodeURIComponent(e)}/live-call`,
|
|
1146
1158
|
{ method: "POST", headers: { Authorization: `Bearer ${n}` } }
|
|
1147
1159
|
);
|
|
1148
1160
|
if (i.status === 401)
|
|
1149
|
-
throw
|
|
1161
|
+
throw N(), new Error("[BugCatch] this browser can no longer prove it filed that report.");
|
|
1150
1162
|
if (!i.ok) {
|
|
1151
1163
|
let r = "";
|
|
1152
1164
|
try {
|
|
@@ -1159,7 +1171,7 @@ async function fn({ apiBase: t, bugId: e }) {
|
|
|
1159
1171
|
return i.json();
|
|
1160
1172
|
}
|
|
1161
1173
|
async function pn({ apiBase: t, bugId: e, callId: n }) {
|
|
1162
|
-
const i =
|
|
1174
|
+
const i = T();
|
|
1163
1175
|
if (i)
|
|
1164
1176
|
try {
|
|
1165
1177
|
await fetch(
|
|
@@ -1170,14 +1182,14 @@ async function pn({ apiBase: t, bugId: e, callId: n }) {
|
|
|
1170
1182
|
}
|
|
1171
1183
|
}
|
|
1172
1184
|
async function gn({ apiBase: t, bugId: e, callId: n }) {
|
|
1173
|
-
const i =
|
|
1185
|
+
const i = T();
|
|
1174
1186
|
if (!i) throw new Error("[BugCatch] nothing filed from this browser yet.");
|
|
1175
1187
|
const r = await fetch(
|
|
1176
1188
|
`${t}/ingest/watch/reports/${encodeURIComponent(e)}/live-call/${encodeURIComponent(n)}/answer`,
|
|
1177
1189
|
{ method: "POST", headers: { Authorization: `Bearer ${i}` } }
|
|
1178
1190
|
);
|
|
1179
1191
|
if (r.status === 401)
|
|
1180
|
-
throw
|
|
1192
|
+
throw N(), new Error("[BugCatch] this browser can no longer prove it filed that report.");
|
|
1181
1193
|
if (r.status === 409)
|
|
1182
1194
|
throw new Error("[BugCatch] that call is no longer ringing.");
|
|
1183
1195
|
if (!r.ok) {
|
|
@@ -1191,8 +1203,8 @@ async function gn({ apiBase: t, bugId: e, callId: n }) {
|
|
|
1191
1203
|
}
|
|
1192
1204
|
return r.json();
|
|
1193
1205
|
}
|
|
1194
|
-
async function
|
|
1195
|
-
const i =
|
|
1206
|
+
async function Oe({ apiBase: t, bugId: e, callId: n }) {
|
|
1207
|
+
const i = T();
|
|
1196
1208
|
if (i)
|
|
1197
1209
|
try {
|
|
1198
1210
|
await fetch(
|
|
@@ -1205,26 +1217,26 @@ async function je({ apiBase: t, bugId: e, callId: n }) {
|
|
|
1205
1217
|
function mn({ apiBase: t, onUpdate: e }) {
|
|
1206
1218
|
let n = !0, i = 0, r = null;
|
|
1207
1219
|
async function o() {
|
|
1208
|
-
const a =
|
|
1220
|
+
const a = T();
|
|
1209
1221
|
if (!a) throw new Error("nothing filed from this browser yet");
|
|
1210
1222
|
r = new AbortController();
|
|
1211
|
-
const s = await fetch(`${t}/ingest/watch/stream${
|
|
1223
|
+
const s = await fetch(`${t}/ingest/watch/stream${te()}`, {
|
|
1212
1224
|
headers: { Authorization: `Bearer ${a}`, Accept: "text/event-stream" },
|
|
1213
1225
|
signal: r.signal
|
|
1214
1226
|
});
|
|
1215
1227
|
if (s.status === 401)
|
|
1216
|
-
throw n = !1,
|
|
1228
|
+
throw n = !1, N(), new Error("subscription no longer valid");
|
|
1217
1229
|
if (!s.ok || !s.body) throw new Error(`stream failed (${s.status})`);
|
|
1218
1230
|
const c = Date.now(), l = s.body.getReader(), h = new TextDecoder();
|
|
1219
1231
|
let f = "";
|
|
1220
1232
|
try {
|
|
1221
1233
|
for (; ; ) {
|
|
1222
|
-
const { value:
|
|
1223
|
-
if (
|
|
1224
|
-
f += h.decode(
|
|
1225
|
-
if (
|
|
1234
|
+
const { value: u, done: d } = await l.read();
|
|
1235
|
+
if (d) break;
|
|
1236
|
+
f += h.decode(u, { stream: !0 }), f = sn(f, (b) => {
|
|
1237
|
+
if (b.type !== "ping")
|
|
1226
1238
|
try {
|
|
1227
|
-
e(
|
|
1239
|
+
e(b);
|
|
1228
1240
|
} catch {
|
|
1229
1241
|
}
|
|
1230
1242
|
});
|
|
@@ -1241,7 +1253,7 @@ function mn({ apiBase: t, onUpdate: e }) {
|
|
|
1241
1253
|
if ((s == null ? void 0 : s.name) === "AbortError") return;
|
|
1242
1254
|
}
|
|
1243
1255
|
if (!n) return;
|
|
1244
|
-
const a =
|
|
1256
|
+
const a = Ae[Math.min(i, Ae.length - 1)];
|
|
1245
1257
|
i += 1, await new Promise((s) => setTimeout(s, a));
|
|
1246
1258
|
}
|
|
1247
1259
|
})(), () => {
|
|
@@ -1267,7 +1279,7 @@ const wn = {
|
|
|
1267
1279
|
ring: "rgba(255,255,255,.09)",
|
|
1268
1280
|
brand: "#a59cff"
|
|
1269
1281
|
};
|
|
1270
|
-
function
|
|
1282
|
+
function Me(t) {
|
|
1271
1283
|
return t != null && t.summary ? t.summary : `Your report ${wn[t == null ? void 0 : t.status] || "was updated"}`;
|
|
1272
1284
|
}
|
|
1273
1285
|
function bn(t) {
|
|
@@ -1303,7 +1315,7 @@ function vn({
|
|
|
1303
1315
|
} = {}) {
|
|
1304
1316
|
const [o, a] = String(e).split("-"), s = o === "top", c = a === "left", l = /* @__PURE__ */ new Map();
|
|
1305
1317
|
let h = null, f = null;
|
|
1306
|
-
function
|
|
1318
|
+
function u() {
|
|
1307
1319
|
return h != null && h.isConnected || (h = document.createElement("div"), h.setAttribute("data-bugcatch", "updates"), h.style.cssText = [
|
|
1308
1320
|
"position:fixed",
|
|
1309
1321
|
`${s ? "top" : "bottom"}:${20 + kn()}px`,
|
|
@@ -1321,30 +1333,30 @@ function vn({
|
|
|
1321
1333
|
"pointer-events:none"
|
|
1322
1334
|
].join(";"), document.body.appendChild(h)), h;
|
|
1323
1335
|
}
|
|
1324
|
-
function
|
|
1325
|
-
if (!
|
|
1326
|
-
|
|
1336
|
+
function d(g) {
|
|
1337
|
+
if (!g._bcShown) {
|
|
1338
|
+
g.remove();
|
|
1327
1339
|
return;
|
|
1328
1340
|
}
|
|
1329
|
-
|
|
1341
|
+
g.style.opacity = "0", g.style.transform = `translateY(${s ? -8 : 8}px)`, setTimeout(() => g.remove(), 250);
|
|
1330
1342
|
}
|
|
1331
|
-
const
|
|
1332
|
-
function
|
|
1333
|
-
const
|
|
1334
|
-
return
|
|
1343
|
+
const b = t || ce, y = t ? Ye(t) : Je;
|
|
1344
|
+
function S(g, k) {
|
|
1345
|
+
const v = document.createElement("button");
|
|
1346
|
+
return v.type = "button", v.textContent = g, v.style.cssText = [
|
|
1335
1347
|
"padding:6px 12px",
|
|
1336
1348
|
"border:0",
|
|
1337
1349
|
`box-shadow:${k ? "none" : `inset 0 0 0 1px ${j.ring}`}`,
|
|
1338
1350
|
"border-radius:999px",
|
|
1339
|
-
`background:${k ?
|
|
1340
|
-
`color:${k ?
|
|
1351
|
+
`background:${k ? b : "rgba(255,255,255,.06)"}`,
|
|
1352
|
+
`color:${k ? y : j.fg}`,
|
|
1341
1353
|
"font:560 12px/1.4 inherit",
|
|
1342
1354
|
"cursor:pointer",
|
|
1343
1355
|
"white-space:nowrap"
|
|
1344
|
-
].join(";"),
|
|
1356
|
+
].join(";"), v;
|
|
1345
1357
|
}
|
|
1346
|
-
function
|
|
1347
|
-
var
|
|
1358
|
+
function E(g) {
|
|
1359
|
+
var O;
|
|
1348
1360
|
const k = document.createElement("div");
|
|
1349
1361
|
k.setAttribute("role", "status"), k.style.cssText = [
|
|
1350
1362
|
"box-sizing:border-box",
|
|
@@ -1360,26 +1372,26 @@ function vn({
|
|
|
1360
1372
|
"transition:opacity .2s ease,transform .2s ease",
|
|
1361
1373
|
"pointer-events:auto"
|
|
1362
1374
|
].join(";");
|
|
1363
|
-
const
|
|
1364
|
-
|
|
1365
|
-
const
|
|
1366
|
-
|
|
1367
|
-
const
|
|
1368
|
-
|
|
1369
|
-
const
|
|
1370
|
-
|
|
1371
|
-
const
|
|
1372
|
-
|
|
1375
|
+
const v = document.createElement("div");
|
|
1376
|
+
v.style.cssText = "display:flex;align-items:baseline;gap:8px;font-weight:600;margin-bottom:2px";
|
|
1377
|
+
const w = document.createElement("span");
|
|
1378
|
+
w.setAttribute("aria-hidden", "true"), w.style.cssText = `flex:none;width:7px;height:7px;border-radius:50%;transform:translateY(-1px);background:${yn[g == null ? void 0 : g.kind] || t || j.brand}`;
|
|
1379
|
+
const C = document.createElement("span");
|
|
1380
|
+
C.textContent = Me(g), v.append(w, C);
|
|
1381
|
+
const m = document.createElement("div");
|
|
1382
|
+
m.style.cssText = (g == null ? void 0 : g.kind) === "reply" ? `color:${j.muted};padding-left:15px;display:-webkit-box;-webkit-line-clamp:3;-webkit-box-orient:vertical;overflow:hidden` : `color:${j.muted};padding-left:15px`, m.textContent = bn(g);
|
|
1383
|
+
const B = document.createElement("div");
|
|
1384
|
+
B.style.cssText = "display:flex;align-items:center;gap:8px;margin-top:10px;padding-left:15px;flex-wrap:wrap";
|
|
1373
1385
|
const A = document.createElement("span");
|
|
1374
|
-
A.style.cssText = `color:${j.faint};font-size:11px;margin-right:auto`, A.textContent = xn(
|
|
1375
|
-
const
|
|
1376
|
-
if (
|
|
1377
|
-
const
|
|
1378
|
-
|
|
1386
|
+
A.style.cssText = `color:${j.faint};font-size:11px;margin-right:auto`, A.textContent = xn(g == null ? void 0 : g.at);
|
|
1387
|
+
const I = S("Mark as read", !1);
|
|
1388
|
+
if (I.setAttribute("aria-label", `Mark as read: ${Me(g)}`), I.addEventListener("click", () => n == null ? void 0 : n(g.id)), B.append(A, I), (O = g == null ? void 0 : g.call) != null && O.offered && typeof r == "function") {
|
|
1389
|
+
const xe = S("Talk it through", !0);
|
|
1390
|
+
xe.addEventListener("click", () => r(g)), B.insertBefore(xe, I);
|
|
1379
1391
|
}
|
|
1380
|
-
return k.append(
|
|
1392
|
+
return k.append(v, m, B), k;
|
|
1381
1393
|
}
|
|
1382
|
-
function
|
|
1394
|
+
function $(g) {
|
|
1383
1395
|
const k = document.createElement("div");
|
|
1384
1396
|
k.style.cssText = [
|
|
1385
1397
|
"box-sizing:border-box",
|
|
@@ -1395,10 +1407,10 @@ function vn({
|
|
|
1395
1407
|
`box-shadow:0 0 0 1px ${j.ring},0 12px 30px -10px rgba(0,0,0,.5)`,
|
|
1396
1408
|
"pointer-events:auto"
|
|
1397
1409
|
].join(";");
|
|
1398
|
-
const
|
|
1399
|
-
|
|
1400
|
-
const
|
|
1401
|
-
return
|
|
1410
|
+
const v = document.createElement("span");
|
|
1411
|
+
v.style.cssText = "margin-right:auto", v.textContent = `${g} more update${g === 1 ? "" : "s"}`;
|
|
1412
|
+
const w = S("Mark all as read", !1);
|
|
1413
|
+
return w.style.cssText += ";padding:4px 9px", w.addEventListener("click", () => i == null ? void 0 : i()), k.append(v, w), k;
|
|
1402
1414
|
}
|
|
1403
1415
|
return {
|
|
1404
1416
|
/**
|
|
@@ -1408,28 +1420,28 @@ function vn({
|
|
|
1408
1420
|
* corner the reporter's eye is already trained on — so the stack grows away
|
|
1409
1421
|
* from the launcher rather than over it.
|
|
1410
1422
|
*/
|
|
1411
|
-
render(
|
|
1412
|
-
const k = Array.isArray(
|
|
1423
|
+
render(g) {
|
|
1424
|
+
const k = Array.isArray(g) ? g : [];
|
|
1413
1425
|
if (!k.length) {
|
|
1414
|
-
for (const
|
|
1426
|
+
for (const I of l.values()) d(I);
|
|
1415
1427
|
l.clear(), f == null || f.remove(), f = null, h == null || h.remove(), h = null;
|
|
1416
1428
|
return;
|
|
1417
1429
|
}
|
|
1418
|
-
const
|
|
1419
|
-
for (const [
|
|
1420
|
-
|
|
1421
|
-
const
|
|
1422
|
-
for (const
|
|
1423
|
-
if (l.has(
|
|
1424
|
-
const
|
|
1425
|
-
l.set(
|
|
1430
|
+
const v = k.slice(-3), w = new Set(v.map((I) => I.id)), C = u();
|
|
1431
|
+
for (const [I, O] of l)
|
|
1432
|
+
w.has(I) || (d(O), l.delete(I));
|
|
1433
|
+
const m = [];
|
|
1434
|
+
for (const I of v) {
|
|
1435
|
+
if (l.has(I.id)) continue;
|
|
1436
|
+
const O = E(I);
|
|
1437
|
+
l.set(I.id, O), m.push(O);
|
|
1426
1438
|
}
|
|
1427
|
-
const
|
|
1428
|
-
for (const
|
|
1429
|
-
const A = k.length -
|
|
1430
|
-
A > 0 ? (f == null || f.remove(), f =
|
|
1431
|
-
for (const
|
|
1432
|
-
|
|
1439
|
+
const B = s ? [...v].reverse() : v;
|
|
1440
|
+
for (const I of B) C.appendChild(l.get(I.id));
|
|
1441
|
+
const A = k.length - v.length;
|
|
1442
|
+
A > 0 ? (f == null || f.remove(), f = $(A), s ? C.appendChild(f) : C.insertBefore(f, C.firstChild)) : (f == null || f.remove(), f = null), requestAnimationFrame(() => {
|
|
1443
|
+
for (const I of m)
|
|
1444
|
+
I.isConnected && (I._bcShown = !0, I.style.opacity = "1", I.style.transform = "translateY(0)");
|
|
1433
1445
|
});
|
|
1434
1446
|
},
|
|
1435
1447
|
destroy() {
|
|
@@ -1437,11 +1449,11 @@ function vn({
|
|
|
1437
1449
|
}
|
|
1438
1450
|
};
|
|
1439
1451
|
}
|
|
1440
|
-
async function
|
|
1452
|
+
async function Cn({ apiBase: t, apiKey: e, projectId: n, sessionToken: i }) {
|
|
1441
1453
|
try {
|
|
1442
1454
|
const r = await fetch(
|
|
1443
1455
|
`${t}/ingest/known-issues?projectId=${encodeURIComponent(n)}`,
|
|
1444
|
-
{ headers:
|
|
1456
|
+
{ headers: me(e, i) }
|
|
1445
1457
|
);
|
|
1446
1458
|
if (!r.ok) return [];
|
|
1447
1459
|
const o = await r.json();
|
|
@@ -1450,9 +1462,9 @@ async function In({ apiBase: t, apiKey: e, projectId: n, sessionToken: i }) {
|
|
|
1450
1462
|
return [];
|
|
1451
1463
|
}
|
|
1452
1464
|
}
|
|
1453
|
-
async function
|
|
1465
|
+
async function In({ apiBase: t, apiKey: e, projectId: n, q: i, sessionToken: r, signal: o }) {
|
|
1454
1466
|
try {
|
|
1455
|
-
const a = `${t}/ingest/known-issues/match?projectId=${encodeURIComponent(n)}&q=${encodeURIComponent(i)}`, s = await fetch(a, { headers:
|
|
1467
|
+
const a = `${t}/ingest/known-issues/match?projectId=${encodeURIComponent(n)}&q=${encodeURIComponent(i)}`, s = await fetch(a, { headers: me(e, r), signal: o });
|
|
1456
1468
|
if (!s.ok) return [];
|
|
1457
1469
|
const c = await s.json();
|
|
1458
1470
|
return Array.isArray(c == null ? void 0 : c.issues) ? c.issues : [];
|
|
@@ -1471,11 +1483,11 @@ async function Sn({
|
|
|
1471
1483
|
logs: s,
|
|
1472
1484
|
sessionToken: c
|
|
1473
1485
|
}) {
|
|
1474
|
-
const l =
|
|
1486
|
+
const l = T(), h = await fetch(
|
|
1475
1487
|
`${t}/ingest/known-issues/${encodeURIComponent(i)}/join`,
|
|
1476
1488
|
{
|
|
1477
1489
|
method: "POST",
|
|
1478
|
-
headers:
|
|
1490
|
+
headers: me(e, c),
|
|
1479
1491
|
body: JSON.stringify({
|
|
1480
1492
|
projectId: n,
|
|
1481
1493
|
reporterEmail: r,
|
|
@@ -1488,9 +1500,9 @@ async function Sn({
|
|
|
1488
1500
|
);
|
|
1489
1501
|
if (!h.ok) throw new Error(await Bn(h));
|
|
1490
1502
|
const f = await h.json();
|
|
1491
|
-
return f != null && f.watchToken &&
|
|
1503
|
+
return f != null && f.watchToken && de(f.watchToken), f;
|
|
1492
1504
|
}
|
|
1493
|
-
function
|
|
1505
|
+
function me(t, e) {
|
|
1494
1506
|
return {
|
|
1495
1507
|
"Content-Type": "application/json",
|
|
1496
1508
|
"X-BugCatch-Key": t,
|
|
@@ -1504,12 +1516,12 @@ async function Bn(t) {
|
|
|
1504
1516
|
e = Array.isArray(n.message) ? n.message.join(", ") : n.message || "";
|
|
1505
1517
|
} catch {
|
|
1506
1518
|
}
|
|
1507
|
-
return t.status === 429 ?
|
|
1519
|
+
return t.status === 429 ? K(e) : e || `Could not add you to this issue (HTTP ${t.status})`;
|
|
1508
1520
|
}
|
|
1509
1521
|
async function En({ apiBase: t, bugId: e, score: n, comment: i }) {
|
|
1510
|
-
const r =
|
|
1522
|
+
const r = T();
|
|
1511
1523
|
if (!r) throw new Error("This browser cannot access that report.");
|
|
1512
|
-
const o = await fetch(`${t}/ingest/watch/reports/${encodeURIComponent(e)}/rating${
|
|
1524
|
+
const o = await fetch(`${t}/ingest/watch/reports/${encodeURIComponent(e)}/rating${te()}`, {
|
|
1513
1525
|
method: "POST",
|
|
1514
1526
|
headers: { "Content-Type": "application/json", Authorization: `Bearer ${r}` },
|
|
1515
1527
|
body: JSON.stringify({ score: n, ...i ? { comment: i } : {} })
|
|
@@ -1521,7 +1533,7 @@ async function En({ apiBase: t, bugId: e, score: n, comment: i }) {
|
|
|
1521
1533
|
return a;
|
|
1522
1534
|
}
|
|
1523
1535
|
async function $n({ apiBase: t, bugId: e, ...n }) {
|
|
1524
|
-
const i =
|
|
1536
|
+
const i = T();
|
|
1525
1537
|
if (!i) throw new Error("This browser cannot access that report.");
|
|
1526
1538
|
const r = await fetch(`${t}/ingest/watch/reports/${encodeURIComponent(e)}/verification`, {
|
|
1527
1539
|
method: "POST",
|
|
@@ -1531,19 +1543,19 @@ async function $n({ apiBase: t, bugId: e, ...n }) {
|
|
|
1531
1543
|
if (!r.ok) throw new Error(o.message || "Could not record feedback. Please refresh and try again.");
|
|
1532
1544
|
return o;
|
|
1533
1545
|
}
|
|
1534
|
-
const Tn = "bugcatch.session.",
|
|
1546
|
+
const Tn = "bugcatch.session.", we = (t) => `${Tn}${t}`, ye = /* @__PURE__ */ new Map();
|
|
1535
1547
|
function M(t) {
|
|
1536
1548
|
var e;
|
|
1537
1549
|
if (!t) return null;
|
|
1538
1550
|
try {
|
|
1539
|
-
const n = (e = window.localStorage) == null ? void 0 : e.getItem(
|
|
1551
|
+
const n = (e = window.localStorage) == null ? void 0 : e.getItem(we(t));
|
|
1540
1552
|
if (n) {
|
|
1541
1553
|
const i = JSON.parse(n);
|
|
1542
1554
|
if (i != null && i.token) return i;
|
|
1543
1555
|
}
|
|
1544
1556
|
} catch {
|
|
1545
1557
|
}
|
|
1546
|
-
return
|
|
1558
|
+
return ye.get(t) || null;
|
|
1547
1559
|
}
|
|
1548
1560
|
function An(t, e) {
|
|
1549
1561
|
var i;
|
|
@@ -1553,23 +1565,23 @@ function An(t, e) {
|
|
|
1553
1565
|
email: e.email || null,
|
|
1554
1566
|
name: e.name || null
|
|
1555
1567
|
};
|
|
1556
|
-
|
|
1568
|
+
ye.set(t, n);
|
|
1557
1569
|
try {
|
|
1558
|
-
(i = window.localStorage) == null || i.setItem(
|
|
1570
|
+
(i = window.localStorage) == null || i.setItem(we(t), JSON.stringify(n));
|
|
1559
1571
|
} catch {
|
|
1560
1572
|
}
|
|
1561
1573
|
}
|
|
1562
|
-
function
|
|
1574
|
+
function ue(t) {
|
|
1563
1575
|
var e;
|
|
1564
1576
|
if (t) {
|
|
1565
|
-
|
|
1577
|
+
ye.delete(t);
|
|
1566
1578
|
try {
|
|
1567
|
-
(e = window.localStorage) == null || e.removeItem(
|
|
1579
|
+
(e = window.localStorage) == null || e.removeItem(we(t));
|
|
1568
1580
|
} catch {
|
|
1569
1581
|
}
|
|
1570
1582
|
}
|
|
1571
1583
|
}
|
|
1572
|
-
function
|
|
1584
|
+
function ie({ apiKey: t, token: e }) {
|
|
1573
1585
|
return {
|
|
1574
1586
|
"Content-Type": "application/json",
|
|
1575
1587
|
"X-BugCatch-Key": t,
|
|
@@ -1586,14 +1598,14 @@ async function Ge(t) {
|
|
|
1586
1598
|
e = Array.isArray(n.message) ? n.message.join(", ") : n.message || "";
|
|
1587
1599
|
} catch {
|
|
1588
1600
|
}
|
|
1589
|
-
return t.status === 429 ?
|
|
1601
|
+
return t.status === 429 ? K(e) : e || `Request failed (HTTP ${t.status})`;
|
|
1590
1602
|
}
|
|
1591
1603
|
async function jn({ apiBase: t, apiKey: e, projectId: n, token: i }) {
|
|
1592
1604
|
const r = { mode: "off", signedIn: null, signedOutReason: null };
|
|
1593
1605
|
try {
|
|
1594
1606
|
const o = await fetch(
|
|
1595
1607
|
`${t}/ingest/login?projectId=${encodeURIComponent(n)}`,
|
|
1596
|
-
{ headers:
|
|
1608
|
+
{ headers: ie({ apiKey: e, token: i }) }
|
|
1597
1609
|
);
|
|
1598
1610
|
if (!o.ok) return r;
|
|
1599
1611
|
const a = await o.json();
|
|
@@ -1609,7 +1621,7 @@ async function jn({ apiBase: t, apiKey: e, projectId: n, token: i }) {
|
|
|
1609
1621
|
async function On({ apiBase: t, apiKey: e, projectId: n, email: i, name: r }) {
|
|
1610
1622
|
const o = await fetch(`${t}/ingest/login/start`, {
|
|
1611
1623
|
method: "POST",
|
|
1612
|
-
headers:
|
|
1624
|
+
headers: ie({ apiKey: e }),
|
|
1613
1625
|
body: JSON.stringify({ projectId: n, email: i, ...r ? { name: r } : {} })
|
|
1614
1626
|
});
|
|
1615
1627
|
if (!o.ok) throw new Error(await Ge(o));
|
|
@@ -1618,7 +1630,7 @@ async function On({ apiBase: t, apiKey: e, projectId: n, email: i, name: r }) {
|
|
|
1618
1630
|
async function Mn({ apiBase: t, apiKey: e, projectId: n, email: i, code: r }) {
|
|
1619
1631
|
const o = await fetch(`${t}/ingest/login`, {
|
|
1620
1632
|
method: "POST",
|
|
1621
|
-
headers:
|
|
1633
|
+
headers: ie({ apiKey: e }),
|
|
1622
1634
|
body: JSON.stringify({ projectId: n, email: i, code: r })
|
|
1623
1635
|
});
|
|
1624
1636
|
if (!o.ok) throw new Error(await Ge(o));
|
|
@@ -1626,11 +1638,11 @@ async function Mn({ apiBase: t, apiKey: e, projectId: n, email: i, code: r }) {
|
|
|
1626
1638
|
return An(n, s), s;
|
|
1627
1639
|
}
|
|
1628
1640
|
async function Rn({ apiBase: t, apiKey: e, projectId: n, token: i }) {
|
|
1629
|
-
if (
|
|
1641
|
+
if (ue(n), !i) return { signedOut: !0 };
|
|
1630
1642
|
try {
|
|
1631
1643
|
await fetch(`${t}/ingest/logout`, {
|
|
1632
1644
|
method: "POST",
|
|
1633
|
-
headers:
|
|
1645
|
+
headers: ie({ apiKey: e, token: i }),
|
|
1634
1646
|
body: JSON.stringify({ projectId: n })
|
|
1635
1647
|
});
|
|
1636
1648
|
} catch {
|
|
@@ -1650,7 +1662,7 @@ if (typeof window < "u" && window.addEventListener)
|
|
|
1650
1662
|
function Ln() {
|
|
1651
1663
|
return Qe;
|
|
1652
1664
|
}
|
|
1653
|
-
const Kn = 2e4, et = 120,
|
|
1665
|
+
const Kn = 2e4, et = 120, he = 200;
|
|
1654
1666
|
function tt(t) {
|
|
1655
1667
|
if (typeof t != "string" || !t.trim() || t.length > 400) return null;
|
|
1656
1668
|
try {
|
|
@@ -1675,80 +1687,80 @@ function ot(t) {
|
|
|
1675
1687
|
function Nn(t, e) {
|
|
1676
1688
|
return ((t.slice(e.start, e.valueStart) + t.slice(e.valueEnd, e.end)).match(/[a-z]/gi) || []).length;
|
|
1677
1689
|
}
|
|
1678
|
-
const Un = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}|[A-Za-z0-9][\w-]{5,40}/gi,
|
|
1679
|
-
function
|
|
1680
|
-
const n = (t || []).filter((
|
|
1681
|
-
o.forEach((
|
|
1682
|
-
|
|
1683
|
-
const
|
|
1684
|
-
if (!
|
|
1685
|
-
let
|
|
1686
|
-
for (
|
|
1687
|
-
if (
|
|
1688
|
-
|
|
1690
|
+
const Un = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}|[A-Za-z0-9][\w-]{5,40}/gi, Re = /[\w-]/;
|
|
1691
|
+
function Ei(t, e) {
|
|
1692
|
+
const n = (t || []).filter((u) => u && u.scan !== !1 && u.pattern), i = [], r = [], o = (e || []).map((u) => typeof u == "string" ? u.slice(0, Kn) : "");
|
|
1693
|
+
o.forEach((u, d) => {
|
|
1694
|
+
u && n.forEach((b, y) => {
|
|
1695
|
+
const S = tt(b.pattern);
|
|
1696
|
+
if (!S) return;
|
|
1697
|
+
let E, $ = 0;
|
|
1698
|
+
for (S.lastIndex = 0; (E = S.exec(u)) !== null && !(++$ > he); ) {
|
|
1699
|
+
if (E[0] === "") {
|
|
1700
|
+
S.lastIndex += 1;
|
|
1689
1701
|
continue;
|
|
1690
1702
|
}
|
|
1691
|
-
const
|
|
1692
|
-
if (!
|
|
1693
|
-
const k =
|
|
1694
|
-
block:
|
|
1695
|
-
order:
|
|
1696
|
-
key:
|
|
1697
|
-
label:
|
|
1698
|
-
value: it(
|
|
1699
|
-
start:
|
|
1700
|
-
end:
|
|
1701
|
-
valueStart:
|
|
1702
|
-
valueEnd:
|
|
1703
|
+
const g = ot(E);
|
|
1704
|
+
if (!g) continue;
|
|
1705
|
+
const k = E.length > 1 && E[1] !== void 0 ? E[1] : E[0], v = E.index + Math.max(0, E[0].indexOf(k)), w = {
|
|
1706
|
+
block: d,
|
|
1707
|
+
order: y,
|
|
1708
|
+
key: b.key,
|
|
1709
|
+
label: b.label,
|
|
1710
|
+
value: it(b, g.value),
|
|
1711
|
+
start: g.start,
|
|
1712
|
+
end: g.end,
|
|
1713
|
+
valueStart: v,
|
|
1714
|
+
valueEnd: v + k.length
|
|
1703
1715
|
};
|
|
1704
|
-
|
|
1716
|
+
w.weight = Nn(u, w), i.push(w);
|
|
1705
1717
|
}
|
|
1706
1718
|
});
|
|
1707
1719
|
});
|
|
1708
|
-
const a = i.filter((
|
|
1709
|
-
for (const
|
|
1710
|
-
const
|
|
1711
|
-
s.has(
|
|
1712
|
-
const
|
|
1713
|
-
|
|
1720
|
+
const a = i.filter((u) => !i.some((d) => d !== u && d.block === u.block && d.key !== u.key && d.valueStart <= u.valueStart && d.valueEnd >= u.valueEnd && d.weight > u.weight)), s = /* @__PURE__ */ new Map();
|
|
1721
|
+
for (const u of a) {
|
|
1722
|
+
const d = u.value.toLowerCase();
|
|
1723
|
+
s.has(d) || s.set(d, { value: u.value, keys: /* @__PURE__ */ new Map() });
|
|
1724
|
+
const b = s.get(d);
|
|
1725
|
+
b.keys.has(u.key) || b.keys.set(u.key, { key: u.key, label: u.label, order: u.order });
|
|
1714
1726
|
}
|
|
1715
1727
|
const c = [], l = [], h = /* @__PURE__ */ new Map();
|
|
1716
|
-
for (const
|
|
1717
|
-
const
|
|
1718
|
-
if (
|
|
1719
|
-
l.push({ value:
|
|
1728
|
+
for (const u of s.values()) {
|
|
1729
|
+
const d = [...u.keys.values()].sort((S, E) => S.order - E.order);
|
|
1730
|
+
if (d.length > 1) {
|
|
1731
|
+
l.push({ value: u.value, kinds: d.map(({ key: S, label: E }) => ({ key: S, label: E })) });
|
|
1720
1732
|
continue;
|
|
1721
1733
|
}
|
|
1722
|
-
const [{ key:
|
|
1723
|
-
h.has(
|
|
1734
|
+
const [{ key: b, label: y }] = d;
|
|
1735
|
+
h.has(b) || h.set(b, []), h.get(b).push({ key: b, label: y, value: u.value });
|
|
1724
1736
|
}
|
|
1725
|
-
for (const
|
|
1726
|
-
if (
|
|
1727
|
-
else for (const
|
|
1737
|
+
for (const u of h.values())
|
|
1738
|
+
if (u.length === 1) c.push(u[0]);
|
|
1739
|
+
else for (const d of u) l.push({ value: d.value, kinds: [{ key: d.key, label: d.label }] });
|
|
1728
1740
|
const f = new Set(s.keys());
|
|
1729
|
-
return o.forEach((
|
|
1730
|
-
if (!
|
|
1731
|
-
const
|
|
1732
|
-
let
|
|
1733
|
-
for (; (
|
|
1734
|
-
const
|
|
1735
|
-
if (
|
|
1736
|
-
const k =
|
|
1737
|
-
if (
|
|
1738
|
-
const
|
|
1739
|
-
if (f.has(
|
|
1740
|
-
const
|
|
1741
|
-
|
|
1741
|
+
return o.forEach((u, d) => {
|
|
1742
|
+
if (!u) return;
|
|
1743
|
+
const b = i.filter(($) => $.block === d), y = new RegExp(Un.source, "gi");
|
|
1744
|
+
let S, E = 0;
|
|
1745
|
+
for (; (S = y.exec(u)) !== null && ++E <= he; ) {
|
|
1746
|
+
const $ = S.index, g = $ + S[0].length;
|
|
1747
|
+
if (b.some((B) => $ < B.end && g > B.start)) continue;
|
|
1748
|
+
const k = u[$ - 1] || "", v = u[g] || "";
|
|
1749
|
+
if (Re.test(k) || Re.test(v) || k === "/" || k === "@" || v === "@" || k === "." || v === "." && /\w/.test(u[g + 1] || "") || !/\d/.test(S[0])) continue;
|
|
1750
|
+
const w = nt(S[0]), C = w.toLowerCase();
|
|
1751
|
+
if (f.has(C)) continue;
|
|
1752
|
+
const m = (t || []).filter((B) => B && Dn(B, w)).map(({ key: B, label: A }) => ({ key: B, label: A }));
|
|
1753
|
+
m.length && (f.add(C), r.push({ value: w, kinds: m }));
|
|
1742
1754
|
}
|
|
1743
1755
|
}), { found: c, conflicts: l, loose: r };
|
|
1744
1756
|
}
|
|
1745
|
-
function
|
|
1757
|
+
function Dn(t, e) {
|
|
1746
1758
|
const n = typeof e == "string" ? e.trim() : "";
|
|
1747
1759
|
if (!n || n.length > et) return null;
|
|
1748
1760
|
const i = tt(t && (t.valuePattern || t.pattern));
|
|
1749
1761
|
if (!i) return null;
|
|
1750
1762
|
let r, o = 0;
|
|
1751
|
-
for (i.lastIndex = 0; (r = i.exec(n)) !== null && !(++o >
|
|
1763
|
+
for (i.lastIndex = 0; (r = i.exec(n)) !== null && !(++o > he); ) {
|
|
1752
1764
|
if (r[0] === "") {
|
|
1753
1765
|
i.lastIndex += 1;
|
|
1754
1766
|
continue;
|
|
@@ -1761,7 +1773,7 @@ function Pn(t, e) {
|
|
|
1761
1773
|
}
|
|
1762
1774
|
return null;
|
|
1763
1775
|
}
|
|
1764
|
-
async function
|
|
1776
|
+
async function Pn({ apiBase: t, apiKey: e, projectId: n }) {
|
|
1765
1777
|
const i = { policy: "off", fields: [] };
|
|
1766
1778
|
try {
|
|
1767
1779
|
const r = await fetch(
|
|
@@ -1775,7 +1787,7 @@ async function Dn({ apiBase: t, apiKey: e, projectId: n }) {
|
|
|
1775
1787
|
return i;
|
|
1776
1788
|
}
|
|
1777
1789
|
}
|
|
1778
|
-
const
|
|
1790
|
+
const $i = /Did this answer your question\?/i;
|
|
1779
1791
|
async function _n({ apiBase: t, apiKey: e, projectId: n }) {
|
|
1780
1792
|
try {
|
|
1781
1793
|
const i = await fetch(
|
|
@@ -1789,8 +1801,8 @@ async function _n({ apiBase: t, apiKey: e, projectId: n }) {
|
|
|
1789
1801
|
return [];
|
|
1790
1802
|
}
|
|
1791
1803
|
}
|
|
1792
|
-
const Hn = 5 * 6e4, rt = "bugcatch:announcements:seen", zn = 40,
|
|
1793
|
-
async function
|
|
1804
|
+
const Hn = 5 * 6e4, rt = "bugcatch:announcements:seen", zn = 40, Fn = ["info", "success", "warning", "critical"], at = (t) => `bugcatch:announcements:${t}`;
|
|
1805
|
+
async function Xn({
|
|
1794
1806
|
apiBase: t,
|
|
1795
1807
|
apiKey: e,
|
|
1796
1808
|
projectId: n,
|
|
@@ -1811,7 +1823,7 @@ async function Fn({
|
|
|
1811
1823
|
return [];
|
|
1812
1824
|
}
|
|
1813
1825
|
}
|
|
1814
|
-
function
|
|
1826
|
+
function qn(t, { on: e = Yn(), seen: n = ct() } = {}) {
|
|
1815
1827
|
return (t || []).filter((i) => Vn(i, e) && !(i.dismissible && n.includes(st(i))));
|
|
1816
1828
|
}
|
|
1817
1829
|
function Wn(t) {
|
|
@@ -1843,7 +1855,7 @@ function Zn(t) {
|
|
|
1843
1855
|
revision: Number.isInteger(e.revision) ? e.revision : 0,
|
|
1844
1856
|
title: e.title,
|
|
1845
1857
|
body: typeof e.body == "string" ? e.body : "",
|
|
1846
|
-
tone:
|
|
1858
|
+
tone: Fn.includes(e.tone) ? e.tone : "info",
|
|
1847
1859
|
// Both halves, or neither, as the API saves them.
|
|
1848
1860
|
ctaLabel: i && typeof e.ctaLabel == "string" ? e.ctaLabel : "",
|
|
1849
1861
|
ctaHref: i && typeof e.ctaLabel == "string" ? i : "",
|
|
@@ -1878,53 +1890,108 @@ function Qn(t, e) {
|
|
|
1878
1890
|
} catch {
|
|
1879
1891
|
}
|
|
1880
1892
|
}
|
|
1881
|
-
const
|
|
1893
|
+
const ei = ["idea", "praise", "confusing", "other"], ti = 5, ni = 4e3;
|
|
1894
|
+
async function ii({ apiBase: t, apiKey: e, projectId: n }) {
|
|
1895
|
+
try {
|
|
1896
|
+
const i = await fetch(`${t}/ingest/feedback?projectId=${encodeURIComponent(n)}`, {
|
|
1897
|
+
headers: { "X-BugCatch-Key": e }
|
|
1898
|
+
});
|
|
1899
|
+
if (!i.ok) return !1;
|
|
1900
|
+
const r = await i.json();
|
|
1901
|
+
return (r == null ? void 0 : r.enabled) === !0;
|
|
1902
|
+
} catch {
|
|
1903
|
+
return !1;
|
|
1904
|
+
}
|
|
1905
|
+
}
|
|
1906
|
+
function oi({ message: t, kind: e, score: n, email: i, name: r } = {}) {
|
|
1907
|
+
const o = typeof t == "string" ? t.trim().slice(0, ni) : "";
|
|
1908
|
+
if (!o) throw new Error("[BugCatch] feedback needs a message.");
|
|
1909
|
+
const a = typeof n == "string" && n.trim() !== "" ? Number(n) : n, s = typeof i == "string" ? i.trim() : "", c = typeof r == "string" ? r.trim() : "";
|
|
1910
|
+
return {
|
|
1911
|
+
message: o,
|
|
1912
|
+
...ei.includes(e) ? { kind: e } : {},
|
|
1913
|
+
...Number.isInteger(a) && a >= 1 && a <= ti ? { score: a } : {},
|
|
1914
|
+
...s ? { email: s.slice(0, 254) } : {},
|
|
1915
|
+
...c ? { name: c.slice(0, 120) } : {}
|
|
1916
|
+
};
|
|
1917
|
+
}
|
|
1918
|
+
async function ri({ apiBase: t, apiKey: e, token: n, payload: i }) {
|
|
1919
|
+
let r;
|
|
1920
|
+
try {
|
|
1921
|
+
r = await fetch(`${t}/ingest/feedback`, {
|
|
1922
|
+
method: "POST",
|
|
1923
|
+
headers: {
|
|
1924
|
+
"Content-Type": "application/json",
|
|
1925
|
+
"X-BugCatch-Key": e,
|
|
1926
|
+
// Present only where they signed in, so the server can put a proved
|
|
1927
|
+
// name and address on it. A stale one is ignored there, not refused.
|
|
1928
|
+
...n ? { "X-BugCatch-Session": n } : {}
|
|
1929
|
+
},
|
|
1930
|
+
body: JSON.stringify(i)
|
|
1931
|
+
});
|
|
1932
|
+
} catch (o) {
|
|
1933
|
+
const a = new Error(`[BugCatch] could not reach ${t} — check your connection and try again.`);
|
|
1934
|
+
throw a.cause = o, a;
|
|
1935
|
+
}
|
|
1936
|
+
if (!r.ok) {
|
|
1937
|
+
let o = "";
|
|
1938
|
+
try {
|
|
1939
|
+
const s = await r.json();
|
|
1940
|
+
o = Array.isArray(s.message) ? s.message.join(", ") : s.message || "";
|
|
1941
|
+
} catch {
|
|
1942
|
+
}
|
|
1943
|
+
const a = r.status === 429 ? new Error(`[BugCatch] ${K(o)}`) : new Error(`[BugCatch] ${o || `feedback could not be sent (HTTP ${r.status})`}`);
|
|
1944
|
+
throw a.status = r.status, a;
|
|
1945
|
+
}
|
|
1946
|
+
return r.json();
|
|
1947
|
+
}
|
|
1948
|
+
const G = 120, ai = 500, Q = 30, si = 1e3, be = {
|
|
1882
1949
|
loanId: ["loanId", "loanNumber"],
|
|
1883
1950
|
applicationId: ["applicationId"],
|
|
1884
1951
|
customerNumber: ["customerNumber", "customerId"]
|
|
1885
|
-
},
|
|
1886
|
-
function
|
|
1952
|
+
}, ci = /[\u0000-\u001f\u007f]/;
|
|
1953
|
+
function li(t) {
|
|
1887
1954
|
if (typeof t == "number") return Number.isFinite(t) ? String(t) : null;
|
|
1888
1955
|
if (typeof t != "string") return null;
|
|
1889
1956
|
const e = t.trim();
|
|
1890
|
-
return !e || e.length >
|
|
1957
|
+
return !e || e.length > G || ci.test(e) ? null : e;
|
|
1891
1958
|
}
|
|
1892
|
-
function
|
|
1959
|
+
function R(t) {
|
|
1893
1960
|
return t === null ? "null" : Array.isArray(t) ? "an array" : typeof t == "object" ? "an object" : `a ${typeof t}`;
|
|
1894
1961
|
}
|
|
1895
|
-
function
|
|
1962
|
+
function fe(t, e, n, i, r) {
|
|
1896
1963
|
for (const o of n) {
|
|
1897
1964
|
if (!(o in t) || t[o] === void 0 || t[o] === null || t[o] === "") continue;
|
|
1898
|
-
const a =
|
|
1965
|
+
const a = li(t[o]);
|
|
1899
1966
|
if (a) return a;
|
|
1900
1967
|
const s = t[o];
|
|
1901
|
-
r(typeof s == "string" && s.trim().length >
|
|
1968
|
+
r(typeof s == "string" && s.trim().length > G ? `${i}.${o} is longer than ${G} characters and was dropped — pass the identifier itself, not a sentence or a URL.` : `${i}.${o} should be a string or number, got ${R(s)} — it was dropped.`);
|
|
1902
1969
|
}
|
|
1903
1970
|
return null;
|
|
1904
1971
|
}
|
|
1905
1972
|
function lt(t) {
|
|
1906
1973
|
if (t === null || typeof t == "boolean") return { ok: !0, value: t };
|
|
1907
1974
|
if (typeof t == "number") return Number.isFinite(t) ? { ok: !0, value: t } : { ok: !1 };
|
|
1908
|
-
if (typeof t == "string") return { ok: !0, value: t.slice(0,
|
|
1975
|
+
if (typeof t == "string") return { ok: !0, value: t.slice(0, ai) };
|
|
1909
1976
|
if (typeof t == "object")
|
|
1910
1977
|
try {
|
|
1911
1978
|
const e = JSON.stringify(t);
|
|
1912
|
-
if (e && e.length <=
|
|
1979
|
+
if (e && e.length <= si) return { ok: !0, value: JSON.parse(e) };
|
|
1913
1980
|
} catch {
|
|
1914
1981
|
}
|
|
1915
1982
|
return { ok: !1 };
|
|
1916
1983
|
}
|
|
1917
|
-
const
|
|
1918
|
-
function
|
|
1984
|
+
const dt = ["email", "name", "phone"], di = /* @__PURE__ */ new Set(["id", "userId", ...dt, ...Object.values(be).flat()]);
|
|
1985
|
+
function Le(t, e = () => {
|
|
1919
1986
|
}) {
|
|
1920
1987
|
if (t == null) return null;
|
|
1921
1988
|
if (typeof t != "object" || Array.isArray(t))
|
|
1922
|
-
return e(`identify() takes an object like { id, email, name } or null, got ${
|
|
1989
|
+
return e(`identify() takes an object like { id, email, name } or null, got ${R(t)} — ignored.`), null;
|
|
1923
1990
|
const n = {};
|
|
1924
1991
|
try {
|
|
1925
|
-
const i =
|
|
1992
|
+
const i = fe(t, "id", ["id", "userId"], "identify()", e);
|
|
1926
1993
|
i && (n.id = i);
|
|
1927
|
-
for (const o of
|
|
1994
|
+
for (const o of dt) {
|
|
1928
1995
|
const a = t[o];
|
|
1929
1996
|
if (a == null || a === "") continue;
|
|
1930
1997
|
if (o === "phone" && typeof a == "number" && Number.isFinite(a)) {
|
|
@@ -1932,26 +1999,26 @@ function Re(t, e = () => {
|
|
|
1932
1999
|
continue;
|
|
1933
2000
|
}
|
|
1934
2001
|
if (typeof a != "string") {
|
|
1935
|
-
e(`identify().${o} should be a string, got ${
|
|
2002
|
+
e(`identify().${o} should be a string, got ${R(a)} — it was dropped.`);
|
|
1936
2003
|
continue;
|
|
1937
2004
|
}
|
|
1938
|
-
const s = a.trim().slice(0, o === "name" ? 200 :
|
|
2005
|
+
const s = a.trim().slice(0, o === "name" ? 200 : G);
|
|
1939
2006
|
s && (o === "email" && !s.includes("@") && e(`identify().email "${s}" does not look like an email address — reports cannot be threaded or followed up without one.`), n[o] = s);
|
|
1940
2007
|
}
|
|
1941
|
-
for (const [o, a] of Object.entries(
|
|
1942
|
-
const s =
|
|
2008
|
+
for (const [o, a] of Object.entries(be)) {
|
|
2009
|
+
const s = fe(t, o, a, "identify()", e);
|
|
1943
2010
|
s && (n[o] = s);
|
|
1944
2011
|
}
|
|
1945
2012
|
let r = 0;
|
|
1946
2013
|
for (const [o, a] of Object.entries(t)) {
|
|
1947
|
-
if (
|
|
1948
|
-
if (r >=
|
|
1949
|
-
e(`identify() was given more than ${
|
|
2014
|
+
if (di.has(o) || a === void 0 || typeof a == "function") continue;
|
|
2015
|
+
if (r >= Q) {
|
|
2016
|
+
e(`identify() was given more than ${Q} extra fields; the rest were dropped.`);
|
|
1950
2017
|
break;
|
|
1951
2018
|
}
|
|
1952
2019
|
const s = lt(a);
|
|
1953
2020
|
if (!s.ok) {
|
|
1954
|
-
e(`identify().${o} could not be sent (${
|
|
2021
|
+
e(`identify().${o} could not be sent (${R(a)} too large or not serialisable) — dropped.`);
|
|
1955
2022
|
continue;
|
|
1956
2023
|
}
|
|
1957
2024
|
n[o] = s.value, r += 1;
|
|
@@ -1960,16 +2027,16 @@ function Re(t, e = () => {
|
|
|
1960
2027
|
}
|
|
1961
2028
|
return !n.id && !n.email && e("identify() was called without an id or email — reports will not be attributed to anyone, and nothing can be looked up by user."), n;
|
|
1962
2029
|
}
|
|
1963
|
-
function
|
|
2030
|
+
function se(t, e, n = () => {
|
|
1964
2031
|
}) {
|
|
1965
2032
|
if (e === null) return {};
|
|
1966
2033
|
const i = { ...t || {} };
|
|
1967
2034
|
if (e === void 0) return i;
|
|
1968
2035
|
if (typeof e != "object" || Array.isArray(e))
|
|
1969
|
-
return n(`setContext() takes an object like { loanId, screen } or null, got ${
|
|
2036
|
+
return n(`setContext() takes an object like { loanId, screen } or null, got ${R(e)} — ignored.`), i;
|
|
1970
2037
|
try {
|
|
1971
2038
|
const r = /* @__PURE__ */ new Map();
|
|
1972
|
-
for (const [o, a] of Object.entries(
|
|
2039
|
+
for (const [o, a] of Object.entries(be)) for (const s of a) r.set(s, o);
|
|
1973
2040
|
for (const [o, a] of Object.entries(e)) {
|
|
1974
2041
|
const s = r.get(o);
|
|
1975
2042
|
if (a == null) {
|
|
@@ -1977,18 +2044,18 @@ function Le(t, e, n = () => {
|
|
|
1977
2044
|
continue;
|
|
1978
2045
|
}
|
|
1979
2046
|
if (s) {
|
|
1980
|
-
const l =
|
|
2047
|
+
const l = fe({ [o]: a }, s, [o], "setContext()", n);
|
|
1981
2048
|
l ? i[s] = l : delete i[s];
|
|
1982
2049
|
continue;
|
|
1983
2050
|
}
|
|
1984
2051
|
if (typeof a == "function") continue;
|
|
1985
|
-
if (!(o in i) && Object.keys(i).length >=
|
|
1986
|
-
n(`setContext() holds at most ${
|
|
2052
|
+
if (!(o in i) && Object.keys(i).length >= Q) {
|
|
2053
|
+
n(`setContext() holds at most ${Q} keys; "${o}" was dropped.`);
|
|
1987
2054
|
continue;
|
|
1988
2055
|
}
|
|
1989
2056
|
const c = lt(a);
|
|
1990
2057
|
if (!c.ok) {
|
|
1991
|
-
n(`setContext().${o} could not be sent (${
|
|
2058
|
+
n(`setContext().${o} could not be sent (${R(a)} too large or not serialisable) — dropped.`);
|
|
1992
2059
|
continue;
|
|
1993
2060
|
}
|
|
1994
2061
|
i[o] = c.value;
|
|
@@ -1997,7 +2064,7 @@ function Le(t, e, n = () => {
|
|
|
1997
2064
|
}
|
|
1998
2065
|
return i;
|
|
1999
2066
|
}
|
|
2000
|
-
const
|
|
2067
|
+
const ut = [
|
|
2001
2068
|
"apiBase",
|
|
2002
2069
|
"apiKey",
|
|
2003
2070
|
"projectId",
|
|
@@ -2034,8 +2101,9 @@ const dt = [
|
|
|
2034
2101
|
"environment",
|
|
2035
2102
|
"buildId",
|
|
2036
2103
|
"chunkBase",
|
|
2037
|
-
"announcements"
|
|
2038
|
-
|
|
2104
|
+
"announcements",
|
|
2105
|
+
"feedback"
|
|
2106
|
+
], ui = [
|
|
2039
2107
|
"beforeSend",
|
|
2040
2108
|
"onUpdate",
|
|
2041
2109
|
"onCallState",
|
|
@@ -2044,35 +2112,35 @@ const dt = [
|
|
|
2044
2112
|
"onAssistantPhase",
|
|
2045
2113
|
"onError"
|
|
2046
2114
|
];
|
|
2047
|
-
function
|
|
2115
|
+
function hi(t) {
|
|
2048
2116
|
const e = t.toLowerCase().replace(/[-_]/g, "");
|
|
2049
|
-
return
|
|
2117
|
+
return ut.find((n) => n.toLowerCase() === e) || null;
|
|
2050
2118
|
}
|
|
2051
|
-
const Ke = /^(your[_-]|<|xxx|todo|changeme)/i,
|
|
2052
|
-
function
|
|
2119
|
+
const Ke = /^(your[_-]|<|xxx|todo|changeme)/i, fi = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
2120
|
+
function pi(t, { pageHost: e = "" } = {}) {
|
|
2053
2121
|
const n = [], i = [];
|
|
2054
2122
|
if (!t || typeof t != "object")
|
|
2055
2123
|
return n.push("init() takes an options object: BugCatch.init({ apiBase, apiKey, projectId })."), { errors: n, warnings: i };
|
|
2056
2124
|
const { apiKey: r, projectId: o, apiBase: a } = t;
|
|
2057
|
-
r ? typeof r != "string" ? n.push(`apiKey must be a string, got ${
|
|
2125
|
+
r ? typeof r != "string" ? n.push(`apiKey must be a string, got ${R(r)}.`) : Ke.test(r) ? n.push(`apiKey is still the placeholder "${r}" — paste the key you saved when you created it.`) : fi.test(r) ? i.push("apiKey looks like a project id — did you swap apiKey and projectId?") : r.startsWith("bc_") || i.push('apiKey does not look like a BugCatch key (they start with "bc_live_") — reports will be refused with HTTP 401.') : n.push("apiKey is required — create one under Workspace Settings → API Keys."), o ? typeof o != "string" ? n.push(`projectId must be a string, got ${R(o)}.`) : Ke.test(o) ? n.push(`projectId is still the placeholder "${o}".`) : o.startsWith("bc_") ? i.push("projectId looks like an API key — did you swap apiKey and projectId?") : /\s/.test(o) && i.push("projectId contains whitespace — check it was copied cleanly.") : n.push("projectId is required — copy it from Project Settings → Web SDK."), a == null ? !e || /^(localhost|127\.|0\.0\.0\.0|\[::1\])/.test(e) || i.push("apiBase is not set, so reports go to http://localhost:3000 — set apiBase to your BugCatch API URL.") : (typeof a != "string" || !/^https?:\/\//.test(a)) && i.push(`apiBase should be an absolute http(s) URL, got ${JSON.stringify(a)}.`);
|
|
2058
2126
|
for (const s of Object.keys(t)) {
|
|
2059
|
-
if (
|
|
2060
|
-
const c =
|
|
2127
|
+
if (ut.includes(s)) continue;
|
|
2128
|
+
const c = hi(s);
|
|
2061
2129
|
i.push(c ? `unknown option "${s}" — did you mean "${c}"?` : `unknown option "${s}" is ignored.`);
|
|
2062
2130
|
}
|
|
2063
|
-
for (const s of
|
|
2131
|
+
for (const s of ui) {
|
|
2064
2132
|
const c = t[s];
|
|
2065
|
-
c != null && typeof c != "function" && i.push(`${s} should be a function, got ${
|
|
2133
|
+
c != null && typeof c != "function" && i.push(`${s} should be a function, got ${R(c)} — it will not be called.`);
|
|
2066
2134
|
}
|
|
2067
2135
|
return { errors: n, warnings: i };
|
|
2068
2136
|
}
|
|
2069
|
-
function
|
|
2137
|
+
function gi(t) {
|
|
2070
2138
|
return typeof t == "string" ? t.replace(/\/+$/, "") : t;
|
|
2071
2139
|
}
|
|
2072
|
-
const
|
|
2140
|
+
const U = {
|
|
2073
2141
|
name: "@sphoro/bugcatch-web-sdk",
|
|
2074
|
-
version: "0.
|
|
2075
|
-
},
|
|
2142
|
+
version: "0.21.0"
|
|
2143
|
+
}, D = {
|
|
2076
2144
|
apiBase: "http://localhost:3000",
|
|
2077
2145
|
apiKey: null,
|
|
2078
2146
|
projectId: null,
|
|
@@ -2094,6 +2162,10 @@ const D = {
|
|
|
2094
2162
|
// ones written for that. false draws nothing; announcements() still answers,
|
|
2095
2163
|
// for a site that shows them its own way.
|
|
2096
2164
|
announcements: !0,
|
|
2165
|
+
// Offer "Give feedback" beside "Report a bug" in the panel, where the
|
|
2166
|
+
// project has it switched on (Settings → Project → General). false hides it
|
|
2167
|
+
// on this site; feedback() still sends, for a site with a form of its own.
|
|
2168
|
+
feedback: !0,
|
|
2097
2169
|
// Screenshot / screen recording / file attach. Capture needs getDisplayMedia,
|
|
2098
2170
|
// so it is offered only where the browser has it — file attach always works.
|
|
2099
2171
|
attachments: !0,
|
|
@@ -2156,15 +2228,15 @@ const D = {
|
|
|
2156
2228
|
// printed either way.
|
|
2157
2229
|
debug: !1
|
|
2158
2230
|
};
|
|
2159
|
-
function
|
|
2160
|
-
const e =
|
|
2231
|
+
function mi(t) {
|
|
2232
|
+
const e = T();
|
|
2161
2233
|
return e ? { ...t, watchToken: e } : t;
|
|
2162
2234
|
}
|
|
2163
|
-
var
|
|
2235
|
+
var p, q, ft, L, pt, pe, _, W, J, gt, mt, wt, Y, yt;
|
|
2164
2236
|
class ht {
|
|
2165
2237
|
constructor() {
|
|
2166
|
-
|
|
2167
|
-
this.config = { ...
|
|
2238
|
+
ve(this, p);
|
|
2239
|
+
this.config = { ...D }, this.started = !1, this.teardown = [], this.consoleBuffer = F(D.consoleLimit), this.networkBuffer = F(D.networkLimit), this.stopWatching = null, this.notifier = null, this.call = null, this.callStarting = !1, this.ringing = null, this.listeners = /* @__PURE__ */ new Map(), this.context = {}, this.warned = /* @__PURE__ */ new Set(), this.phases = /* @__PURE__ */ new Map();
|
|
2168
2240
|
}
|
|
2169
2241
|
/** A misconfiguration, said once. Always printed — it is what saves a day of guessing. */
|
|
2170
2242
|
warn(e) {
|
|
@@ -2177,14 +2249,14 @@ class ht {
|
|
|
2177
2249
|
init(e = {}) {
|
|
2178
2250
|
if (this.started)
|
|
2179
2251
|
return console.warn("[BugCatch] init() called twice — ignoring the second call."), this;
|
|
2180
|
-
const { errors: n, warnings: i } =
|
|
2252
|
+
const { errors: n, warnings: i } = pi(e, {
|
|
2181
2253
|
pageHost: typeof location < "u" ? location.hostname : ""
|
|
2182
2254
|
});
|
|
2183
2255
|
if (n.length) throw new Error(`[BugCatch] ${n[0]}`);
|
|
2184
2256
|
for (const o of i) this.warn(o);
|
|
2185
2257
|
const r = this.config.user;
|
|
2186
|
-
return this.config = { ...
|
|
2187
|
-
version:
|
|
2258
|
+
return this.config = { ...D, ...e, apiBase: gi(e.apiBase ?? D.apiBase) }, this.config.user = e.user !== void 0 ? Le(e.user, (o) => this.warn(o.replace("identify()", "init({ user })"))) : r || null, e.context && this.setContext(e.context), this.consoleBuffer = F(this.config.consoleLimit), this.networkBuffer = F(this.config.networkLimit), this.config.captureConsole && this.teardown.push(At(this.consoleBuffer)), this.config.captureNetwork && this.teardown.push(jt(this.networkBuffer)), this.config.captureErrors && this.teardown.push(Ot(this.consoleBuffer)), tn(this.config.projectId), this.config.widget && this.teardown.push(Xt(this)), this.config.updates && T() && (this.startWatching(), queueMicrotask(() => x(this, p, L).call(this))), this.started = !0, x(this, p, ft).call(this), this.debugLog("initialised", {
|
|
2259
|
+
version: U.version,
|
|
2188
2260
|
apiBase: this.config.apiBase,
|
|
2189
2261
|
projectId: this.config.projectId,
|
|
2190
2262
|
user: this.config.user,
|
|
@@ -2201,22 +2273,22 @@ class ht {
|
|
|
2201
2273
|
apiBase: this.config.apiBase,
|
|
2202
2274
|
onUpdate: (n) => {
|
|
2203
2275
|
if (n != null && n.incomingCall) {
|
|
2204
|
-
x(this,
|
|
2276
|
+
x(this, p, wt).call(this, n);
|
|
2205
2277
|
return;
|
|
2206
2278
|
}
|
|
2207
2279
|
if (n != null && n.callWithdrawn) {
|
|
2208
|
-
x(this,
|
|
2280
|
+
x(this, p, Y).call(this, n.callWithdrawn.callId);
|
|
2209
2281
|
return;
|
|
2210
2282
|
}
|
|
2211
2283
|
const i = on(n);
|
|
2212
|
-
typeof this.config.onUpdate == "function" && this.config.onUpdate(i), this.emit("update", i), x(this,
|
|
2284
|
+
typeof this.config.onUpdate == "function" && this.config.onUpdate(i), this.emit("update", i), x(this, p, L).call(this);
|
|
2213
2285
|
}
|
|
2214
2286
|
}), this.teardown.push(() => {
|
|
2215
2287
|
var n;
|
|
2216
2288
|
return (n = this.stopWatching) == null ? void 0 : n.call(this);
|
|
2217
|
-
}), this.teardown.push(() => x(this,
|
|
2289
|
+
}), this.teardown.push(() => x(this, p, Y).call(this));
|
|
2218
2290
|
const e = (n) => {
|
|
2219
|
-
(n.key ===
|
|
2291
|
+
(n.key === Z || n.key === null) && x(this, p, L).call(this);
|
|
2220
2292
|
};
|
|
2221
2293
|
return window.addEventListener("storage", e), this.teardown.push(() => window.removeEventListener("storage", e)), this;
|
|
2222
2294
|
}
|
|
@@ -2260,7 +2332,7 @@ class ht {
|
|
|
2260
2332
|
* Each carries the `id` the mark-read calls take.
|
|
2261
2333
|
*/
|
|
2262
2334
|
unreadUpdates() {
|
|
2263
|
-
return
|
|
2335
|
+
return z();
|
|
2264
2336
|
}
|
|
2265
2337
|
/**
|
|
2266
2338
|
* Mark one update read. It stops being shown, here and on the next load.
|
|
@@ -2273,7 +2345,7 @@ class ht {
|
|
|
2273
2345
|
* knows when its reader has seen one, so it has to say.
|
|
2274
2346
|
*/
|
|
2275
2347
|
markUpdateRead(e) {
|
|
2276
|
-
return rn(e), x(this,
|
|
2348
|
+
return rn(e), x(this, p, L).call(this), this;
|
|
2277
2349
|
}
|
|
2278
2350
|
/**
|
|
2279
2351
|
* Mark everything about one report read.
|
|
@@ -2282,18 +2354,18 @@ class ht {
|
|
|
2282
2354
|
* the thread opens; an integration with its own report view should too.
|
|
2283
2355
|
*/
|
|
2284
2356
|
markReportRead(e) {
|
|
2285
|
-
return an(e), x(this,
|
|
2357
|
+
return an(e), x(this, p, L).call(this), this;
|
|
2286
2358
|
}
|
|
2287
2359
|
/** Mark everything read. The "clear all" behind your own notification list. */
|
|
2288
2360
|
markUpdatesRead() {
|
|
2289
|
-
return Ze(), x(this,
|
|
2361
|
+
return Ze(), x(this, p, L).call(this), this;
|
|
2290
2362
|
}
|
|
2291
2363
|
/**
|
|
2292
2364
|
* Tell the team whether their fix worked. STILL_HAPPENING reopens the report
|
|
2293
2365
|
* and re-sends this browser's context with it.
|
|
2294
2366
|
*/
|
|
2295
2367
|
async verifyFix(e, { result: n, resolvedAt: i, note: r }) {
|
|
2296
|
-
const o = n === "STILL_HAPPENING" ? await x(this,
|
|
2368
|
+
const o = n === "STILL_HAPPENING" ? await x(this, p, W).call(this, {}) : {};
|
|
2297
2369
|
return $n({ apiBase: this.config.apiBase, bugId: e, result: n, resolvedAt: i, note: r, metadata: o.metadata, logs: o.logs });
|
|
2298
2370
|
}
|
|
2299
2371
|
/**
|
|
@@ -2318,7 +2390,7 @@ class ht {
|
|
|
2318
2390
|
*/
|
|
2319
2391
|
async myReport(e) {
|
|
2320
2392
|
const n = await ln({ apiBase: this.config.apiBase, bugId: e });
|
|
2321
|
-
return x(this,
|
|
2393
|
+
return x(this, p, pt).call(this, e, n == null ? void 0 : n.assistant), n;
|
|
2322
2394
|
}
|
|
2323
2395
|
/**
|
|
2324
2396
|
* Write back on a report this browser filed.
|
|
@@ -2334,7 +2406,7 @@ class ht {
|
|
|
2334
2406
|
* the caller renders what the server kept rather than what it hoped it sent.
|
|
2335
2407
|
*/
|
|
2336
2408
|
replyToReport(e, { body: n, attachments: i } = {}) {
|
|
2337
|
-
return
|
|
2409
|
+
return dn({ apiBase: this.config.apiBase, bugId: e, body: n, attachments: i });
|
|
2338
2410
|
}
|
|
2339
2411
|
/**
|
|
2340
2412
|
* Whether this visitor can report something by talking about it instead.
|
|
@@ -2387,7 +2459,7 @@ class ht {
|
|
|
2387
2459
|
async callKinds() {
|
|
2388
2460
|
var n;
|
|
2389
2461
|
const e = { agent: !1, live: !1 };
|
|
2390
|
-
return !this.config.voice || !((n = this.config.user) != null && n.email) ? e : this.kinds !== void 0 ? this.kinds : (this.kinds = await
|
|
2462
|
+
return !this.config.voice || !((n = this.config.user) != null && n.email) ? e : this.kinds !== void 0 ? this.kinds : (this.kinds = await un({
|
|
2391
2463
|
apiBase: this.config.apiBase,
|
|
2392
2464
|
apiKey: this.config.apiKey,
|
|
2393
2465
|
projectId: this.config.projectId
|
|
@@ -2408,7 +2480,7 @@ class ht {
|
|
|
2408
2480
|
* for either of them to be asking about.
|
|
2409
2481
|
*/
|
|
2410
2482
|
canCall(e) {
|
|
2411
|
-
return this.config.voice ?
|
|
2483
|
+
return this.config.voice ? je({ apiBase: this.config.apiBase, bugId: e }) : Promise.resolve(!1);
|
|
2412
2484
|
}
|
|
2413
2485
|
/**
|
|
2414
2486
|
* Ring the team.
|
|
@@ -2451,7 +2523,7 @@ class ht {
|
|
|
2451
2523
|
try {
|
|
2452
2524
|
if (!await this.callKind())
|
|
2453
2525
|
throw new Error((n = this.config.user) != null && n.email ? "[BugCatch] calling is not available on this project." : "[BugCatch] a call needs to know who is calling — call identify() with an email first.");
|
|
2454
|
-
return await x(this,
|
|
2526
|
+
return await x(this, p, mt).call(this, e);
|
|
2455
2527
|
} finally {
|
|
2456
2528
|
this.callStarting = !1;
|
|
2457
2529
|
}
|
|
@@ -2474,7 +2546,7 @@ class ht {
|
|
|
2474
2546
|
* For a host application drawing its own button. The widget asks this itself.
|
|
2475
2547
|
*/
|
|
2476
2548
|
canCallTeam(e) {
|
|
2477
|
-
return this.config.voice ?
|
|
2549
|
+
return this.config.voice ? je({ apiBase: this.config.apiBase, bugId: e }) : Promise.resolve(!1);
|
|
2478
2550
|
}
|
|
2479
2551
|
/**
|
|
2480
2552
|
* End the call in progress, of either kind. Does nothing when there is not
|
|
@@ -2501,7 +2573,7 @@ class ht {
|
|
|
2501
2573
|
/** True when this browser has filed something, so a "your reports" entry
|
|
2502
2574
|
* point can be hidden until it would show anything. */
|
|
2503
2575
|
hasReports() {
|
|
2504
|
-
return !!
|
|
2576
|
+
return !!T();
|
|
2505
2577
|
}
|
|
2506
2578
|
/**
|
|
2507
2579
|
* Forget this browser's reports — call on sign-out, or the next person at
|
|
@@ -2509,7 +2581,7 @@ class ht {
|
|
|
2509
2581
|
*/
|
|
2510
2582
|
forgetReports() {
|
|
2511
2583
|
var e;
|
|
2512
|
-
return (e = this.stopWatching) == null || e.call(this), this.stopWatching = null, this.endCall(),
|
|
2584
|
+
return (e = this.stopWatching) == null || e.call(this), this.stopWatching = null, this.endCall(), N(), x(this, p, L).call(this), this;
|
|
2513
2585
|
}
|
|
2514
2586
|
/**
|
|
2515
2587
|
* Attach the signed-in user so reports say who hit the bug.
|
|
@@ -2526,7 +2598,7 @@ class ht {
|
|
|
2526
2598
|
* Pass null to forget them again on sign-out.
|
|
2527
2599
|
*/
|
|
2528
2600
|
identify(e) {
|
|
2529
|
-
const n =
|
|
2601
|
+
const n = Le(e, (i) => this.warn(i));
|
|
2530
2602
|
return e != null && !n ? this : (this.config.user = n, this.debugLog("identify", n), this);
|
|
2531
2603
|
}
|
|
2532
2604
|
/**
|
|
@@ -2543,7 +2615,7 @@ class ht {
|
|
|
2543
2615
|
* outrank the same field on identify(); anything else is readable metadata.
|
|
2544
2616
|
*/
|
|
2545
2617
|
setContext(e) {
|
|
2546
|
-
return this.context =
|
|
2618
|
+
return this.context = se(this.context, e, (n) => this.warn(n)), this.debugLog("context", this.context), this;
|
|
2547
2619
|
}
|
|
2548
2620
|
/** What setContext() currently holds (a copy). */
|
|
2549
2621
|
getContext() {
|
|
@@ -2553,11 +2625,16 @@ class ht {
|
|
|
2553
2625
|
* Open the report panel, as if the floating button had been pressed — for a
|
|
2554
2626
|
* "Report a problem" item in your own menu.
|
|
2555
2627
|
*
|
|
2556
|
-
*
|
|
2557
|
-
*
|
|
2628
|
+
* BugCatch.open(); // the report form
|
|
2629
|
+
* BugCatch.open({ mode: 'feedback' }); // straight to "Give feedback"
|
|
2630
|
+
*
|
|
2631
|
+
* Feedback opens only where this project takes it; otherwise the report form
|
|
2632
|
+
* does. An open panel moves to the mode asked for. Needs the built-in widget
|
|
2633
|
+
* (`widget: true`, the default). With `widget: false` there is no panel to
|
|
2634
|
+
* open: draw your own form and call report() or feedback().
|
|
2558
2635
|
*/
|
|
2559
|
-
open() {
|
|
2560
|
-
return this.started ? this.widgetControls ? (this.widgetControls.open(), this) : (this.warn("open() needs the built-in widget; it was turned off with widget: false."), this) : (this.warn("open() was called before init() — nothing to open yet."), this);
|
|
2636
|
+
open({ mode: e } = {}) {
|
|
2637
|
+
return this.started ? this.widgetControls ? (e !== void 0 && e !== "report" && e !== "feedback" && (this.warn(`open({ mode: "${e}" }) is not 'report' or 'feedback' — opened the report form.`), e = "report"), this.widgetControls.open(e), this) : (this.warn("open() needs the built-in widget; it was turned off with widget: false."), this) : (this.warn("open() was called before init() — nothing to open yet."), this);
|
|
2561
2638
|
}
|
|
2562
2639
|
/** Close the report panel if it is open. */
|
|
2563
2640
|
close() {
|
|
@@ -2598,17 +2675,17 @@ class ht {
|
|
|
2598
2675
|
context: s = null,
|
|
2599
2676
|
issue: c = null
|
|
2600
2677
|
} = {}) {
|
|
2601
|
-
var
|
|
2678
|
+
var S, E, $, g, k, v, w, C;
|
|
2602
2679
|
if (!this.started) throw new Error("[BugCatch] call init() first.");
|
|
2603
2680
|
if (typeof e != "string" || !e.trim()) throw new Error("[BugCatch] a title is required.");
|
|
2604
2681
|
["LOW", "MEDIUM", "HIGH", "CRITICAL"].includes(String(i).toUpperCase()) || (this.warn(`priority "${i}" is not one of LOW, MEDIUM, HIGH, CRITICAL — sent as MEDIUM.`), i = "MEDIUM");
|
|
2605
|
-
const l = (o || []).filter((
|
|
2606
|
-
type:
|
|
2607
|
-
storageKey:
|
|
2608
|
-
mime:
|
|
2609
|
-
})), h = (Array.isArray(a) ? a : []).filter((
|
|
2682
|
+
const l = (o || []).filter((m) => (m == null ? void 0 : m.storageKey) && le(m.mime, Te)).map((m) => ({
|
|
2683
|
+
type: m.type === "VIDEO" ? "VIDEO" : "SCREENSHOT",
|
|
2684
|
+
storageKey: m.storageKey,
|
|
2685
|
+
mime: le(m.mime, Te)
|
|
2686
|
+
})), h = (Array.isArray(a) ? a : []).filter((m) => m && typeof m.key == "string" && m.key && (typeof m.value == "string" || typeof m.value == "number")).map((m) => ({ key: m.key.slice(0, 64), value: String(m.value).trim().slice(0, 120) })).filter((m) => m.value);
|
|
2610
2687
|
Array.isArray(a) && h.length < a.length && this.warn("report({ references }) takes [{ key, value }] with string values; malformed entries were dropped.");
|
|
2611
|
-
let f = await x(this,
|
|
2688
|
+
let f = await x(this, p, W).call(this, {
|
|
2612
2689
|
title: e.trim(),
|
|
2613
2690
|
description: typeof n == "string" ? n : String(n ?? ""),
|
|
2614
2691
|
priority: String(i).toUpperCase(),
|
|
@@ -2618,20 +2695,20 @@ class ht {
|
|
|
2618
2695
|
context: s,
|
|
2619
2696
|
issue: typeof c == "string" && c ? c.slice(0, 32) : null
|
|
2620
2697
|
});
|
|
2621
|
-
const
|
|
2622
|
-
if (
|
|
2623
|
-
f =
|
|
2698
|
+
const u = x(this, p, J).call(this, f, { type: "report" });
|
|
2699
|
+
if (u === !1) return { cancelled: !0 };
|
|
2700
|
+
f = u, this.debugLog("sending report", {
|
|
2624
2701
|
title: f.title,
|
|
2625
|
-
user: (
|
|
2626
|
-
context: (
|
|
2702
|
+
user: (S = f.metadata) == null ? void 0 : S.user,
|
|
2703
|
+
context: (E = f.metadata) == null ? void 0 : E.context,
|
|
2627
2704
|
references: f.references,
|
|
2628
|
-
console: (k = (
|
|
2629
|
-
network: (
|
|
2705
|
+
console: (k = (g = ($ = f.logs) == null ? void 0 : $.console) == null ? void 0 : g.entries) == null ? void 0 : k.length,
|
|
2706
|
+
network: (C = (w = (v = f.logs) == null ? void 0 : v.network) == null ? void 0 : w.entries) == null ? void 0 : C.length
|
|
2630
2707
|
});
|
|
2631
|
-
const
|
|
2632
|
-
let
|
|
2708
|
+
const d = M(this.config.projectId);
|
|
2709
|
+
let b;
|
|
2633
2710
|
try {
|
|
2634
|
-
|
|
2711
|
+
b = await fetch(`${this.config.apiBase}/ingest/bugs`, {
|
|
2635
2712
|
method: "POST",
|
|
2636
2713
|
headers: {
|
|
2637
2714
|
"Content-Type": "application/json",
|
|
@@ -2640,27 +2717,27 @@ class ht {
|
|
|
2640
2717
|
// address from here rather than from the payload when it is — on a
|
|
2641
2718
|
// project that requires sign-in, letting the page name a different
|
|
2642
2719
|
// reporter would undo the requirement.
|
|
2643
|
-
...
|
|
2720
|
+
...d != null && d.token ? { "X-BugCatch-Session": d.token } : {}
|
|
2644
2721
|
},
|
|
2645
|
-
body: JSON.stringify(
|
|
2722
|
+
body: JSON.stringify(mi(f))
|
|
2646
2723
|
});
|
|
2647
|
-
} catch (
|
|
2648
|
-
const
|
|
2649
|
-
throw
|
|
2724
|
+
} catch (m) {
|
|
2725
|
+
const B = new Error(`[BugCatch] could not reach ${this.config.apiBase} — check apiBase, and that this site's origin is allowed by the API.`);
|
|
2726
|
+
throw B.cause = m, x(this, p, _).call(this, "report", B), B;
|
|
2650
2727
|
}
|
|
2651
|
-
if (
|
|
2652
|
-
let
|
|
2728
|
+
if (b.status === 401 && d && ue(this.config.projectId), !b.ok) {
|
|
2729
|
+
let m = "";
|
|
2653
2730
|
try {
|
|
2654
|
-
const A = await
|
|
2655
|
-
|
|
2731
|
+
const A = await b.json();
|
|
2732
|
+
m = Array.isArray(A.message) ? A.message.join(", ") : A.message || "";
|
|
2656
2733
|
} catch {
|
|
2657
2734
|
}
|
|
2658
|
-
|
|
2659
|
-
const
|
|
2660
|
-
throw
|
|
2735
|
+
b.status === 401 && !d && (m || (m = "the apiKey was not accepted")), b.status === 403 && (m || (m = "the apiKey is not allowed to report to this projectId"));
|
|
2736
|
+
const B = b.status === 429 ? new Error(`[BugCatch] ${K(m)}`) : new Error(`[BugCatch] report failed (HTTP ${b.status})${m ? ": " + m : ""}`);
|
|
2737
|
+
throw B.status = b.status, x(this, p, _).call(this, "report", B), B;
|
|
2661
2738
|
}
|
|
2662
|
-
const
|
|
2663
|
-
return x(this,
|
|
2739
|
+
const y = await b.json();
|
|
2740
|
+
return x(this, p, pe).call(this, y, { title: f.title ?? e.trim(), via: "form" }), y.watchToken && (de(y.watchToken), this.config.updates && this.startWatching()), y;
|
|
2664
2741
|
}
|
|
2665
2742
|
/**
|
|
2666
2743
|
* What this project asks of the person reporting, and who this browser is
|
|
@@ -2702,7 +2779,7 @@ class ht {
|
|
|
2702
2779
|
* whether that form should have an identifier box on it.
|
|
2703
2780
|
*/
|
|
2704
2781
|
referenceFields() {
|
|
2705
|
-
return this.refFields ? this.refFields : (this.refFields =
|
|
2782
|
+
return this.refFields ? this.refFields : (this.refFields = Pn({
|
|
2706
2783
|
apiBase: this.config.apiBase,
|
|
2707
2784
|
apiKey: this.config.apiKey,
|
|
2708
2785
|
projectId: this.config.projectId
|
|
@@ -2745,12 +2822,12 @@ class ht {
|
|
|
2745
2822
|
* `widget: false` or `announcements: false`. Empty on every failure.
|
|
2746
2823
|
*/
|
|
2747
2824
|
async announcements() {
|
|
2748
|
-
const e = await
|
|
2825
|
+
const e = await Xn({
|
|
2749
2826
|
apiBase: this.config.apiBase,
|
|
2750
2827
|
apiKey: this.config.apiKey,
|
|
2751
2828
|
projectId: this.config.projectId
|
|
2752
2829
|
});
|
|
2753
|
-
return
|
|
2830
|
+
return qn(e);
|
|
2754
2831
|
}
|
|
2755
2832
|
/**
|
|
2756
2833
|
* Stop showing an announcement in this browser, until the team uses "Show it
|
|
@@ -2760,6 +2837,82 @@ class ht {
|
|
|
2760
2837
|
dismissAnnouncement(e) {
|
|
2761
2838
|
Wn(e);
|
|
2762
2839
|
}
|
|
2840
|
+
/**
|
|
2841
|
+
* Whether this project takes feedback from the widget — the answer that
|
|
2842
|
+
* decides whether "Give feedback" is drawn.
|
|
2843
|
+
*
|
|
2844
|
+
* if (await BugCatch.feedbackEnabled()) showMyFeedbackButton();
|
|
2845
|
+
*
|
|
2846
|
+
* Switched on and off on the project's settings page, not here. Asked once
|
|
2847
|
+
* per page and kept; false on any failure.
|
|
2848
|
+
*/
|
|
2849
|
+
feedbackEnabled() {
|
|
2850
|
+
return this.feedbackState ? this.feedbackState : (this.feedbackState = ii({
|
|
2851
|
+
apiBase: this.config.apiBase,
|
|
2852
|
+
apiKey: this.config.apiKey,
|
|
2853
|
+
projectId: this.config.projectId
|
|
2854
|
+
}), this.feedbackState);
|
|
2855
|
+
}
|
|
2856
|
+
/**
|
|
2857
|
+
* Send feedback — an idea, praise, something that confused them — to this
|
|
2858
|
+
* project's team. Not a bug: it is not triaged, assigned or answered in the
|
|
2859
|
+
* widget; it lands on the dashboard's Feedback page.
|
|
2860
|
+
*
|
|
2861
|
+
* await BugCatch.feedback({
|
|
2862
|
+
* message: 'Export to CSV would save me an hour a week',
|
|
2863
|
+
* kind: 'idea', // 'idea' | 'praise' | 'confusing' | 'other' (optional)
|
|
2864
|
+
* score: 4, // 1 (terrible) – 5 (great), how it feels so far (optional)
|
|
2865
|
+
* email: 'jo@acme.com', // only if they want a reply; identify()'s is used otherwise
|
|
2866
|
+
* });
|
|
2867
|
+
* // → { id }
|
|
2868
|
+
*
|
|
2869
|
+
* Sent with the page and browser details, who identify() says they are and
|
|
2870
|
+
* the setContext() context — never the console or network logs, which say
|
|
2871
|
+
* nothing about an opinion. Goes through beforeSend, whose second argument is
|
|
2872
|
+
* `{ type: 'feedback' }`. Rejects with a message fit to show the person.
|
|
2873
|
+
*/
|
|
2874
|
+
async feedback({ message: e, kind: n, score: i, email: r, name: o, context: a = null } = {}) {
|
|
2875
|
+
var f, u, d, b;
|
|
2876
|
+
if (!this.started) throw new Error("[BugCatch] call init() first.");
|
|
2877
|
+
const s = oi({
|
|
2878
|
+
message: e,
|
|
2879
|
+
kind: n,
|
|
2880
|
+
score: i,
|
|
2881
|
+
// What they typed wins: it is the address they asked to be answered at.
|
|
2882
|
+
email: r ?? ((f = this.config.user) == null ? void 0 : f.email),
|
|
2883
|
+
name: o ?? ((u = this.config.user) == null ? void 0 : u.name)
|
|
2884
|
+
});
|
|
2885
|
+
n != null && !s.kind && this.warn(`feedback({ kind: "${n}" }) is not one of idea, praise, confusing, other — sent without one.`);
|
|
2886
|
+
const c = a ? se(this.context, a, (y) => this.warn(y.replace("setContext()", "feedback({ context })"))) : this.context;
|
|
2887
|
+
let l = {
|
|
2888
|
+
projectId: this.config.projectId,
|
|
2889
|
+
...s,
|
|
2890
|
+
url: window.location.href,
|
|
2891
|
+
metadata: {
|
|
2892
|
+
...await ae(),
|
|
2893
|
+
release: this.config.release,
|
|
2894
|
+
environment: this.config.environment,
|
|
2895
|
+
buildId: this.config.buildId,
|
|
2896
|
+
user: this.config.user || void 0,
|
|
2897
|
+
...Object.keys(c).length ? { context: c } : {},
|
|
2898
|
+
sdk: U
|
|
2899
|
+
}
|
|
2900
|
+
};
|
|
2901
|
+
const h = x(this, p, J).call(this, l, { type: "feedback" });
|
|
2902
|
+
if (h === !1) return { cancelled: !0 };
|
|
2903
|
+
l = h, this.debugLog("sending feedback", { kind: l.kind, score: l.score, user: (d = l.metadata) == null ? void 0 : d.user });
|
|
2904
|
+
try {
|
|
2905
|
+
const y = await ri({
|
|
2906
|
+
apiBase: this.config.apiBase,
|
|
2907
|
+
apiKey: this.config.apiKey,
|
|
2908
|
+
token: (b = M(this.config.projectId)) == null ? void 0 : b.token,
|
|
2909
|
+
payload: l
|
|
2910
|
+
}), S = { id: (y == null ? void 0 : y.id) ?? null, kind: l.kind ?? null, score: l.score ?? null };
|
|
2911
|
+
return this.debugLog("feedback accepted", S), this.emit("feedback", S), y;
|
|
2912
|
+
} catch (y) {
|
|
2913
|
+
throw x(this, p, _).call(this, "feedback", y), y;
|
|
2914
|
+
}
|
|
2915
|
+
}
|
|
2763
2916
|
/**
|
|
2764
2917
|
* Who this browser is signed in as on this project, from storage alone.
|
|
2765
2918
|
*
|
|
@@ -2840,7 +2993,7 @@ class ht {
|
|
|
2840
2993
|
*/
|
|
2841
2994
|
knownIssues() {
|
|
2842
2995
|
var e;
|
|
2843
|
-
return
|
|
2996
|
+
return Cn({
|
|
2844
2997
|
apiBase: this.config.apiBase,
|
|
2845
2998
|
apiKey: this.config.apiKey,
|
|
2846
2999
|
projectId: this.config.projectId,
|
|
@@ -2855,7 +3008,7 @@ class ht {
|
|
|
2855
3008
|
*/
|
|
2856
3009
|
matchKnownIssues(e, { signal: n } = {}) {
|
|
2857
3010
|
var i;
|
|
2858
|
-
return
|
|
3011
|
+
return In({
|
|
2859
3012
|
apiBase: this.config.apiBase,
|
|
2860
3013
|
apiKey: this.config.apiKey,
|
|
2861
3014
|
projectId: this.config.projectId,
|
|
@@ -2879,7 +3032,7 @@ class ht {
|
|
|
2879
3032
|
*/
|
|
2880
3033
|
async meToo(e, { email: n, name: i } = {}) {
|
|
2881
3034
|
var a, s;
|
|
2882
|
-
const r = M(this.config.projectId), o = await
|
|
3035
|
+
const r = M(this.config.projectId), o = await ae();
|
|
2883
3036
|
return Sn({
|
|
2884
3037
|
apiBase: this.config.apiBase,
|
|
2885
3038
|
apiKey: this.config.apiKey,
|
|
@@ -2891,7 +3044,7 @@ class ht {
|
|
|
2891
3044
|
...o,
|
|
2892
3045
|
user: this.config.user || void 0,
|
|
2893
3046
|
...Object.keys(this.context).length ? { context: this.context } : {},
|
|
2894
|
-
sdk:
|
|
3047
|
+
sdk: U
|
|
2895
3048
|
},
|
|
2896
3049
|
logs: {
|
|
2897
3050
|
console: { entries: this.consoleBuffer.all() },
|
|
@@ -2923,8 +3076,8 @@ class ht {
|
|
|
2923
3076
|
}), this.teardown = [], this.notifier = null, this.started = !1;
|
|
2924
3077
|
}
|
|
2925
3078
|
}
|
|
2926
|
-
|
|
2927
|
-
|
|
3079
|
+
p = new WeakSet(), /** Call a host callback without letting it break the SDK. */
|
|
3080
|
+
q = function(e, n) {
|
|
2928
3081
|
const i = this.config[e];
|
|
2929
3082
|
if (typeof i == "function")
|
|
2930
3083
|
try {
|
|
@@ -2960,7 +3113,7 @@ ft = function() {
|
|
|
2960
3113
|
headers: { "Content-Type": "application/json", "X-BugCatch-Key": this.config.apiKey },
|
|
2961
3114
|
body: JSON.stringify({
|
|
2962
3115
|
projectId: this.config.projectId,
|
|
2963
|
-
version:
|
|
3116
|
+
version: U.version,
|
|
2964
3117
|
identify: !!this.config.user,
|
|
2965
3118
|
context: !!(this.context && Object.keys(this.context).length),
|
|
2966
3119
|
widget: !!this.config.widget,
|
|
@@ -2978,8 +3131,8 @@ ft = function() {
|
|
|
2978
3131
|
* here, so the cards on screen and a host app's own badge cannot disagree
|
|
2979
3132
|
* about what is outstanding.
|
|
2980
3133
|
*/
|
|
2981
|
-
|
|
2982
|
-
const e =
|
|
3134
|
+
L = function() {
|
|
3135
|
+
const e = z();
|
|
2983
3136
|
if (this.emit("unread", { count: e.length, updates: e }), !!this.config.updateToast) {
|
|
2984
3137
|
if (!this.notifier) {
|
|
2985
3138
|
if (!e.length) return;
|
|
@@ -3015,18 +3168,18 @@ pt = function(e, n) {
|
|
|
3015
3168
|
if (!e || typeof i != "string" || this.phases.get(e) === i) return;
|
|
3016
3169
|
this.phases.set(e, i);
|
|
3017
3170
|
const r = { bugId: e, phase: i, title: n.title ?? null, detail: n.detail ?? null };
|
|
3018
|
-
this.debugLog("assistant", r), x(this,
|
|
3171
|
+
this.debugLog("assistant", r), x(this, p, q).call(this, "onAssistantPhase", r), this.emit("assistant", r);
|
|
3019
3172
|
}, /** A report was accepted: tell the host app, however it was filed. */
|
|
3020
|
-
|
|
3173
|
+
pe = function(e, { title: n, via: i }) {
|
|
3021
3174
|
if (!(e != null && e.id)) return;
|
|
3022
3175
|
const r = { bugId: e.id, title: n ?? null, via: i, result: e };
|
|
3023
|
-
this.debugLog("report accepted", r), x(this,
|
|
3176
|
+
this.debugLog("report accepted", r), x(this, p, q).call(this, "onReportSubmitted", r), this.emit("report", r);
|
|
3024
3177
|
}, /** Something done on the page's behalf failed. */
|
|
3025
|
-
|
|
3026
|
-
x(this,
|
|
3178
|
+
_ = function(e, n) {
|
|
3179
|
+
x(this, p, q).call(this, "onError", { action: e, error: n }), this.emit("error", { action: e, error: n });
|
|
3027
3180
|
}, W = async function({ title: e, description: n = "", priority: i = "MEDIUM", metadata: r = {}, media: o = [], references: a = [], context: s = null, issue: c = null }) {
|
|
3028
3181
|
var h, f;
|
|
3029
|
-
const l = s ?
|
|
3182
|
+
const l = s ? se(this.context, s, (u) => this.warn(u.replace("setContext()", "report({ context })"))) : this.context;
|
|
3030
3183
|
return {
|
|
3031
3184
|
projectId: this.config.projectId,
|
|
3032
3185
|
...e ? { title: e } : {},
|
|
@@ -3038,7 +3191,7 @@ X = function(e, n) {
|
|
|
3038
3191
|
// than a mailbox, and so the resolution email can open with their name.
|
|
3039
3192
|
reporterName: (f = this.config.user) == null ? void 0 : f.name,
|
|
3040
3193
|
metadata: {
|
|
3041
|
-
...await
|
|
3194
|
+
...await ae(),
|
|
3042
3195
|
release: this.config.release,
|
|
3043
3196
|
environment: this.config.environment,
|
|
3044
3197
|
buildId: this.config.buildId,
|
|
@@ -3050,7 +3203,7 @@ X = function(e, n) {
|
|
|
3050
3203
|
// The screen the report came from — setContext(). Its identifiers
|
|
3051
3204
|
// outrank the same kind on `user`.
|
|
3052
3205
|
...Object.keys(l).length ? { context: l } : {},
|
|
3053
|
-
sdk:
|
|
3206
|
+
sdk: U
|
|
3054
3207
|
},
|
|
3055
3208
|
logs: {
|
|
3056
3209
|
console: { entries: this.consoleBuffer.all() },
|
|
@@ -3089,17 +3242,17 @@ X = function(e, n) {
|
|
|
3089
3242
|
*
|
|
3090
3243
|
* Returns the payload to send, or false when the host cancelled.
|
|
3091
3244
|
*/
|
|
3092
|
-
|
|
3245
|
+
J = function(e, n = { type: "report" }) {
|
|
3093
3246
|
if (typeof this.config.beforeSend != "function") return e;
|
|
3094
|
-
let
|
|
3247
|
+
let i;
|
|
3095
3248
|
try {
|
|
3096
|
-
|
|
3097
|
-
} catch (
|
|
3098
|
-
return this.warn(`beforeSend threw, so nothing was sent: ${(
|
|
3249
|
+
i = this.config.beforeSend(e, n);
|
|
3250
|
+
} catch (r) {
|
|
3251
|
+
return this.warn(`beforeSend threw, so nothing was sent: ${(r == null ? void 0 : r.message) || r}`), !1;
|
|
3099
3252
|
}
|
|
3100
|
-
return
|
|
3253
|
+
return i === !1 ? !1 : i && typeof i == "object" ? i : e;
|
|
3101
3254
|
}, gt = async function() {
|
|
3102
|
-
const e = M(this.config.projectId), n = x(this,
|
|
3255
|
+
const e = M(this.config.projectId), n = x(this, p, J).call(this, await x(this, p, W).call(this, {}));
|
|
3103
3256
|
if (n === !1)
|
|
3104
3257
|
return this.debugLog("call cancelled by beforeSend"), { cancelled: !0 };
|
|
3105
3258
|
let i;
|
|
@@ -3111,14 +3264,14 @@ he = function(e) {
|
|
|
3111
3264
|
payload: n,
|
|
3112
3265
|
// See report(): the token this browser holds, so the one that comes
|
|
3113
3266
|
// back still covers what it covered.
|
|
3114
|
-
watchToken:
|
|
3267
|
+
watchToken: T()
|
|
3115
3268
|
});
|
|
3116
3269
|
} catch (r) {
|
|
3117
|
-
throw r.status === 401 && e &&
|
|
3270
|
+
throw r.status === 401 && e && ue(this.config.projectId), x(this, p, _).call(this, "call", r), r;
|
|
3118
3271
|
}
|
|
3119
|
-
return x(this,
|
|
3272
|
+
return x(this, p, pe).call(this, i, { title: null, via: "call" }), i.watchToken && (de(i.watchToken), this.config.updates && this.startWatching()), i;
|
|
3120
3273
|
}, mt = async function(e) {
|
|
3121
|
-
const { joinLiveCall: n, liveCallSupported: i, openMicrophone: r } = await
|
|
3274
|
+
const { joinLiveCall: n, liveCallSupported: i, openMicrophone: r } = await X(this.config.chunkBase);
|
|
3122
3275
|
if (!i())
|
|
3123
3276
|
throw new Error("[BugCatch] this browser cannot make live calls.");
|
|
3124
3277
|
const o = await r();
|
|
@@ -3126,7 +3279,7 @@ he = function(e) {
|
|
|
3126
3279
|
try {
|
|
3127
3280
|
if (e)
|
|
3128
3281
|
a = await fn({ apiBase: this.config.apiBase, bugId: e });
|
|
3129
|
-
else if (s = await x(this,
|
|
3282
|
+
else if (s = await x(this, p, gt).call(this), e = s.id, a = s.live_call, !(a != null && a.realtime_url)) {
|
|
3130
3283
|
const l = new Error(`[BugCatch] the report was filed, but the team could not be rung${s.call_error ? `: ${s.call_error}` : "."}`);
|
|
3131
3284
|
throw l.filed = s, l.reason = s.call_error || null, l;
|
|
3132
3285
|
}
|
|
@@ -3168,10 +3321,10 @@ wt = function(e) {
|
|
|
3168
3321
|
var r;
|
|
3169
3322
|
const n = e.incomingCall;
|
|
3170
3323
|
if (!this.config.voice || ((r = this.ringing) == null ? void 0 : r.callId) === n.callId || this.call || this.callStarting) return;
|
|
3171
|
-
x(this,
|
|
3324
|
+
x(this, p, Y).call(this);
|
|
3172
3325
|
const i = { callId: n.callId, dismiss: () => {
|
|
3173
3326
|
} };
|
|
3174
|
-
this.ringing = i,
|
|
3327
|
+
this.ringing = i, X(this.config.chunkBase).then(({ liveCallSupported: o, showIncomingCall: a }) => {
|
|
3175
3328
|
if (this.ringing !== i || (this.ringing = null, !o()) || this.call || this.callStarting) return;
|
|
3176
3329
|
const s = a({
|
|
3177
3330
|
call: n,
|
|
@@ -3181,10 +3334,10 @@ wt = function(e) {
|
|
|
3181
3334
|
// out loud — tracked since load, which the card's own code cannot be.
|
|
3182
3335
|
touched: Ln,
|
|
3183
3336
|
onAnswer: () => {
|
|
3184
|
-
x(this,
|
|
3337
|
+
x(this, p, yt).call(this, e.bugId, n);
|
|
3185
3338
|
},
|
|
3186
3339
|
onDecline: () => {
|
|
3187
|
-
this.ringing = null,
|
|
3340
|
+
this.ringing = null, Oe({
|
|
3188
3341
|
apiBase: this.config.apiBase,
|
|
3189
3342
|
bugId: e.bugId,
|
|
3190
3343
|
callId: n.callId
|
|
@@ -3208,7 +3361,7 @@ wt = function(e) {
|
|
|
3208
3361
|
this.ringing === i && (this.ringing = null);
|
|
3209
3362
|
});
|
|
3210
3363
|
}, /** Take the card away, whatever it is showing. */
|
|
3211
|
-
|
|
3364
|
+
Y = function(e) {
|
|
3212
3365
|
if (this.ringing && !(e && this.ringing.callId !== e)) {
|
|
3213
3366
|
try {
|
|
3214
3367
|
this.ringing.dismiss();
|
|
@@ -3221,10 +3374,10 @@ J = function(e) {
|
|
|
3221
3374
|
this.callStarting = !0;
|
|
3222
3375
|
let i, r;
|
|
3223
3376
|
try {
|
|
3224
|
-
const a = await
|
|
3377
|
+
const a = await X(this.config.chunkBase);
|
|
3225
3378
|
r = a.joinLiveCall, i = await a.openMicrophone();
|
|
3226
3379
|
} catch (a) {
|
|
3227
|
-
this.callStarting = !1,
|
|
3380
|
+
this.callStarting = !1, Oe({ apiBase: this.config.apiBase, bugId: e, callId: n.callId }), this.emit("incoming-call", { bugId: e, callId: n.callId, state: "failed", error: a });
|
|
3228
3381
|
return;
|
|
3229
3382
|
}
|
|
3230
3383
|
let o;
|
|
@@ -3260,33 +3413,35 @@ J = function(e) {
|
|
|
3260
3413
|
};
|
|
3261
3414
|
const bt = new ht();
|
|
3262
3415
|
bt.Client = ht;
|
|
3263
|
-
bt.version =
|
|
3416
|
+
bt.version = U.version;
|
|
3264
3417
|
export {
|
|
3265
3418
|
bt as B,
|
|
3419
|
+
ei as F,
|
|
3266
3420
|
Je as I,
|
|
3267
|
-
|
|
3268
|
-
|
|
3269
|
-
|
|
3421
|
+
ni as M,
|
|
3422
|
+
ce as P,
|
|
3423
|
+
Te as R,
|
|
3424
|
+
$i as S,
|
|
3270
3425
|
Zt as U,
|
|
3271
3426
|
Kt as a,
|
|
3272
|
-
|
|
3273
|
-
|
|
3274
|
-
|
|
3275
|
-
|
|
3276
|
-
|
|
3277
|
-
|
|
3278
|
-
|
|
3427
|
+
ki as b,
|
|
3428
|
+
Fe as c,
|
|
3429
|
+
xi as d,
|
|
3430
|
+
vi as e,
|
|
3431
|
+
Ci as f,
|
|
3432
|
+
Bi as g,
|
|
3433
|
+
Si as h,
|
|
3279
3434
|
ze as i,
|
|
3280
3435
|
Nt as j,
|
|
3281
|
-
|
|
3282
|
-
|
|
3436
|
+
Pt as k,
|
|
3437
|
+
bi as l,
|
|
3283
3438
|
Lt as m,
|
|
3284
|
-
|
|
3285
|
-
|
|
3286
|
-
|
|
3439
|
+
le as n,
|
|
3440
|
+
Ii as o,
|
|
3441
|
+
yi as p,
|
|
3287
3442
|
Ye as q,
|
|
3288
|
-
|
|
3443
|
+
Ei as r,
|
|
3289
3444
|
Rt as s,
|
|
3290
|
-
|
|
3445
|
+
Dn as v
|
|
3291
3446
|
};
|
|
3292
3447
|
//# sourceMappingURL=bugcatch-core.es.js.map
|