@sonicjs-cms/core 2.17.2 → 2.18.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/{chunk-P4RAIX7B.cjs → chunk-3XP76LM7.cjs} +8 -8
- package/dist/{chunk-P4RAIX7B.cjs.map → chunk-3XP76LM7.cjs.map} +1 -1
- package/dist/{chunk-FXWF5D5V.cjs → chunk-56PLLVDG.cjs} +9 -3
- package/dist/chunk-56PLLVDG.cjs.map +1 -0
- package/dist/{chunk-Q3W6LCEN.cjs → chunk-74BFRAQS.cjs} +3 -3
- package/dist/{chunk-Q3W6LCEN.cjs.map → chunk-74BFRAQS.cjs.map} +1 -1
- package/dist/{chunk-LVGB5UU5.cjs → chunk-DAESIIWY.cjs} +2 -2
- package/dist/{chunk-LVGB5UU5.cjs.map → chunk-DAESIIWY.cjs.map} +1 -1
- package/dist/{chunk-K6QVIOTA.js → chunk-GH3HYA7D.js} +4 -4
- package/dist/{chunk-K6QVIOTA.js.map → chunk-GH3HYA7D.js.map} +1 -1
- package/dist/{chunk-2VY2G7OR.cjs → chunk-LTJ7P7RT.cjs} +242 -124
- package/dist/chunk-LTJ7P7RT.cjs.map +1 -0
- package/dist/{chunk-I2Z72YTD.js → chunk-NDS4S4AG.js} +3 -3
- package/dist/{chunk-I2Z72YTD.js.map → chunk-NDS4S4AG.js.map} +1 -1
- package/dist/{chunk-ITGOUYVN.js → chunk-OWJPOVFW.js} +2 -2
- package/dist/{chunk-ITGOUYVN.js.map → chunk-OWJPOVFW.js.map} +1 -1
- package/dist/{chunk-KJSZMIBF.js → chunk-RYRNZYND.js} +128 -10
- package/dist/chunk-RYRNZYND.js.map +1 -0
- package/dist/{chunk-NAYUXSNR.js → chunk-YK5IEGQZ.js} +9 -3
- package/dist/chunk-YK5IEGQZ.js.map +1 -0
- package/dist/index.cjs +196 -153
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +65 -22
- package/dist/index.js.map +1 -1
- package/dist/middleware.cjs +32 -32
- package/dist/middleware.js +3 -3
- package/dist/migrations-CW2IT5YP.cjs +13 -0
- package/dist/{migrations-Q7C6F2RM.cjs.map → migrations-CW2IT5YP.cjs.map} +1 -1
- package/dist/migrations-S42BOXI4.js +4 -0
- package/dist/{migrations-IFZLGVV3.js.map → migrations-S42BOXI4.js.map} +1 -1
- package/dist/routes.cjs +28 -28
- package/dist/routes.js +5 -5
- package/dist/services.cjs +23 -23
- package/dist/services.js +2 -2
- package/dist/utils.cjs +11 -11
- package/dist/utils.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-2VY2G7OR.cjs.map +0 -1
- package/dist/chunk-FXWF5D5V.cjs.map +0 -1
- package/dist/chunk-KJSZMIBF.js.map +0 -1
- package/dist/chunk-NAYUXSNR.js.map +0 -1
- package/dist/migrations-IFZLGVV3.js +0 -4
- package/dist/migrations-Q7C6F2RM.cjs +0 -13
package/dist/index.js
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
import { renderConfirmationDialog, getConfirmationDialogScript, api_default, api_media_default, api_system_default, admin_api_default, router, adminCollectionsRoutes, adminFormsRoutes, adminSettingsRoutes, public_forms_default, router2, admin_content_default, adminMediaRoutes, userProfilesPlugin, adminPluginRoutes, adminLogsRoutes, userRoutes, auth_default, test_cleanup_default } from './chunk-
|
|
2
|
-
export { ROUTES_INFO, admin_api_default as adminApiRoutes, adminCheckboxRoutes, admin_code_examples_default as adminCodeExamplesRoutes, adminCollectionsRoutes, admin_content_default as adminContentRoutes, router as adminDashboardRoutes, adminDesignRoutes, adminLogsRoutes, adminMediaRoutes, adminPluginRoutes, adminSettingsRoutes, admin_testimonials_default as adminTestimonialsRoutes, userRoutes as adminUsersRoutes, api_content_crud_default as apiContentCrudRoutes, api_media_default as apiMediaRoutes, api_default as apiRoutes, api_system_default as apiSystemRoutes, auth_default as authRoutes, createUserProfilesPlugin, defineUserProfile, getUserProfileConfig, userProfilesPlugin } from './chunk-
|
|
1
|
+
import { renderConfirmationDialog, getConfirmationDialogScript, api_default, api_media_default, api_system_default, admin_api_default, router, adminCollectionsRoutes, adminFormsRoutes, adminSettingsRoutes, public_forms_default, router2, admin_content_default, adminMediaRoutes, userProfilesPlugin, adminPluginRoutes, adminLogsRoutes, userRoutes, auth_default, test_cleanup_default } from './chunk-RYRNZYND.js';
|
|
2
|
+
export { ROUTES_INFO, admin_api_default as adminApiRoutes, adminCheckboxRoutes, admin_code_examples_default as adminCodeExamplesRoutes, adminCollectionsRoutes, admin_content_default as adminContentRoutes, router as adminDashboardRoutes, adminDesignRoutes, adminLogsRoutes, adminMediaRoutes, adminPluginRoutes, adminSettingsRoutes, admin_testimonials_default as adminTestimonialsRoutes, userRoutes as adminUsersRoutes, api_content_crud_default as apiContentCrudRoutes, api_media_default as apiMediaRoutes, api_default as apiRoutes, api_system_default as apiSystemRoutes, auth_default as authRoutes, createUserProfilesPlugin, defineUserProfile, getUserProfileConfig, userProfilesPlugin } from './chunk-RYRNZYND.js';
|
|
3
3
|
import { SettingsService, setAppInstance, schema_exports } from './chunk-QFWHAFEO.js';
|
|
4
4
|
export { Logger, apiTokens, collections, content, contentVersions, getLogger, initLogger, insertCollectionSchema, insertContentSchema, insertLogConfigSchema, insertMediaSchema, insertPluginActivityLogSchema, insertPluginAssetSchema, insertPluginHookSchema, insertPluginRouteSchema, insertPluginSchema, insertSystemLogSchema, insertUserSchema, insertWorkflowHistorySchema, logConfig, media, pluginActivityLog, pluginAssets, pluginHooks, pluginRoutes, plugins, selectCollectionSchema, selectContentSchema, selectLogConfigSchema, selectMediaSchema, selectPluginActivityLogSchema, selectPluginAssetSchema, selectPluginHookSchema, selectPluginRouteSchema, selectPluginSchema, selectSystemLogSchema, selectUserSchema, selectWorkflowHistorySchema, systemLogs, users, workflowHistory } from './chunk-QFWHAFEO.js';
|
|
5
|
-
import { requireAuth, getJwtExpirySecondsFromDb, AuthManager, metricsMiddleware, bootstrapMiddleware, securityHeadersMiddleware, csrfProtection, requireRole } from './chunk-
|
|
6
|
-
export { AuthManager, PermissionManager, bootstrapMiddleware, cacheHeaders, compressionMiddleware, detailedLoggingMiddleware, getActivePlugins, isPluginActive, logActivity, loggingMiddleware, optionalAuth, performanceLoggingMiddleware, requireActivePlugin, requireActivePlugins, requireAnyPermission, requireAuth, requirePermission, requireRole, securityHeadersMiddleware as securityHeaders, securityLoggingMiddleware } from './chunk-
|
|
7
|
-
import { PluginService, PLUGIN_REGISTRY } from './chunk-
|
|
8
|
-
export { PluginBootstrapService, PluginService as PluginServiceClass, backfillFormSubmissions, cleanupRemovedCollections, createContentFromSubmission, deriveCollectionSchemaFromFormio, deriveSubmissionTitle, fullCollectionSync, getAvailableCollectionNames, getManagedCollections, isCollectionManaged, loadCollectionConfig, loadCollectionConfigs, mapFormStatusToContentStatus, registerCollections, syncAllFormCollections, syncCollection, syncCollections, syncFormCollection, validateCollectionConfig } from './chunk-
|
|
9
|
-
export { MigrationService } from './chunk-
|
|
5
|
+
import { requireAuth, getJwtExpirySecondsFromDb, AuthManager, metricsMiddleware, bootstrapMiddleware, securityHeadersMiddleware, csrfProtection, requireRole } from './chunk-GH3HYA7D.js';
|
|
6
|
+
export { AuthManager, PermissionManager, bootstrapMiddleware, cacheHeaders, compressionMiddleware, detailedLoggingMiddleware, getActivePlugins, isPluginActive, logActivity, loggingMiddleware, optionalAuth, performanceLoggingMiddleware, requireActivePlugin, requireActivePlugins, requireAnyPermission, requireAuth, requirePermission, requireRole, securityHeadersMiddleware as securityHeaders, securityLoggingMiddleware } from './chunk-GH3HYA7D.js';
|
|
7
|
+
import { PluginService, PLUGIN_REGISTRY } from './chunk-YK5IEGQZ.js';
|
|
8
|
+
export { PluginBootstrapService, PluginService as PluginServiceClass, backfillFormSubmissions, cleanupRemovedCollections, createContentFromSubmission, deriveCollectionSchemaFromFormio, deriveSubmissionTitle, fullCollectionSync, getAvailableCollectionNames, getManagedCollections, isCollectionManaged, loadCollectionConfig, loadCollectionConfigs, mapFormStatusToContentStatus, registerCollections, syncAllFormCollections, syncCollection, syncCollections, syncFormCollection, validateCollectionConfig } from './chunk-YK5IEGQZ.js';
|
|
9
|
+
export { MigrationService } from './chunk-OWJPOVFW.js';
|
|
10
10
|
export { renderFilterBar } from './chunk-ON5ZMSU4.js';
|
|
11
11
|
import { renderAdminLayout } from './chunk-XWIA3HVX.js';
|
|
12
12
|
export { getConfirmationDialogScript, renderAlert, renderConfirmationDialog, renderForm, renderFormField, renderPagination, renderTable } from './chunk-XWIA3HVX.js';
|
|
@@ -14,8 +14,8 @@ import { init_admin_layout_catalyst_template, renderAdminLayoutCatalyst } from '
|
|
|
14
14
|
export { HookSystemImpl, HookUtils, PluginManager as PluginManagerClass, PluginRegistryImpl, PluginValidator as PluginValidatorClass, ScopedHookSystem as ScopedHookSystemClass } from './chunk-TFNTM3OA.js';
|
|
15
15
|
import { PluginBuilder, PluginHelpers } from './chunk-EXNEW5US.js';
|
|
16
16
|
export { PluginBuilder, PluginHelpers } from './chunk-EXNEW5US.js';
|
|
17
|
-
import { package_default, getCoreVersion } from './chunk-
|
|
18
|
-
export { QueryFilterBuilder, SONICJS_VERSION, TemplateRenderer, buildQuery, getCoreVersion, renderTemplate, templateRenderer } from './chunk-
|
|
17
|
+
import { package_default, getCoreVersion } from './chunk-NDS4S4AG.js';
|
|
18
|
+
export { QueryFilterBuilder, SONICJS_VERSION, TemplateRenderer, buildQuery, getCoreVersion, renderTemplate, templateRenderer } from './chunk-NDS4S4AG.js';
|
|
19
19
|
import './chunk-X7ZAEI5S.js';
|
|
20
20
|
export { metricsTracker } from './chunk-FICTAGD4.js';
|
|
21
21
|
export { escapeHtml, sanitizeInput, sanitizeObject } from './chunk-TQABQWOP.js';
|
|
@@ -1613,7 +1613,27 @@ var OTPService = class {
|
|
|
1613
1613
|
};
|
|
1614
1614
|
|
|
1615
1615
|
// src/plugins/core-plugins/otp-login-plugin/email-templates.ts
|
|
1616
|
+
function sanitizeColor(value) {
|
|
1617
|
+
if (!value) return "";
|
|
1618
|
+
if (/^#[0-9a-fA-F]{3,8}$/.test(value)) return value;
|
|
1619
|
+
if (/^[a-zA-Z]+$/.test(value)) return value;
|
|
1620
|
+
if (/^(rgb|rgba|hsl|hsla)\([0-9.,\s%]+\)$/.test(value)) return value;
|
|
1621
|
+
return "";
|
|
1622
|
+
}
|
|
1623
|
+
function escapeHtml3(value) {
|
|
1624
|
+
return value.replace(/&/g, "&").replace(/"/g, """).replace(/'/g, "'").replace(/</g, "<").replace(/>/g, ">");
|
|
1625
|
+
}
|
|
1616
1626
|
function renderOTPEmailHTML(data) {
|
|
1627
|
+
const logoUrl = data.logoUrl ? escapeHtml3(data.logoUrl) : "";
|
|
1628
|
+
const loginUrl = data.loginUrl ? escapeHtml3(data.loginUrl) : "";
|
|
1629
|
+
const appName = escapeHtml3(data.appName);
|
|
1630
|
+
const loginButtonText = escapeHtml3(
|
|
1631
|
+
data.loginButtonText && data.loginButtonText.trim() || `Sign in to ${data.appName}`
|
|
1632
|
+
);
|
|
1633
|
+
const logoWidth = Math.max(20, Math.min(600, Number(data.logoWidth) || 150));
|
|
1634
|
+
const logoBorderWidth = Math.max(0, Math.min(20, Number(data.logoBorderWidth) || 0));
|
|
1635
|
+
const logoBorderColor = sanitizeColor(data.logoBorderColor);
|
|
1636
|
+
const logoBorderStyle = logoBorderWidth > 0 && logoBorderColor ? `border: ${logoBorderWidth}px solid ${logoBorderColor}; border-radius: 8px;` : "";
|
|
1617
1637
|
return `<!DOCTYPE html>
|
|
1618
1638
|
<html>
|
|
1619
1639
|
<head>
|
|
@@ -1625,15 +1645,15 @@ function renderOTPEmailHTML(data) {
|
|
|
1625
1645
|
|
|
1626
1646
|
<div style="background: white; border-radius: 12px; overflow: hidden; box-shadow: 0 2px 8px rgba(0,0,0,0.1);">
|
|
1627
1647
|
|
|
1628
|
-
${
|
|
1648
|
+
${logoUrl ? `
|
|
1629
1649
|
<div style="text-align: center; padding: 30px 20px 20px;">
|
|
1630
|
-
<img src="${
|
|
1650
|
+
<img src="${logoUrl}" alt="${appName}" style="max-width: ${logoWidth}px; width: 100%; height: auto; ${logoBorderStyle}">
|
|
1631
1651
|
</div>
|
|
1632
1652
|
` : ""}
|
|
1633
1653
|
|
|
1634
1654
|
<div style="background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); color: white; padding: 40px 30px; text-align: center;">
|
|
1635
1655
|
<h1 style="margin: 0 0 10px 0; font-size: 32px; font-weight: 600;">Your Login Code</h1>
|
|
1636
|
-
<p style="margin: 0; opacity: 0.95; font-size: 16px;">Enter this code to sign in to ${
|
|
1656
|
+
<p style="margin: 0; opacity: 0.95; font-size: 16px;">Enter this code to sign in to ${appName}</p>
|
|
1637
1657
|
</div>
|
|
1638
1658
|
|
|
1639
1659
|
<div style="padding: 40px 30px;">
|
|
@@ -1643,6 +1663,14 @@ function renderOTPEmailHTML(data) {
|
|
|
1643
1663
|
</div>
|
|
1644
1664
|
</div>
|
|
1645
1665
|
|
|
1666
|
+
${loginUrl ? `
|
|
1667
|
+
<div style="text-align: center; margin: 0 0 30px 0;">
|
|
1668
|
+
<a href="${loginUrl}" style="display: inline-block; background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); color: white; text-decoration: none; padding: 14px 32px; border-radius: 8px; font-weight: 600; font-size: 16px;">
|
|
1669
|
+
${loginButtonText}
|
|
1670
|
+
</a>
|
|
1671
|
+
</div>
|
|
1672
|
+
` : ""}
|
|
1673
|
+
|
|
1646
1674
|
<div style="background: #fff3cd; border-left: 4px solid #ffc107; padding: 16px 20px; margin: 0 0 30px 0; border-radius: 6px;">
|
|
1647
1675
|
<p style="margin: 0; font-size: 14px; color: #856404;">
|
|
1648
1676
|
<strong>\u26A0\uFE0F This code expires in ${data.expiryMinutes} minutes</strong>
|
|
@@ -1664,7 +1692,7 @@ function renderOTPEmailHTML(data) {
|
|
|
1664
1692
|
\u{1F512} Security Notice
|
|
1665
1693
|
</p>
|
|
1666
1694
|
<p style="margin: 0; font-size: 13px; color: #004080; line-height: 1.6;">
|
|
1667
|
-
Never share this code with anyone. ${
|
|
1695
|
+
Never share this code with anyone. ${appName} will never ask you for this code via phone, email, or social media.
|
|
1668
1696
|
</p>
|
|
1669
1697
|
</div>
|
|
1670
1698
|
</div>
|
|
@@ -1676,22 +1704,23 @@ function renderOTPEmailHTML(data) {
|
|
|
1676
1704
|
</p>
|
|
1677
1705
|
|
|
1678
1706
|
<div style="text-align: center; color: #999; font-size: 12px; line-height: 1.6;">
|
|
1679
|
-
<p style="margin: 5px 0;">This email was sent to ${data.email}</p>
|
|
1680
|
-
${data.ipAddress ? `<p style="margin: 5px 0;">IP Address: ${data.ipAddress}</p>` : ""}
|
|
1681
|
-
<p style="margin: 5px 0;">Time: ${data.timestamp}</p>
|
|
1707
|
+
<p style="margin: 5px 0;">This email was sent to ${escapeHtml3(data.email)}</p>
|
|
1708
|
+
${data.ipAddress ? `<p style="margin: 5px 0;">IP Address: ${escapeHtml3(data.ipAddress)}</p>` : ""}
|
|
1709
|
+
<p style="margin: 5px 0;">Time: ${escapeHtml3(data.timestamp)}</p>
|
|
1682
1710
|
</div>
|
|
1683
1711
|
</div>
|
|
1684
1712
|
|
|
1685
1713
|
</div>
|
|
1686
1714
|
|
|
1687
1715
|
<div style="text-align: center; padding: 20px; color: #999; font-size: 12px;">
|
|
1688
|
-
<p style="margin: 0;">© ${(/* @__PURE__ */ new Date()).getFullYear()} ${
|
|
1716
|
+
<p style="margin: 0;">© ${(/* @__PURE__ */ new Date()).getFullYear()} ${appName}. All rights reserved.</p>
|
|
1689
1717
|
</div>
|
|
1690
1718
|
|
|
1691
1719
|
</body>
|
|
1692
1720
|
</html>`;
|
|
1693
1721
|
}
|
|
1694
1722
|
function renderOTPEmailText(data) {
|
|
1723
|
+
const ctaLabel = data.loginButtonText && data.loginButtonText.trim() || `Sign in to ${data.appName}`;
|
|
1695
1724
|
return `Your Login Code for ${data.appName}
|
|
1696
1725
|
|
|
1697
1726
|
Your one-time verification code is:
|
|
@@ -1699,6 +1728,9 @@ Your one-time verification code is:
|
|
|
1699
1728
|
${data.code}
|
|
1700
1729
|
|
|
1701
1730
|
This code expires in ${data.expiryMinutes} minutes.
|
|
1731
|
+
${data.loginUrl ? `
|
|
1732
|
+
${ctaLabel}: ${data.loginUrl}
|
|
1733
|
+
` : ""}
|
|
1702
1734
|
|
|
1703
1735
|
Quick Tips:
|
|
1704
1736
|
\u2022 Enter the code exactly as shown (${data.codeLength} digits)
|
|
@@ -1739,7 +1771,13 @@ var DEFAULT_SETTINGS = {
|
|
|
1739
1771
|
codeExpiryMinutes: 10,
|
|
1740
1772
|
maxAttempts: 3,
|
|
1741
1773
|
rateLimitPerHour: 5,
|
|
1742
|
-
allowNewUserRegistration: false
|
|
1774
|
+
allowNewUserRegistration: false,
|
|
1775
|
+
logoUrl: "",
|
|
1776
|
+
logoWidth: 150,
|
|
1777
|
+
logoBorderWidth: 0,
|
|
1778
|
+
logoBorderColor: "#ffffff",
|
|
1779
|
+
loginUrl: "",
|
|
1780
|
+
loginButtonText: ""
|
|
1743
1781
|
};
|
|
1744
1782
|
function createOTPLoginPlugin() {
|
|
1745
1783
|
const builder = PluginBuilder.create({
|
|
@@ -1829,7 +1867,12 @@ function createOTPLoginPlugin() {
|
|
|
1829
1867
|
ipAddress,
|
|
1830
1868
|
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
1831
1869
|
appName: siteName,
|
|
1832
|
-
logoUrl: settings.logoUrl || ""
|
|
1870
|
+
logoUrl: settings.logoUrl || "",
|
|
1871
|
+
logoWidth: settings.logoWidth,
|
|
1872
|
+
logoBorderWidth: settings.logoBorderWidth,
|
|
1873
|
+
logoBorderColor: settings.logoBorderColor || "",
|
|
1874
|
+
loginUrl: settings.loginUrl || "",
|
|
1875
|
+
loginButtonText: settings.loginButtonText || ""
|
|
1833
1876
|
});
|
|
1834
1877
|
const emailPlugin2 = await db.prepare(`
|
|
1835
1878
|
SELECT settings FROM plugins WHERE id = 'email'
|
|
@@ -7868,7 +7911,7 @@ adminRoutes4.get("/", async (c) => {
|
|
|
7868
7911
|
<div class="divide-y divide-zinc-950/5 dark:divide-white/10">
|
|
7869
7912
|
${topPages.length > 0 ? topPages.map((p) => `
|
|
7870
7913
|
<div class="flex items-center justify-between px-6 py-3">
|
|
7871
|
-
<span class="text-sm text-zinc-700 dark:text-zinc-300 font-mono truncate">${
|
|
7914
|
+
<span class="text-sm text-zinc-700 dark:text-zinc-300 font-mono truncate">${escapeHtml4(p.path)}</span>
|
|
7872
7915
|
<span class="text-sm font-medium text-zinc-500 dark:text-zinc-400">${p.views}</span>
|
|
7873
7916
|
</div>
|
|
7874
7917
|
`).join("") : `
|
|
@@ -7897,7 +7940,7 @@ adminRoutes4.get("/", async (c) => {
|
|
|
7897
7940
|
<tbody class="divide-y divide-zinc-950/5 dark:divide-white/10">
|
|
7898
7941
|
${recentActivity.length > 0 ? recentActivity.map((a) => `
|
|
7899
7942
|
<tr>
|
|
7900
|
-
<td class="px-6 py-2 font-mono text-zinc-700 dark:text-zinc-300 truncate max-w-xs">${
|
|
7943
|
+
<td class="px-6 py-2 font-mono text-zinc-700 dark:text-zinc-300 truncate max-w-xs">${escapeHtml4(a.url || "")}</td>
|
|
7901
7944
|
<td class="px-6 py-2"><span class="inline-flex items-center rounded px-1.5 py-0.5 text-xs font-medium ${a.method === "GET" ? "bg-green-50 text-green-700 dark:bg-green-900/30 dark:text-green-400" : "bg-blue-50 text-blue-700 dark:bg-blue-900/30 dark:text-blue-400"}">${a.method || ""}</span></td>
|
|
7902
7945
|
<td class="px-6 py-2"><span class="inline-flex items-center rounded px-1.5 py-0.5 text-xs font-medium ${(a.status_code || 0) >= 400 ? "bg-red-50 text-red-700 dark:bg-red-900/30 dark:text-red-400" : "bg-green-50 text-green-700 dark:bg-green-900/30 dark:text-green-400"}">${a.status_code || ""}</span></td>
|
|
7903
7946
|
<td class="px-6 py-2 text-zinc-500 dark:text-zinc-400">${a.duration || 0}ms</td>
|
|
@@ -7927,7 +7970,7 @@ adminRoutes4.get("/", async (c) => {
|
|
|
7927
7970
|
dynamicMenuItems: c.get("pluginMenuItems")
|
|
7928
7971
|
}));
|
|
7929
7972
|
});
|
|
7930
|
-
function
|
|
7973
|
+
function escapeHtml4(str) {
|
|
7931
7974
|
return str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
|
7932
7975
|
}
|
|
7933
7976
|
|