glitchgrab 1.20.1 → 1.22.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +177 -95
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +177 -95
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -90,7 +90,10 @@ function interceptFetch() {
|
|
|
90
90
|
const method = (_a = init == null ? void 0 : init.method) != null ? _a : "GET";
|
|
91
91
|
const start = Date.now();
|
|
92
92
|
try {
|
|
93
|
-
const response = await origFetch
|
|
93
|
+
const response = await origFetch(
|
|
94
|
+
input,
|
|
95
|
+
init
|
|
96
|
+
);
|
|
94
97
|
addBreadcrumb("api", `${method} ${url.slice(0, 100)} \u2192 ${response.status}`, {
|
|
95
98
|
method,
|
|
96
99
|
status: String(response.status),
|
|
@@ -222,7 +225,7 @@ function captureContext(visitedPages) {
|
|
|
222
225
|
};
|
|
223
226
|
}
|
|
224
227
|
}
|
|
225
|
-
var DEFAULT_BASE_URL = "https://
|
|
228
|
+
var DEFAULT_BASE_URL = "https://glitchgrab.dev";
|
|
226
229
|
var MAX_RETRIES = 3;
|
|
227
230
|
var RETRY_BASE_MS = 500;
|
|
228
231
|
async function sendReport(payload, baseUrl) {
|
|
@@ -569,6 +572,7 @@ function ReportDialog({
|
|
|
569
572
|
showSeverity = true
|
|
570
573
|
}) {
|
|
571
574
|
const [isEnhancing, setIsEnhancing] = useState(false);
|
|
575
|
+
const [screenshotDragOver, setScreenshotDragOver] = useState(false);
|
|
572
576
|
const [mounted, setMounted] = useState(false);
|
|
573
577
|
useEffect(() => {
|
|
574
578
|
setMounted(true);
|
|
@@ -987,6 +991,144 @@ function ReportDialog({
|
|
|
987
991
|
}
|
|
988
992
|
)
|
|
989
993
|
] }),
|
|
994
|
+
/* @__PURE__ */ jsxs("div", { style: { marginTop: "10px" }, children: [
|
|
995
|
+
/* @__PURE__ */ jsx("span", { style: { fontSize: "12px", color: t.textMuted, marginBottom: "6px", display: "block", fontWeight: 500 }, children: "Screenshot" }),
|
|
996
|
+
screenshot ? /* @__PURE__ */ jsxs("div", { children: [
|
|
997
|
+
/* @__PURE__ */ jsxs("div", { style: { position: "relative" }, children: [
|
|
998
|
+
/* @__PURE__ */ jsx(
|
|
999
|
+
"img",
|
|
1000
|
+
{
|
|
1001
|
+
src: screenshot,
|
|
1002
|
+
alt: "Page screenshot",
|
|
1003
|
+
onClick: () => setPreviewOpen(true),
|
|
1004
|
+
style: {
|
|
1005
|
+
width: "100%",
|
|
1006
|
+
borderRadius: "6px",
|
|
1007
|
+
border: `1px solid ${t.border}`,
|
|
1008
|
+
maxHeight: "64px",
|
|
1009
|
+
objectFit: "cover",
|
|
1010
|
+
objectPosition: "top",
|
|
1011
|
+
cursor: "zoom-in",
|
|
1012
|
+
display: "block"
|
|
1013
|
+
}
|
|
1014
|
+
}
|
|
1015
|
+
),
|
|
1016
|
+
/* @__PURE__ */ jsx("span", { style: {
|
|
1017
|
+
position: "absolute",
|
|
1018
|
+
bottom: "5px",
|
|
1019
|
+
left: "6px",
|
|
1020
|
+
background: "rgba(0,0,0,0.55)",
|
|
1021
|
+
color: "#fff",
|
|
1022
|
+
fontSize: "10px",
|
|
1023
|
+
padding: "1px 5px",
|
|
1024
|
+
borderRadius: "3px",
|
|
1025
|
+
pointerEvents: "none"
|
|
1026
|
+
}, children: "click to preview" })
|
|
1027
|
+
] }),
|
|
1028
|
+
/* @__PURE__ */ jsxs("div", { style: { display: "flex", gap: "6px", marginTop: "6px" }, children: [
|
|
1029
|
+
/* @__PURE__ */ jsxs(
|
|
1030
|
+
"button",
|
|
1031
|
+
{
|
|
1032
|
+
type: "button",
|
|
1033
|
+
onClick: () => setScreenshot(null),
|
|
1034
|
+
style: {
|
|
1035
|
+
flex: 1,
|
|
1036
|
+
padding: "6px 0",
|
|
1037
|
+
borderRadius: "6px",
|
|
1038
|
+
border: `1px solid ${t.inputBorder}`,
|
|
1039
|
+
background: "transparent",
|
|
1040
|
+
color: "#ef4444",
|
|
1041
|
+
fontSize: "12px",
|
|
1042
|
+
fontWeight: 500,
|
|
1043
|
+
cursor: "pointer",
|
|
1044
|
+
fontFamily: "inherit",
|
|
1045
|
+
display: "flex",
|
|
1046
|
+
alignItems: "center",
|
|
1047
|
+
justifyContent: "center",
|
|
1048
|
+
gap: "4px"
|
|
1049
|
+
},
|
|
1050
|
+
children: [
|
|
1051
|
+
/* @__PURE__ */ jsx("svg", { width: "11", height: "11", viewBox: "0 0 10 10", fill: "none", children: /* @__PURE__ */ jsx("path", { d: "M1 1L9 9M9 1L1 9", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round" }) }),
|
|
1052
|
+
"Remove"
|
|
1053
|
+
]
|
|
1054
|
+
}
|
|
1055
|
+
),
|
|
1056
|
+
/* @__PURE__ */ jsxs(
|
|
1057
|
+
"button",
|
|
1058
|
+
{
|
|
1059
|
+
type: "button",
|
|
1060
|
+
onClick: () => {
|
|
1061
|
+
var _a;
|
|
1062
|
+
return (_a = fileInputRef.current) == null ? void 0 : _a.click();
|
|
1063
|
+
},
|
|
1064
|
+
style: {
|
|
1065
|
+
flex: 1,
|
|
1066
|
+
padding: "6px 0",
|
|
1067
|
+
borderRadius: "6px",
|
|
1068
|
+
border: `1px solid ${t.inputBorder}`,
|
|
1069
|
+
background: "transparent",
|
|
1070
|
+
color: t.textMuted,
|
|
1071
|
+
fontSize: "12px",
|
|
1072
|
+
fontWeight: 500,
|
|
1073
|
+
cursor: "pointer",
|
|
1074
|
+
fontFamily: "inherit",
|
|
1075
|
+
display: "flex",
|
|
1076
|
+
alignItems: "center",
|
|
1077
|
+
justifyContent: "center",
|
|
1078
|
+
gap: "4px"
|
|
1079
|
+
},
|
|
1080
|
+
children: [
|
|
1081
|
+
/* @__PURE__ */ jsx("svg", { width: "11", height: "11", viewBox: "0 0 24 24", fill: "none", children: /* @__PURE__ */ jsx("path", { d: "M21 15v4a2 2 0 01-2 2H5a2 2 0 01-2-2v-4M17 8l-5-5-5 5M12 3v12", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }) }),
|
|
1082
|
+
"Replace"
|
|
1083
|
+
]
|
|
1084
|
+
}
|
|
1085
|
+
)
|
|
1086
|
+
] })
|
|
1087
|
+
] }) : (
|
|
1088
|
+
/* Drop zone */
|
|
1089
|
+
/* @__PURE__ */ jsxs(
|
|
1090
|
+
"div",
|
|
1091
|
+
{
|
|
1092
|
+
onClick: () => {
|
|
1093
|
+
var _a;
|
|
1094
|
+
return (_a = fileInputRef.current) == null ? void 0 : _a.click();
|
|
1095
|
+
},
|
|
1096
|
+
onDrop: (e) => {
|
|
1097
|
+
e.preventDefault();
|
|
1098
|
+
setScreenshotDragOver(false);
|
|
1099
|
+
const file = Array.from(e.dataTransfer.files).find((f) => f.type.startsWith("image/"));
|
|
1100
|
+
if (!file) return;
|
|
1101
|
+
const reader = new FileReader();
|
|
1102
|
+
reader.onload = () => setScreenshot(reader.result);
|
|
1103
|
+
reader.readAsDataURL(file);
|
|
1104
|
+
},
|
|
1105
|
+
onDragOver: (e) => {
|
|
1106
|
+
e.preventDefault();
|
|
1107
|
+
setScreenshotDragOver(true);
|
|
1108
|
+
},
|
|
1109
|
+
onDragLeave: () => setScreenshotDragOver(false),
|
|
1110
|
+
style: {
|
|
1111
|
+
border: `1.5px dashed ${screenshotDragOver ? t.accent : t.inputBorder}`,
|
|
1112
|
+
borderRadius: "8px",
|
|
1113
|
+
padding: "18px 12px",
|
|
1114
|
+
textAlign: "center",
|
|
1115
|
+
cursor: "pointer",
|
|
1116
|
+
background: screenshotDragOver ? isDark ? "rgba(34,211,238,0.06)" : "rgba(8,145,178,0.04)" : "transparent",
|
|
1117
|
+
transition: "border-color 0.15s ease, background 0.15s ease"
|
|
1118
|
+
},
|
|
1119
|
+
children: [
|
|
1120
|
+
/* @__PURE__ */ jsxs("svg", { width: "22", height: "22", viewBox: "0 0 24 24", fill: "none", style: { margin: "0 auto 6px", display: "block", opacity: 0.45 }, children: [
|
|
1121
|
+
/* @__PURE__ */ jsx("rect", { x: "3", y: "3", width: "18", height: "18", rx: "2", stroke: t.textMuted, strokeWidth: "1.5" }),
|
|
1122
|
+
/* @__PURE__ */ jsx("circle", { cx: "8.5", cy: "8.5", r: "1.5", stroke: t.textMuted, strokeWidth: "1.5" }),
|
|
1123
|
+
/* @__PURE__ */ jsx("path", { d: "M21 15l-5-5L5 21", stroke: t.textMuted, strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" })
|
|
1124
|
+
] }),
|
|
1125
|
+
/* @__PURE__ */ jsx("p", { style: { margin: 0, fontSize: "12px", fontWeight: 600, color: t.text }, children: screenshotDragOver ? "Drop to attach" : "Add a screenshot" }),
|
|
1126
|
+
/* @__PURE__ */ jsx("p", { style: { margin: "3px 0 0", fontSize: "11px", color: t.textMuted }, children: "Drag & drop \xB7 Paste \u2318V / Ctrl+V \xB7 Click to browse" })
|
|
1127
|
+
]
|
|
1128
|
+
}
|
|
1129
|
+
)
|
|
1130
|
+
)
|
|
1131
|
+
] }),
|
|
990
1132
|
showSeverity && reportType === "BUG" && /* @__PURE__ */ jsxs("div", { style: { marginTop: "10px" }, children: [
|
|
991
1133
|
/* @__PURE__ */ jsx("span", { style: { fontSize: "12px", color: t.textMuted, marginBottom: "6px", display: "block" }, children: "Severity" }),
|
|
992
1134
|
/* @__PURE__ */ jsx("div", { style: { display: "flex", gap: "6px" }, children: ["low", "medium", "high"].map((s) => /* @__PURE__ */ jsx(
|
|
@@ -1088,91 +1230,23 @@ function ReportDialog({
|
|
|
1088
1230
|
overflow: "hidden",
|
|
1089
1231
|
lineHeight: "1.4"
|
|
1090
1232
|
}, children: description.length > 200 ? description.slice(0, 200) + "..." : description }),
|
|
1091
|
-
screenshot && /* @__PURE__ */
|
|
1092
|
-
|
|
1093
|
-
|
|
1094
|
-
|
|
1095
|
-
|
|
1096
|
-
|
|
1097
|
-
|
|
1098
|
-
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
cursor: "pointer"
|
|
1106
|
-
}
|
|
1107
|
-
}
|
|
1108
|
-
),
|
|
1109
|
-
/* @__PURE__ */ jsx(
|
|
1110
|
-
"button",
|
|
1111
|
-
{
|
|
1112
|
-
type: "button",
|
|
1113
|
-
onClick: () => setScreenshot(null),
|
|
1114
|
-
style: {
|
|
1115
|
-
position: "absolute",
|
|
1116
|
-
top: "4px",
|
|
1117
|
-
right: "4px",
|
|
1118
|
-
background: "rgba(0,0,0,0.6)",
|
|
1119
|
-
border: "none",
|
|
1120
|
-
borderRadius: "50%",
|
|
1121
|
-
width: "20px",
|
|
1122
|
-
height: "20px",
|
|
1123
|
-
cursor: "pointer",
|
|
1124
|
-
display: "flex",
|
|
1125
|
-
alignItems: "center",
|
|
1126
|
-
justifyContent: "center"
|
|
1127
|
-
},
|
|
1128
|
-
"aria-label": "Remove screenshot",
|
|
1129
|
-
children: /* @__PURE__ */ jsx("svg", { width: "10", height: "10", viewBox: "0 0 10 10", fill: "none", children: /* @__PURE__ */ jsx("path", { d: "M1 1L9 9M9 1L1 9", stroke: "#fff", strokeWidth: "1.5", strokeLinecap: "round" }) })
|
|
1130
|
-
}
|
|
1131
|
-
)
|
|
1132
|
-
] }),
|
|
1133
|
-
!screenshot && /* @__PURE__ */ jsxs("div", { style: { display: "flex", gap: "6px", marginBottom: "10px" }, children: [
|
|
1134
|
-
/* @__PURE__ */ jsx(
|
|
1135
|
-
"button",
|
|
1136
|
-
{
|
|
1137
|
-
type: "button",
|
|
1138
|
-
onClick: () => {
|
|
1139
|
-
var _a;
|
|
1140
|
-
return (_a = fileInputRef.current) == null ? void 0 : _a.click();
|
|
1141
|
-
},
|
|
1142
|
-
style: {
|
|
1143
|
-
flex: 1,
|
|
1144
|
-
padding: "8px",
|
|
1145
|
-
borderRadius: "6px",
|
|
1146
|
-
border: `1px dashed ${t.inputBorder}`,
|
|
1147
|
-
textAlign: "center",
|
|
1148
|
-
fontSize: "11px",
|
|
1149
|
-
color: t.textMuted,
|
|
1150
|
-
background: "none",
|
|
1151
|
-
cursor: "pointer"
|
|
1152
|
-
},
|
|
1153
|
-
children: "Upload or paste (\u2318V)"
|
|
1154
|
-
}
|
|
1155
|
-
),
|
|
1156
|
-
/* @__PURE__ */ jsx(
|
|
1157
|
-
"button",
|
|
1158
|
-
{
|
|
1159
|
-
type: "button",
|
|
1160
|
-
onClick: retakeScreenshot,
|
|
1161
|
-
style: {
|
|
1162
|
-
flex: 1,
|
|
1163
|
-
padding: "8px",
|
|
1164
|
-
borderRadius: "6px",
|
|
1165
|
-
border: `1px dashed ${t.inputBorder}`,
|
|
1166
|
-
textAlign: "center",
|
|
1167
|
-
fontSize: "11px",
|
|
1168
|
-
color: t.textMuted,
|
|
1169
|
-
background: "none",
|
|
1170
|
-
cursor: "pointer"
|
|
1171
|
-
},
|
|
1172
|
-
children: "Retake screenshot"
|
|
1233
|
+
screenshot && /* @__PURE__ */ jsx("div", { style: { marginBottom: "10px", position: "relative" }, children: /* @__PURE__ */ jsx(
|
|
1234
|
+
"img",
|
|
1235
|
+
{
|
|
1236
|
+
src: screenshot,
|
|
1237
|
+
alt: "Page screenshot",
|
|
1238
|
+
onClick: () => setPreviewOpen(true),
|
|
1239
|
+
style: {
|
|
1240
|
+
width: "100%",
|
|
1241
|
+
borderRadius: "6px",
|
|
1242
|
+
border: `1px solid ${t.border}`,
|
|
1243
|
+
maxHeight: "80px",
|
|
1244
|
+
objectFit: "cover",
|
|
1245
|
+
objectPosition: "top",
|
|
1246
|
+
cursor: "pointer"
|
|
1173
1247
|
}
|
|
1174
|
-
|
|
1175
|
-
|
|
1248
|
+
}
|
|
1249
|
+
) }),
|
|
1176
1250
|
/* @__PURE__ */ jsx(
|
|
1177
1251
|
"button",
|
|
1178
1252
|
{
|
|
@@ -1335,7 +1409,7 @@ function getTypeIcon(type, color, size = 24) {
|
|
|
1335
1409
|
|
|
1336
1410
|
// src/provider.tsx
|
|
1337
1411
|
import { Fragment as Fragment2, jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
|
|
1338
|
-
var DEFAULT_BASE_URL2 = "https://
|
|
1412
|
+
var DEFAULT_BASE_URL2 = "https://glitchgrab.dev";
|
|
1339
1413
|
var GlitchgrabContext = createContext(null);
|
|
1340
1414
|
function useGlitchgrab() {
|
|
1341
1415
|
const ctx = useContext(GlitchgrabContext);
|
|
@@ -1404,18 +1478,25 @@ function GlitchgrabProviderInner({
|
|
|
1404
1478
|
try {
|
|
1405
1479
|
if (typeof window === "undefined") return;
|
|
1406
1480
|
if (process.env.NODE_ENV === "development") return;
|
|
1481
|
+
const EXTENSION_ORIGIN_RE = /\b(?:chrome|safari|moz)-extension:\/\//;
|
|
1407
1482
|
const handleError = (event) => {
|
|
1408
|
-
var _a, _b, _c, _d, _e, _f;
|
|
1483
|
+
var _a, _b, _c, _d, _e, _f, _g;
|
|
1409
1484
|
try {
|
|
1410
1485
|
const isOpaqueCrossOrigin = event.message === "Script error." || event.message === "Script error" || !event.error && !event.filename;
|
|
1411
1486
|
if (isOpaqueCrossOrigin) {
|
|
1412
1487
|
return;
|
|
1413
1488
|
}
|
|
1489
|
+
if (event.message === "ResizeObserver loop completed with undelivered notifications." || event.message === "ResizeObserver loop limit exceeded") {
|
|
1490
|
+
return;
|
|
1491
|
+
}
|
|
1492
|
+
if (event.filename && EXTENSION_ORIGIN_RE.test(event.filename) || ((_a = event.error) == null ? void 0 : _a.stack) && EXTENSION_ORIGIN_RE.test(event.error.stack)) {
|
|
1493
|
+
return;
|
|
1494
|
+
}
|
|
1414
1495
|
const context = captureContext(visitedPagesRef.current);
|
|
1415
1496
|
const sig = computeSignature({
|
|
1416
1497
|
errorMessage: event.message,
|
|
1417
1498
|
pageUrl: context.url,
|
|
1418
|
-
errorStack: (
|
|
1499
|
+
errorStack: (_b = event.error) == null ? void 0 : _b.stack
|
|
1419
1500
|
});
|
|
1420
1501
|
if (shouldSkipDuplicate(sig)) return;
|
|
1421
1502
|
const payload = {
|
|
@@ -1423,17 +1504,17 @@ function GlitchgrabProviderInner({
|
|
|
1423
1504
|
source: "SDK_AUTO",
|
|
1424
1505
|
type: "BUG",
|
|
1425
1506
|
errorMessage: event.message,
|
|
1426
|
-
errorStack: (
|
|
1507
|
+
errorStack: (_c = event.error) == null ? void 0 : _c.stack,
|
|
1427
1508
|
pageUrl: context.url,
|
|
1428
1509
|
userAgent: context.userAgent,
|
|
1429
1510
|
breadcrumbs: context.breadcrumbs,
|
|
1430
|
-
deviceInfo: (
|
|
1511
|
+
deviceInfo: (_d = context.deviceInfo) != null ? _d : void 0,
|
|
1431
1512
|
metadata: {
|
|
1432
1513
|
timestamp: context.timestamp,
|
|
1433
1514
|
visitedPages: JSON.stringify(context.visitedPages),
|
|
1434
|
-
filename: (
|
|
1435
|
-
lineno: String((
|
|
1436
|
-
colno: String((
|
|
1515
|
+
filename: (_e = event.filename) != null ? _e : "",
|
|
1516
|
+
lineno: String((_f = event.lineno) != null ? _f : ""),
|
|
1517
|
+
colno: String((_g = event.colno) != null ? _g : ""),
|
|
1437
1518
|
...(session == null ? void 0 : session.userId) ? { sessionUserId: session.userId } : {},
|
|
1438
1519
|
...(session == null ? void 0 : session.name) ? { sessionUserName: String(session.name) } : {},
|
|
1439
1520
|
...(session == null ? void 0 : session.email) ? { sessionUserEmail: String(session.email) } : {},
|
|
@@ -1457,6 +1538,7 @@ function GlitchgrabProviderInner({
|
|
|
1457
1538
|
return;
|
|
1458
1539
|
}
|
|
1459
1540
|
const errStack = reason instanceof Error ? reason.stack : void 0;
|
|
1541
|
+
if (errStack && EXTENSION_ORIGIN_RE.test(errStack)) return;
|
|
1460
1542
|
const sig = computeSignature({
|
|
1461
1543
|
errorMessage: errMsg,
|
|
1462
1544
|
pageUrl: context.url,
|
|
@@ -1708,7 +1790,7 @@ function ReportButton({
|
|
|
1708
1790
|
|
|
1709
1791
|
// src/use-reports.ts
|
|
1710
1792
|
import { useState as useState4, useEffect as useEffect3, useCallback as useCallback2 } from "react";
|
|
1711
|
-
var BASE_URL = "https://
|
|
1793
|
+
var BASE_URL = "https://glitchgrab.dev";
|
|
1712
1794
|
function useGlitchgrabReports({
|
|
1713
1795
|
token,
|
|
1714
1796
|
userId,
|