@feedvalue/core 0.1.5 → 0.1.7
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.cjs +57 -33
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +9 -2
- package/dist/index.d.ts +9 -2
- package/dist/index.js +57 -33
- package/dist/index.js.map +1 -1
- package/dist/umd/index.min.js +9 -7
- package/dist/umd/index.min.js.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -389,7 +389,7 @@ var DEFAULT_CONFIG = {
|
|
|
389
389
|
locale: "en"
|
|
390
390
|
};
|
|
391
391
|
var instances = /* @__PURE__ */ new Map();
|
|
392
|
-
var
|
|
392
|
+
var _FeedValue = class _FeedValue {
|
|
393
393
|
/**
|
|
394
394
|
* Create a new FeedValue instance
|
|
395
395
|
* Use FeedValue.init() for public API
|
|
@@ -423,6 +423,8 @@ var FeedValue = class _FeedValue {
|
|
|
423
423
|
__publicField(this, "stylesInjected", false);
|
|
424
424
|
// Auto-close timeout reference (for cleanup on destroy)
|
|
425
425
|
__publicField(this, "autoCloseTimeout", null);
|
|
426
|
+
// Destroyed flag - guards async continuations (fixes React StrictMode race condition)
|
|
427
|
+
__publicField(this, "isDestroyed", false);
|
|
426
428
|
this.widgetId = options.widgetId;
|
|
427
429
|
this.headless = options.headless ?? false;
|
|
428
430
|
this.config = { ...DEFAULT_CONFIG, ...options.config };
|
|
@@ -467,11 +469,19 @@ var FeedValue = class _FeedValue {
|
|
|
467
469
|
this.log("Already initialized");
|
|
468
470
|
return;
|
|
469
471
|
}
|
|
472
|
+
if (this.isDestroyed) {
|
|
473
|
+
this.log("Instance destroyed before init could complete");
|
|
474
|
+
return;
|
|
475
|
+
}
|
|
470
476
|
try {
|
|
471
477
|
this.log("Initializing...");
|
|
472
478
|
const fingerprint = generateFingerprint();
|
|
473
479
|
this.apiClient.setFingerprint(fingerprint);
|
|
474
480
|
const configResponse = await this.apiClient.fetchConfig(this.widgetId);
|
|
481
|
+
if (this.isDestroyed) {
|
|
482
|
+
this.log("Instance destroyed during config fetch, aborting init");
|
|
483
|
+
return;
|
|
484
|
+
}
|
|
475
485
|
this.widgetConfig = {
|
|
476
486
|
widgetId: configResponse.widget_id,
|
|
477
487
|
widgetKey: configResponse.widget_key,
|
|
@@ -513,6 +523,7 @@ var FeedValue = class _FeedValue {
|
|
|
513
523
|
*/
|
|
514
524
|
destroy() {
|
|
515
525
|
this.log("Destroying...");
|
|
526
|
+
this.isDestroyed = true;
|
|
516
527
|
if (this.autoCloseTimeout) {
|
|
517
528
|
clearTimeout(this.autoCloseTimeout);
|
|
518
529
|
this.autoCloseTimeout = null;
|
|
@@ -884,9 +895,6 @@ var FeedValue = class _FeedValue {
|
|
|
884
895
|
.fv-widget-trigger {
|
|
885
896
|
position: fixed;
|
|
886
897
|
${positionStyles}
|
|
887
|
-
display: inline-flex;
|
|
888
|
-
align-items: center;
|
|
889
|
-
gap: 8px;
|
|
890
898
|
background-color: ${styling.primaryColor};
|
|
891
899
|
color: ${styling.buttonTextColor};
|
|
892
900
|
padding: 12px 24px;
|
|
@@ -905,13 +913,18 @@ var FeedValue = class _FeedValue {
|
|
|
905
913
|
box-shadow: 0 6px 12px rgba(0, 0, 0, 0.15);
|
|
906
914
|
}
|
|
907
915
|
.fv-widget-trigger-icon {
|
|
916
|
+
width: 56px;
|
|
917
|
+
height: 56px;
|
|
918
|
+
padding: 14px;
|
|
919
|
+
border-radius: 50%;
|
|
908
920
|
display: flex;
|
|
909
921
|
align-items: center;
|
|
910
922
|
justify-content: center;
|
|
911
923
|
}
|
|
912
924
|
.fv-widget-trigger-icon svg {
|
|
913
|
-
width:
|
|
914
|
-
height:
|
|
925
|
+
width: 24px;
|
|
926
|
+
height: 24px;
|
|
927
|
+
stroke: currentColor;
|
|
915
928
|
}
|
|
916
929
|
.fv-widget-overlay {
|
|
917
930
|
position: fixed;
|
|
@@ -1067,50 +1080,49 @@ var FeedValue = class _FeedValue {
|
|
|
1067
1080
|
}
|
|
1068
1081
|
}
|
|
1069
1082
|
/**
|
|
1070
|
-
*
|
|
1083
|
+
* Parse SVG string to DOM element safely using DOMParser
|
|
1071
1084
|
*/
|
|
1072
|
-
|
|
1073
|
-
const icons = {
|
|
1074
|
-
chat: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z"/></svg>',
|
|
1075
|
-
message: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21 11.5a8.38 8.38 0 0 1-.9 3.8 8.5 8.5 0 0 1-7.6 4.7 8.38 8.38 0 0 1-3.8-.9L3 21l1.9-5.7a8.38 8.38 0 0 1-.9-3.8 8.5 8.5 0 0 1 4.7-7.6 8.38 8.38 0 0 1 3.8-.9h.5a8.48 8.48 0 0 1 8 8v.5z"/></svg>',
|
|
1076
|
-
feedback: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M14 9V5a3 3 0 0 0-3-3l-4 9v11h11.28a2 2 0 0 0 2-1.7l1.38-9a2 2 0 0 0-2-2.3zM7 22H4a2 2 0 0 1-2-2v-7a2 2 0 0 1 2-2h3"/></svg>',
|
|
1077
|
-
comment: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z"/><line x1="9" y1="10" x2="15" y2="10"/></svg>',
|
|
1078
|
-
help: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',
|
|
1079
|
-
lightbulb: '<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="9" y1="18" x2="15" y2="18"/><line x1="10" y1="22" x2="14" y2="22"/><path d="M15.09 14c.18-.98.65-1.74 1.41-2.5A4.65 4.65 0 0 0 18 8 6 6 0 0 0 6 8c0 1 .23 2.23 1.5 3.5A4.61 4.61 0 0 1 8.91 14"/></svg>'
|
|
1080
|
-
};
|
|
1081
|
-
const svgString = icons[iconType];
|
|
1082
|
-
if (!svgString) return null;
|
|
1085
|
+
parseSvgString(svgString) {
|
|
1083
1086
|
const parser = new DOMParser();
|
|
1084
1087
|
const doc = parser.parseFromString(svgString, "image/svg+xml");
|
|
1088
|
+
const parserError = doc.querySelector("parsererror");
|
|
1089
|
+
if (parserError) {
|
|
1090
|
+
this.log("SVG parse error:", parserError.textContent);
|
|
1091
|
+
return null;
|
|
1092
|
+
}
|
|
1085
1093
|
const svg = doc.querySelector("svg");
|
|
1086
1094
|
if (!svg || svg.nodeName !== "svg") return null;
|
|
1087
1095
|
return svg;
|
|
1088
1096
|
}
|
|
1089
1097
|
/**
|
|
1090
1098
|
* Render trigger button using safe DOM methods
|
|
1099
|
+
* Matches widget-bundle behavior: icon mode = circular button, text mode = rectangular
|
|
1100
|
+
* Falls back to text mode if icon rendering fails (fixes "square with ellipses" bug)
|
|
1091
1101
|
*/
|
|
1092
1102
|
renderTrigger() {
|
|
1093
1103
|
if (!this.widgetConfig) return;
|
|
1094
1104
|
const { triggerIcon, triggerText } = this.widgetConfig.config;
|
|
1105
|
+
const hasIcon = triggerIcon && triggerIcon !== "none";
|
|
1095
1106
|
this.triggerButton = document.createElement("button");
|
|
1096
|
-
|
|
1097
|
-
if (
|
|
1098
|
-
const
|
|
1099
|
-
if (
|
|
1100
|
-
const
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
|
|
1107
|
-
this.triggerButton.appendChild(textSpan);
|
|
1107
|
+
let iconRendered = false;
|
|
1108
|
+
if (hasIcon) {
|
|
1109
|
+
const iconSvgString = _FeedValue.TRIGGER_ICONS[triggerIcon];
|
|
1110
|
+
if (iconSvgString) {
|
|
1111
|
+
const svgElement = this.parseSvgString(iconSvgString);
|
|
1112
|
+
if (svgElement) {
|
|
1113
|
+
this.triggerButton.className = "fv-widget-trigger fv-widget-trigger-icon";
|
|
1114
|
+
this.triggerButton.appendChild(svgElement);
|
|
1115
|
+
iconRendered = true;
|
|
1116
|
+
} else {
|
|
1117
|
+
this.log(`SVG parsing failed for icon: ${triggerIcon}, falling back to text`);
|
|
1108
1118
|
}
|
|
1109
1119
|
} else {
|
|
1110
|
-
this.
|
|
1120
|
+
this.log(`Icon not found: ${triggerIcon}, falling back to text`);
|
|
1111
1121
|
}
|
|
1112
|
-
}
|
|
1113
|
-
|
|
1122
|
+
}
|
|
1123
|
+
if (!iconRendered) {
|
|
1124
|
+
this.triggerButton.className = "fv-widget-trigger";
|
|
1125
|
+
this.triggerButton.textContent = triggerText || "Feedback";
|
|
1114
1126
|
}
|
|
1115
1127
|
this.triggerButton.addEventListener("click", () => this.open());
|
|
1116
1128
|
document.body.appendChild(this.triggerButton);
|
|
@@ -1267,6 +1279,18 @@ var FeedValue = class _FeedValue {
|
|
|
1267
1279
|
}
|
|
1268
1280
|
}
|
|
1269
1281
|
};
|
|
1282
|
+
/**
|
|
1283
|
+
* SVG icons for trigger button (matching widget-bundle exactly)
|
|
1284
|
+
*/
|
|
1285
|
+
__publicField(_FeedValue, "TRIGGER_ICONS", {
|
|
1286
|
+
chat: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M7.9 20A9 9 0 1 0 4 16.1L2 22Z"/></svg>',
|
|
1287
|
+
message: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect width="18" height="18" x="3" y="3" rx="2"/><path d="M8 12h.01"/><path d="M12 12h.01"/><path d="M16 12h.01"/></svg>',
|
|
1288
|
+
feedback: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M14 9a2 2 0 0 1-2 2H6l-4 4V4c0-1.1.9-2 2-2h8a2 2 0 0 1 2 2v5Z"/><path d="M18 9h2a2 2 0 0 1 2 2v11l-4-4h-6a2 2 0 0 1-2-2v-1"/></svg>',
|
|
1289
|
+
comment: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z"/><path d="M13 8H7"/><path d="M17 12H7"/></svg>',
|
|
1290
|
+
help: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3"/><path d="M12 17h.01"/></svg>',
|
|
1291
|
+
lightbulb: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5"/><path d="M9 18h6"/><path d="M10 22h4"/></svg>'
|
|
1292
|
+
});
|
|
1293
|
+
var FeedValue = _FeedValue;
|
|
1270
1294
|
|
|
1271
1295
|
exports.ApiClient = ApiClient;
|
|
1272
1296
|
exports.DEFAULT_API_BASE_URL = DEFAULT_API_BASE_URL;
|