dolphin-client 1.1.1 → 1.1.2
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/.vscode/settings.json +5 -0
- package/dist/dolphin-client.js +181 -171
- package/dist/dolphin-client.min.js +19 -19
- package/dist/index.cjs +181 -171
- package/dist/index.js +181 -171
- package/package.json +1 -1
package/dist/dolphin-client.js
CHANGED
|
@@ -997,6 +997,82 @@ var DolphinModule = (() => {
|
|
|
997
997
|
function escapeRegExp(str) {
|
|
998
998
|
return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
999
999
|
}
|
|
1000
|
+
function evaluateExpression(expr, ctx) {
|
|
1001
|
+
if (!ctx || typeof ctx !== "object") return void 0;
|
|
1002
|
+
try {
|
|
1003
|
+
const safeCtx = new Proxy(ctx, {
|
|
1004
|
+
has(target, prop) {
|
|
1005
|
+
return true;
|
|
1006
|
+
},
|
|
1007
|
+
get(target, prop) {
|
|
1008
|
+
if (typeof prop === "string") {
|
|
1009
|
+
if (prop in target) return target[prop];
|
|
1010
|
+
if (typeof globalThis !== "undefined" && prop in globalThis) return globalThis[prop];
|
|
1011
|
+
if (typeof window !== "undefined" && prop in window) return window[prop];
|
|
1012
|
+
}
|
|
1013
|
+
return void 0;
|
|
1014
|
+
}
|
|
1015
|
+
});
|
|
1016
|
+
const fn = new Function("ctx", `with(ctx) { return (${expr}); }`);
|
|
1017
|
+
return fn(safeCtx);
|
|
1018
|
+
} catch {
|
|
1019
|
+
return ctx[expr];
|
|
1020
|
+
}
|
|
1021
|
+
}
|
|
1022
|
+
function splitByUnquotedChar(str, char) {
|
|
1023
|
+
const parts = [];
|
|
1024
|
+
let current = "";
|
|
1025
|
+
let inSingleQuote = false;
|
|
1026
|
+
let inDoubleQuote = false;
|
|
1027
|
+
let inBacktick = false;
|
|
1028
|
+
let depth = 0;
|
|
1029
|
+
for (let i = 0; i < str.length; i++) {
|
|
1030
|
+
const c = str[i];
|
|
1031
|
+
if (c === "'" && !inDoubleQuote && !inBacktick) {
|
|
1032
|
+
inSingleQuote = !inSingleQuote;
|
|
1033
|
+
} else if (c === '"' && !inSingleQuote && !inBacktick) {
|
|
1034
|
+
inDoubleQuote = !inDoubleQuote;
|
|
1035
|
+
} else if (c === "`" && !inSingleQuote && !inDoubleQuote) {
|
|
1036
|
+
inBacktick = !inBacktick;
|
|
1037
|
+
} else if (c === "(" || c === "[" || c === "{") {
|
|
1038
|
+
if (!inSingleQuote && !inDoubleQuote && !inBacktick) depth++;
|
|
1039
|
+
} else if (c === ")" || c === "]" || c === "}") {
|
|
1040
|
+
if (!inSingleQuote && !inDoubleQuote && !inBacktick) depth--;
|
|
1041
|
+
}
|
|
1042
|
+
if (c === char && !inSingleQuote && !inDoubleQuote && !inBacktick && depth === 0) {
|
|
1043
|
+
parts.push(current);
|
|
1044
|
+
current = "";
|
|
1045
|
+
} else {
|
|
1046
|
+
current += c;
|
|
1047
|
+
}
|
|
1048
|
+
}
|
|
1049
|
+
parts.push(current);
|
|
1050
|
+
return parts;
|
|
1051
|
+
}
|
|
1052
|
+
function splitFirstUnquotedColon(str) {
|
|
1053
|
+
let inSingleQuote = false;
|
|
1054
|
+
let inDoubleQuote = false;
|
|
1055
|
+
let inBacktick = false;
|
|
1056
|
+
let depth = 0;
|
|
1057
|
+
for (let i = 0; i < str.length; i++) {
|
|
1058
|
+
const c = str[i];
|
|
1059
|
+
if (c === "'" && !inDoubleQuote && !inBacktick) {
|
|
1060
|
+
inSingleQuote = !inSingleQuote;
|
|
1061
|
+
} else if (c === '"' && !inSingleQuote && !inBacktick) {
|
|
1062
|
+
inDoubleQuote = !inDoubleQuote;
|
|
1063
|
+
} else if (c === "`" && !inSingleQuote && !inDoubleQuote) {
|
|
1064
|
+
inBacktick = !inBacktick;
|
|
1065
|
+
} else if (c === "(" || c === "[" || c === "{") {
|
|
1066
|
+
if (!inSingleQuote && !inDoubleQuote && !inBacktick) depth++;
|
|
1067
|
+
} else if (c === ")" || c === "]" || c === "}") {
|
|
1068
|
+
if (!inSingleQuote && !inDoubleQuote && !inBacktick) depth--;
|
|
1069
|
+
}
|
|
1070
|
+
if (c === ":" && !inSingleQuote && !inDoubleQuote && !inBacktick && depth === 0) {
|
|
1071
|
+
return [str.slice(0, i), str.slice(i + 1)];
|
|
1072
|
+
}
|
|
1073
|
+
}
|
|
1074
|
+
return null;
|
|
1075
|
+
}
|
|
1000
1076
|
function resolveTemplate(el) {
|
|
1001
1077
|
const template = el.getAttribute("data-rt-template");
|
|
1002
1078
|
if (!template) return null;
|
|
@@ -1013,9 +1089,26 @@ var DolphinModule = (() => {
|
|
|
1013
1089
|
if (!templateStr.includes("{#if") && !templateStr.includes("{#each")) {
|
|
1014
1090
|
let result = templateStr;
|
|
1015
1091
|
for (let key in context) {
|
|
1016
|
-
const escapedKey = key.replace(/[
|
|
1017
|
-
result = result.replace(new RegExp(
|
|
1018
|
-
}
|
|
1092
|
+
const escapedKey = key.replace(/[.*+?^$${}()|[\]\\]/g, "\\$&");
|
|
1093
|
+
result = result.replace(new RegExp("\\{\\{" + escapedKey + "\\}}", "g"), context[key] !== void 0 && context[key] !== null ? context[key] : "");
|
|
1094
|
+
}
|
|
1095
|
+
result = result.replace(/\{\{([\s\S]*?)\}\}/g, (match, expr) => {
|
|
1096
|
+
const trimmed = expr.trim();
|
|
1097
|
+
if (!trimmed) return "";
|
|
1098
|
+
if (/^[a-zA-Z_$][a-zA-Z0-9_$]*(?:\??\.[a-zA-Z_$][a-zA-Z0-9_$]*)+$/.test(trimmed)) {
|
|
1099
|
+
const parts = trimmed.split(/\??\./);
|
|
1100
|
+
let val = context;
|
|
1101
|
+
for (const part of parts) {
|
|
1102
|
+
if (val === void 0 || val === null) {
|
|
1103
|
+
val = void 0;
|
|
1104
|
+
break;
|
|
1105
|
+
}
|
|
1106
|
+
val = val[part];
|
|
1107
|
+
}
|
|
1108
|
+
return val !== void 0 && val !== null ? val : "";
|
|
1109
|
+
}
|
|
1110
|
+
return match;
|
|
1111
|
+
});
|
|
1019
1112
|
return result;
|
|
1020
1113
|
}
|
|
1021
1114
|
try {
|
|
@@ -1135,7 +1228,9 @@ var DolphinModule = (() => {
|
|
|
1135
1228
|
if (typeof document === "undefined") return html;
|
|
1136
1229
|
try {
|
|
1137
1230
|
const parser = new DOMParser();
|
|
1138
|
-
const
|
|
1231
|
+
const hasBodyOrHtml = /<\s*(?:body|html)\b/i.test(html);
|
|
1232
|
+
const parseString = hasBodyOrHtml ? html : `<body>${html}</body>`;
|
|
1233
|
+
const doc = parser.parseFromString(parseString, "text/html");
|
|
1139
1234
|
const body = doc.body;
|
|
1140
1235
|
const sanitizeNode = (el) => {
|
|
1141
1236
|
const tag = el.tagName.toLowerCase();
|
|
@@ -1249,7 +1344,7 @@ var DolphinModule = (() => {
|
|
|
1249
1344
|
});
|
|
1250
1345
|
}
|
|
1251
1346
|
}
|
|
1252
|
-
clientProto.setStoreState = function(storeName, key, val) {
|
|
1347
|
+
clientProto.setStoreState = function(storeName, key, val, originEl) {
|
|
1253
1348
|
this.uiStores = this.uiStores || /* @__PURE__ */ new Map();
|
|
1254
1349
|
if (!this.uiStores.has(storeName)) {
|
|
1255
1350
|
this.uiStores.set(storeName, {});
|
|
@@ -1262,6 +1357,7 @@ var DolphinModule = (() => {
|
|
|
1262
1357
|
if (typeof document !== "undefined") {
|
|
1263
1358
|
const readElements = document.querySelectorAll(`[data-store-read="${storeName}.${key}"]`);
|
|
1264
1359
|
readElements.forEach((el) => {
|
|
1360
|
+
if (el === originEl) return;
|
|
1265
1361
|
if (el.tagName === "INPUT" || el.tagName === "TEXTAREA") {
|
|
1266
1362
|
if (el.type === "checkbox") {
|
|
1267
1363
|
el.checked = !!val;
|
|
@@ -1337,20 +1433,49 @@ var DolphinModule = (() => {
|
|
|
1337
1433
|
if (key) return ctx[key];
|
|
1338
1434
|
return ctx;
|
|
1339
1435
|
}
|
|
1340
|
-
current = current.parentElement;
|
|
1436
|
+
current = current.parentElement || current.parentNode;
|
|
1341
1437
|
}
|
|
1342
1438
|
return null;
|
|
1343
1439
|
};
|
|
1344
1440
|
clientProto._executeStoreAction = function(expression, element) {
|
|
1345
1441
|
this.uiStores = this.uiStores || /* @__PURE__ */ new Map();
|
|
1442
|
+
const parentCtx = element && typeof this.getClosestContext === "function" ? this.getClosestContext(element) : null;
|
|
1346
1443
|
const context = new Proxy({}, {
|
|
1347
1444
|
has: (target, prop) => {
|
|
1348
1445
|
return true;
|
|
1349
1446
|
},
|
|
1350
1447
|
get: (target, prop) => {
|
|
1351
1448
|
if (typeof prop === "string") {
|
|
1449
|
+
if (prop === "log") {
|
|
1450
|
+
return (arg) => {
|
|
1451
|
+
if (arg === void 0) {
|
|
1452
|
+
const allStores = {};
|
|
1453
|
+
this.uiStores.forEach((val, key) => {
|
|
1454
|
+
allStores[key] = { ...val };
|
|
1455
|
+
});
|
|
1456
|
+
console.log(`%c\u{1F4CA} [Dolphin All UI Stores]:`, "color: #06b6d4; font-weight: bold;", allStores);
|
|
1457
|
+
} else if (arg && typeof arg === "object" && arg.__isStoreProxy__) {
|
|
1458
|
+
const storeName = arg.__storeName__;
|
|
1459
|
+
const store = this.uiStores.get(storeName);
|
|
1460
|
+
console.log(`%c\u{1F4CA} [Dolphin Store: ${storeName}]:`, "color: #06b6d4; font-weight: bold;", store ? { ...store } : {});
|
|
1461
|
+
} else {
|
|
1462
|
+
console.log(`%c\u{1F4CA} [Dolphin Log]:`, "color: #06b6d4; font-weight: bold;", arg);
|
|
1463
|
+
}
|
|
1464
|
+
};
|
|
1465
|
+
}
|
|
1466
|
+
if (parentCtx && parentCtx[prop] !== void 0) {
|
|
1467
|
+
return parentCtx[prop];
|
|
1468
|
+
}
|
|
1469
|
+
if (typeof globalThis !== "undefined" && prop in globalThis) {
|
|
1470
|
+
return globalThis[prop];
|
|
1471
|
+
}
|
|
1472
|
+
if (typeof window !== "undefined" && prop in window) {
|
|
1473
|
+
return window[prop];
|
|
1474
|
+
}
|
|
1352
1475
|
return new Proxy({}, {
|
|
1353
1476
|
get: (subTarget, subProp) => {
|
|
1477
|
+
if (subProp === "__storeName__") return prop;
|
|
1478
|
+
if (subProp === "__isStoreProxy__") return true;
|
|
1354
1479
|
if (typeof subProp === "string") {
|
|
1355
1480
|
return this.getStoreState(prop, subProp);
|
|
1356
1481
|
}
|
|
@@ -1377,86 +1502,6 @@ var DolphinModule = (() => {
|
|
|
1377
1502
|
console.error("%cFailed Expression:", "color: #3b82f6; font-style: italic;", expression);
|
|
1378
1503
|
}
|
|
1379
1504
|
};
|
|
1380
|
-
clientProto._showAlert = function(id, duration) {
|
|
1381
|
-
if (typeof document === "undefined") return;
|
|
1382
|
-
const el = document.getElementById(id) || document.querySelector(`[id="${id}"]`);
|
|
1383
|
-
if (!el) return;
|
|
1384
|
-
el.removeAttribute("hidden");
|
|
1385
|
-
el.style.display = "";
|
|
1386
|
-
if (duration && duration > 0) {
|
|
1387
|
-
setTimeout(() => {
|
|
1388
|
-
el.setAttribute("hidden", "");
|
|
1389
|
-
}, duration);
|
|
1390
|
-
}
|
|
1391
|
-
};
|
|
1392
|
-
clientProto._showToast = function(message, type = "success") {
|
|
1393
|
-
if (typeof document === "undefined") return;
|
|
1394
|
-
const colors = {
|
|
1395
|
-
success: { bg: "rgba(16,185,129,0.15)", border: "#10b981", icon: "\u2705" },
|
|
1396
|
-
error: { bg: "rgba(239,68,68,0.15)", border: "#ef4444", icon: "\u274C" },
|
|
1397
|
-
info: { bg: "rgba(59,130,246,0.15)", border: "#3b82f6", icon: "\u2139\uFE0F" }
|
|
1398
|
-
};
|
|
1399
|
-
const c = colors[type] || colors.success;
|
|
1400
|
-
const toast = document.createElement("div");
|
|
1401
|
-
toast.setAttribute("data-dolphin-toast", "");
|
|
1402
|
-
const existing = document.querySelectorAll("[data-dolphin-toast]");
|
|
1403
|
-
const offset = existing.length * 72;
|
|
1404
|
-
toast.style.cssText = [
|
|
1405
|
-
"position:fixed",
|
|
1406
|
-
`bottom:${24 + offset}px`,
|
|
1407
|
-
"right:24px",
|
|
1408
|
-
"z-index:2147483647",
|
|
1409
|
-
`background:${c.bg}`,
|
|
1410
|
-
`border:1px solid ${c.border}`,
|
|
1411
|
-
"color:#fff",
|
|
1412
|
-
"padding:14px 20px",
|
|
1413
|
-
"border-radius:14px",
|
|
1414
|
-
"font-size:14px",
|
|
1415
|
-
"font-weight:600",
|
|
1416
|
-
"font-family:system-ui,sans-serif",
|
|
1417
|
-
"box-shadow:0 8px 32px rgba(0,0,0,0.4)",
|
|
1418
|
-
"display:flex",
|
|
1419
|
-
"align-items:center",
|
|
1420
|
-
"gap:10px",
|
|
1421
|
-
"max-width:380px",
|
|
1422
|
-
"word-break:break-word",
|
|
1423
|
-
"transform:translateY(80px)",
|
|
1424
|
-
"opacity:0",
|
|
1425
|
-
"transition:transform 0.35s cubic-bezier(0.34,1.56,0.64,1),opacity 0.3s ease",
|
|
1426
|
-
"pointer-events:auto",
|
|
1427
|
-
"backdrop-filter:blur(12px)"
|
|
1428
|
-
].join(";");
|
|
1429
|
-
toast.innerHTML = `<span style="font-size:18px">${c.icon}</span><span>${message}</span>`;
|
|
1430
|
-
document.body.appendChild(toast);
|
|
1431
|
-
const restack = () => {
|
|
1432
|
-
const remaining = document.querySelectorAll("[data-dolphin-toast]");
|
|
1433
|
-
remaining.forEach((el, i) => {
|
|
1434
|
-
el.style.bottom = `${24 + i * 72}px`;
|
|
1435
|
-
});
|
|
1436
|
-
};
|
|
1437
|
-
const raf = typeof requestAnimationFrame !== "undefined" ? requestAnimationFrame : (cb) => setTimeout(cb, 0);
|
|
1438
|
-
raf(() => raf(() => {
|
|
1439
|
-
toast.style.transform = "translateY(0)";
|
|
1440
|
-
toast.style.opacity = "1";
|
|
1441
|
-
}));
|
|
1442
|
-
const removeToast = () => {
|
|
1443
|
-
clearTimeout(toast._removeTimer);
|
|
1444
|
-
if (toast.parentNode) {
|
|
1445
|
-
toast.parentNode.removeChild(toast);
|
|
1446
|
-
restack();
|
|
1447
|
-
}
|
|
1448
|
-
};
|
|
1449
|
-
const hideTimer = setTimeout(() => {
|
|
1450
|
-
toast.style.transform = "translateY(80px)";
|
|
1451
|
-
toast.style.opacity = "0";
|
|
1452
|
-
toast._removeTimer = setTimeout(removeToast, 400);
|
|
1453
|
-
}, 3500);
|
|
1454
|
-
toast._hideTimer = hideTimer;
|
|
1455
|
-
toast.addEventListener("click", () => {
|
|
1456
|
-
clearTimeout(toast._hideTimer);
|
|
1457
|
-
removeToast();
|
|
1458
|
-
}, { once: true });
|
|
1459
|
-
};
|
|
1460
1505
|
clientProto._initDOMBinding = function() {
|
|
1461
1506
|
if (this._domInitialized) return;
|
|
1462
1507
|
this._domInitialized = true;
|
|
@@ -1472,7 +1517,7 @@ var DolphinModule = (() => {
|
|
|
1472
1517
|
const storeName = parts[0];
|
|
1473
1518
|
const key = parts[1];
|
|
1474
1519
|
const val = e.target.type === "checkbox" ? e.target.checked : e.target.value;
|
|
1475
|
-
this.setStoreState(storeName, key, val);
|
|
1520
|
+
this.setStoreState(storeName, key, val, e.target);
|
|
1476
1521
|
}
|
|
1477
1522
|
}
|
|
1478
1523
|
const rules = e.target.getAttribute("data-rt-validate");
|
|
@@ -1555,11 +1600,6 @@ var DolphinModule = (() => {
|
|
|
1555
1600
|
resolvedTopic = resolvedTopic.replace(new RegExp(`\\{\\{${escapedK}\\}\\}`, "g"), parentCtx[k] !== void 0 && parentCtx[k] !== null ? parentCtx[k] : "");
|
|
1556
1601
|
}
|
|
1557
1602
|
this.publish(resolvedTopic, data);
|
|
1558
|
-
const rtSuccessId = e.target.getAttribute("data-rt-api-success");
|
|
1559
|
-
if (rtSuccessId) {
|
|
1560
|
-
const rtSuccessEl = document.getElementById(rtSuccessId);
|
|
1561
|
-
if (rtSuccessEl) this._showToast(rtSuccessEl.textContent || rtSuccessEl.innerText || "", "success");
|
|
1562
|
-
}
|
|
1563
1603
|
} else if (apiTarget) {
|
|
1564
1604
|
let resolvedTarget = apiTarget;
|
|
1565
1605
|
for (const k in parentCtx) {
|
|
@@ -1576,40 +1616,16 @@ var DolphinModule = (() => {
|
|
|
1576
1616
|
const result = await this.api.request(method, path, data);
|
|
1577
1617
|
const resultBind = e.target.getAttribute("data-api-result");
|
|
1578
1618
|
if (resultBind) this._updateDOM(resultBind, result);
|
|
1579
|
-
const successToast = e.target.getAttribute("data-api-toast");
|
|
1580
|
-
if (successToast) this._showToast(successToast, "success");
|
|
1581
|
-
const successElId = e.target.getAttribute("data-rt-api-success");
|
|
1582
|
-
if (successElId) {
|
|
1583
|
-
const duration = parseInt(e.target.getAttribute("data-rt-alert-duration") || "0", 10);
|
|
1584
|
-
this._showAlert(successElId, duration);
|
|
1585
|
-
const errElId = e.target.getAttribute("data-rt-api-error");
|
|
1586
|
-
if (errElId) {
|
|
1587
|
-
const errEl = document.getElementById(errElId);
|
|
1588
|
-
if (errEl) errEl.setAttribute("hidden", "");
|
|
1589
|
-
}
|
|
1590
|
-
}
|
|
1591
1619
|
const redirect = e.target.getAttribute("data-api-redirect");
|
|
1592
1620
|
if (redirect) window.location.href = redirect;
|
|
1593
1621
|
if (e.target.hasAttribute("data-api-reload")) window.location.reload();
|
|
1594
1622
|
} catch (err) {
|
|
1595
1623
|
console.error("[Dolphin] API Submit Error:", err);
|
|
1596
|
-
const errorToast = e.target.getAttribute("data-api-error-toast");
|
|
1597
|
-
if (errorToast) this._showToast(errorToast, "error");
|
|
1598
|
-
const errorElId = e.target.getAttribute("data-rt-api-error");
|
|
1599
|
-
if (errorElId) {
|
|
1600
|
-
const duration = parseInt(e.target.getAttribute("data-rt-alert-duration") || "0", 10);
|
|
1601
|
-
this._showAlert(errorElId, duration);
|
|
1602
|
-
const sucElId = e.target.getAttribute("data-rt-api-success");
|
|
1603
|
-
if (sucElId) {
|
|
1604
|
-
const sucEl = document.getElementById(sucElId);
|
|
1605
|
-
if (sucEl) sucEl.setAttribute("hidden", "");
|
|
1606
|
-
}
|
|
1607
|
-
}
|
|
1608
1624
|
}
|
|
1609
1625
|
}
|
|
1610
1626
|
}
|
|
1611
1627
|
});
|
|
1612
|
-
const INTERACTION_EVENTS = ["click", "change", "input", "keydown", "keyup", "dblclick", "focus", "blur", "mouseenter", "mouseleave"];
|
|
1628
|
+
const INTERACTION_EVENTS = ["click", "change", "submit", "input", "keydown", "keyup", "dblclick", "focus", "blur", "mouseenter", "mouseleave"];
|
|
1613
1629
|
INTERACTION_EVENTS.forEach((evtName) => {
|
|
1614
1630
|
this.addDomListener(document, evtName, async (e) => {
|
|
1615
1631
|
if (!e.target || !e.target.closest) return;
|
|
@@ -1640,12 +1656,7 @@ var DolphinModule = (() => {
|
|
|
1640
1656
|
const apiTarget = apiBtn.getAttribute(`data-api-${evtName}`);
|
|
1641
1657
|
const actionData = apiBtn.getAttribute("data-api-payload");
|
|
1642
1658
|
const parentCtx = this.getClosestContext(apiBtn) || {};
|
|
1643
|
-
|
|
1644
|
-
for (const k in parentCtx) {
|
|
1645
|
-
const escapedK = escapeRegExp(k);
|
|
1646
|
-
resolvedApiTarget = resolvedApiTarget.replace(new RegExp(`\\{\\{${escapedK}\\}\\}`, "g"), parentCtx[k] !== void 0 && parentCtx[k] !== null ? parentCtx[k] : "");
|
|
1647
|
-
}
|
|
1648
|
-
const parts = resolvedApiTarget.trim().split(" ");
|
|
1659
|
+
const parts = apiTarget.trim().split(" ");
|
|
1649
1660
|
const method = parts.length > 1 ? parts[0].toUpperCase() : "POST";
|
|
1650
1661
|
const path = parts.length > 1 ? parts[1] : parts[0];
|
|
1651
1662
|
let payload = null;
|
|
@@ -1665,35 +1676,11 @@ var DolphinModule = (() => {
|
|
|
1665
1676
|
const result = await this.api.request(method, path, payload);
|
|
1666
1677
|
const resultBind = apiBtn.getAttribute("data-api-result");
|
|
1667
1678
|
if (resultBind) this._updateDOM(resultBind, result);
|
|
1668
|
-
const successToast = apiBtn.getAttribute("data-api-toast");
|
|
1669
|
-
if (successToast) this._showToast(successToast, "success");
|
|
1670
|
-
const successElId = apiBtn.getAttribute("data-rt-api-success");
|
|
1671
|
-
if (successElId) {
|
|
1672
|
-
const duration = parseInt(apiBtn.getAttribute("data-rt-alert-duration") || "0", 10);
|
|
1673
|
-
this._showAlert(successElId, duration);
|
|
1674
|
-
const errElId = apiBtn.getAttribute("data-rt-api-error");
|
|
1675
|
-
if (errElId) {
|
|
1676
|
-
const errEl = document.getElementById(errElId);
|
|
1677
|
-
if (errEl) errEl.setAttribute("hidden", "");
|
|
1678
|
-
}
|
|
1679
|
-
}
|
|
1680
1679
|
const redirect = apiBtn.getAttribute("data-api-redirect");
|
|
1681
1680
|
if (redirect) window.location.href = redirect;
|
|
1682
1681
|
if (apiBtn.hasAttribute("data-api-reload")) window.location.reload();
|
|
1683
1682
|
} catch (err) {
|
|
1684
1683
|
console.error(`[Dolphin] API ${evtName} Error:`, err);
|
|
1685
|
-
const errorToast = apiBtn.getAttribute("data-api-error-toast");
|
|
1686
|
-
if (errorToast) this._showToast(errorToast, "error");
|
|
1687
|
-
const errorElId = apiBtn.getAttribute("data-rt-api-error");
|
|
1688
|
-
if (errorElId) {
|
|
1689
|
-
const duration = parseInt(apiBtn.getAttribute("data-rt-alert-duration") || "0", 10);
|
|
1690
|
-
this._showAlert(errorElId, duration);
|
|
1691
|
-
const sucElId = apiBtn.getAttribute("data-rt-api-success");
|
|
1692
|
-
if (sucElId) {
|
|
1693
|
-
const sucEl = document.getElementById(sucElId);
|
|
1694
|
-
if (sucEl) sucEl.setAttribute("hidden", "");
|
|
1695
|
-
}
|
|
1696
|
-
}
|
|
1697
1684
|
}
|
|
1698
1685
|
}
|
|
1699
1686
|
const storeActionBtn = e.target.closest(`[data-store-${evtName}]`);
|
|
@@ -1890,24 +1877,33 @@ var DolphinModule = (() => {
|
|
|
1890
1877
|
const processNode = (node) => {
|
|
1891
1878
|
if (node.hasAttribute("data-rt-text")) {
|
|
1892
1879
|
const key = node.getAttribute("data-rt-text");
|
|
1893
|
-
if (key
|
|
1880
|
+
if (key) {
|
|
1881
|
+
const val = evaluateExpression(key, processedPayload);
|
|
1882
|
+
if (val !== void 0 && val !== null) node.textContent = val;
|
|
1883
|
+
}
|
|
1894
1884
|
}
|
|
1895
1885
|
if (node.hasAttribute("data-rt-html")) {
|
|
1896
1886
|
const key = node.getAttribute("data-rt-html");
|
|
1897
|
-
if (key
|
|
1898
|
-
|
|
1887
|
+
if (key) {
|
|
1888
|
+
const val = evaluateExpression(key, processedPayload);
|
|
1889
|
+
if (val !== void 0 && val !== null) {
|
|
1890
|
+
node.innerHTML = sanitizeHTML(val);
|
|
1891
|
+
}
|
|
1899
1892
|
}
|
|
1900
1893
|
}
|
|
1901
1894
|
if (node.hasAttribute("data-rt-attr")) {
|
|
1902
1895
|
const attrStr = node.getAttribute("data-rt-attr");
|
|
1903
1896
|
if (attrStr) {
|
|
1904
|
-
attrStr
|
|
1905
|
-
const
|
|
1906
|
-
if (
|
|
1907
|
-
const attrName =
|
|
1908
|
-
const key =
|
|
1909
|
-
if (attrName && key
|
|
1910
|
-
|
|
1897
|
+
splitByUnquotedChar(attrStr, ",").forEach((b) => {
|
|
1898
|
+
const pair = splitFirstUnquotedColon(b);
|
|
1899
|
+
if (pair) {
|
|
1900
|
+
const attrName = pair[0].trim();
|
|
1901
|
+
const key = pair[1].trim();
|
|
1902
|
+
if (attrName && key) {
|
|
1903
|
+
const val = evaluateExpression(key, processedPayload);
|
|
1904
|
+
if (val !== void 0 && val !== null) {
|
|
1905
|
+
node.setAttribute(attrName, val);
|
|
1906
|
+
}
|
|
1911
1907
|
}
|
|
1912
1908
|
}
|
|
1913
1909
|
});
|
|
@@ -1916,13 +1912,13 @@ var DolphinModule = (() => {
|
|
|
1916
1912
|
if (node.hasAttribute("data-rt-class")) {
|
|
1917
1913
|
const classStr = node.getAttribute("data-rt-class");
|
|
1918
1914
|
if (classStr) {
|
|
1919
|
-
classStr
|
|
1920
|
-
const
|
|
1921
|
-
if (
|
|
1922
|
-
const className =
|
|
1923
|
-
const key =
|
|
1915
|
+
splitByUnquotedChar(classStr, ",").forEach((b) => {
|
|
1916
|
+
const pair = splitFirstUnquotedColon(b);
|
|
1917
|
+
if (pair) {
|
|
1918
|
+
const className = pair[0].trim();
|
|
1919
|
+
const key = pair[1].trim();
|
|
1924
1920
|
const classNames = className.split(/\s+/).filter(Boolean);
|
|
1925
|
-
if (processedPayload
|
|
1921
|
+
if (evaluateExpression(key, processedPayload)) {
|
|
1926
1922
|
classNames.forEach((c) => node.classList.add(c));
|
|
1927
1923
|
} else {
|
|
1928
1924
|
classNames.forEach((c) => node.classList.remove(c));
|
|
@@ -1934,7 +1930,7 @@ var DolphinModule = (() => {
|
|
|
1934
1930
|
if (node.hasAttribute("data-rt-if")) {
|
|
1935
1931
|
const key = node.getAttribute("data-rt-if");
|
|
1936
1932
|
if (key) {
|
|
1937
|
-
if (processedPayload
|
|
1933
|
+
if (evaluateExpression(key, processedPayload)) {
|
|
1938
1934
|
node.style.display = "";
|
|
1939
1935
|
} else {
|
|
1940
1936
|
node.style.display = "none";
|
|
@@ -1944,7 +1940,7 @@ var DolphinModule = (() => {
|
|
|
1944
1940
|
if (node.hasAttribute("data-rt-hide")) {
|
|
1945
1941
|
const key = node.getAttribute("data-rt-hide");
|
|
1946
1942
|
if (key) {
|
|
1947
|
-
if (processedPayload
|
|
1943
|
+
if (evaluateExpression(key, processedPayload)) {
|
|
1948
1944
|
node.style.display = "none";
|
|
1949
1945
|
} else {
|
|
1950
1946
|
node.style.display = "";
|
|
@@ -1994,21 +1990,35 @@ var DolphinModule = (() => {
|
|
|
1994
1990
|
return;
|
|
1995
1991
|
}
|
|
1996
1992
|
resolvingSet.add(src);
|
|
1997
|
-
|
|
1993
|
+
const hashIndex = src.indexOf("#");
|
|
1994
|
+
const url = hashIndex !== -1 ? src.substring(0, hashIndex) : src;
|
|
1995
|
+
const selector = hashIndex !== -1 ? src.substring(hashIndex) : null;
|
|
1996
|
+
let promise = componentPromiseCache.get(url);
|
|
1998
1997
|
if (!promise) {
|
|
1999
|
-
promise = fetch(
|
|
1998
|
+
promise = fetch(url).then((res) => {
|
|
2000
1999
|
if (!res.ok) throw new Error(`HTTP ${res.status}`);
|
|
2001
2000
|
return res.text();
|
|
2002
2001
|
});
|
|
2003
|
-
promise.catch(() => componentPromiseCache.delete(
|
|
2004
|
-
componentPromiseCache.set(
|
|
2002
|
+
promise.catch(() => componentPromiseCache.delete(url));
|
|
2003
|
+
componentPromiseCache.set(url, promise);
|
|
2005
2004
|
}
|
|
2006
2005
|
let content = "";
|
|
2007
2006
|
try {
|
|
2008
2007
|
content = await promise;
|
|
2008
|
+
if (selector && typeof DOMParser !== "undefined") {
|
|
2009
|
+
const parser = new DOMParser();
|
|
2010
|
+
const doc = parser.parseFromString(content, "text/html");
|
|
2011
|
+
const targetEl = doc.querySelector(selector);
|
|
2012
|
+
if (targetEl) {
|
|
2013
|
+
content = targetEl.outerHTML;
|
|
2014
|
+
} else {
|
|
2015
|
+
console.warn(`[Dolphin Component Warning]: Selector "${selector}" not found in imported file "${url}".`);
|
|
2016
|
+
content = `<span style="color:orange;font-weight:bold;">Selector ${selector} not found in ${url}</span>`;
|
|
2017
|
+
}
|
|
2018
|
+
}
|
|
2009
2019
|
} catch (err) {
|
|
2010
|
-
console.error(`[Dolphin Component Error]: Failed to fetch component "${
|
|
2011
|
-
content = `<span style="color:red;font-weight:bold;">Failed to import ${
|
|
2020
|
+
console.error(`[Dolphin Component Error]: Failed to fetch component "${url}":`, err);
|
|
2021
|
+
content = `<span style="color:red;font-weight:bold;">Failed to import ${url}</span>`;
|
|
2012
2022
|
}
|
|
2013
2023
|
el.innerHTML = sanitizeHTML(content);
|
|
2014
2024
|
el.removeAttribute("data-import");
|