strapi-plugin-magic-sessionmanager 4.2.16 → 4.3.1

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.
Files changed (23) hide show
  1. package/dist/_chunks/{Analytics-BC4jdzBT.mjs → Analytics-sX94t6D9.mjs} +2 -2
  2. package/dist/_chunks/{Analytics-D6RGeWO5.js → Analytics-tOOj5T92.js} +2 -2
  3. package/dist/_chunks/{App-CahdcIEB.mjs → App-Cs4KKd3L.mjs} +155 -54
  4. package/dist/_chunks/{App-BkaaNOpt.js → App-D4qVym6y.js} +154 -53
  5. package/dist/_chunks/{License-BFx721o7.mjs → License-CN5YpqIu.mjs} +1 -1
  6. package/dist/_chunks/{License-C8VnKtV1.js → License-kfVcskd3.js} +1 -1
  7. package/dist/_chunks/{OnlineUsersWidget-uJ6DZB_N.js → OnlineUsersWidget-Cg3R7602.js} +1 -1
  8. package/dist/_chunks/{OnlineUsersWidget-r2ZgSnok.mjs → OnlineUsersWidget-ytykP_tA.mjs} +1 -1
  9. package/dist/_chunks/{Settings-jtZRw_VP.js → Settings-DVRIrGho.js} +26 -54
  10. package/dist/_chunks/{Settings-DOUUwwxB.mjs → Settings-XloJ-aHl.mjs} +26 -54
  11. package/dist/_chunks/StyledButtons-D2EbG_Zw.js +419 -0
  12. package/dist/_chunks/StyledButtons-fbNVRlMY.mjs +418 -0
  13. package/dist/_chunks/{UpgradePage-mqr6dLVY.mjs → UpgradePage-C441wvPX.mjs} +1 -1
  14. package/dist/_chunks/{UpgradePage-Bwy_1m6f.js → UpgradePage-D2FRalDz.js} +1 -1
  15. package/dist/_chunks/{index-BuxWeACw.js → index-DtBfKBne.js} +236 -190
  16. package/dist/_chunks/{index-CUSrDKCG.mjs → index-Ij0JRf9W.mjs} +237 -193
  17. package/dist/_chunks/{useLicense-xjKLHcVq.mjs → useLicense-DJEDGSap.mjs} +1 -1
  18. package/dist/_chunks/{useLicense-D7FSpX8c.js → useLicense-NCFYHpDd.js} +1 -1
  19. package/dist/admin/index.js +1 -1
  20. package/dist/admin/index.mjs +1 -1
  21. package/dist/server/index.js +35938 -169
  22. package/dist/server/index.mjs +35927 -167
  23. package/package.json +7 -7
@@ -4,8 +4,8 @@ import { useFetchClient } from "@strapi/strapi/admin";
4
4
  import styled, { css, keyframes } from "styled-components";
5
5
  import { Loader, Typography, Box, Flex, Badge } from "@strapi/design-system";
6
6
  import { ChartBubble, Crown, User, Clock, Monitor } from "@strapi/icons";
7
- import { a as pluginId } from "./index-CUSrDKCG.mjs";
8
- import { u as useLicense } from "./useLicense-xjKLHcVq.mjs";
7
+ import { a as pluginId } from "./index-Ij0JRf9W.mjs";
8
+ import { u as useLicense } from "./useLicense-DJEDGSap.mjs";
9
9
  const theme = {
10
10
  colors: {
11
11
  primary: { 100: "#E0F2FE", 500: "#0EA5E9", 600: "#0284C7" },
@@ -6,8 +6,8 @@ const admin = require("@strapi/strapi/admin");
6
6
  const styled = require("styled-components");
7
7
  const designSystem = require("@strapi/design-system");
8
8
  const icons = require("@strapi/icons");
9
- const index = require("./index-BuxWeACw.js");
10
- const useLicense = require("./useLicense-D7FSpX8c.js");
9
+ const index = require("./index-DtBfKBne.js");
10
+ const useLicense = require("./useLicense-NCFYHpDd.js");
11
11
  const _interopDefault = (e) => e && e.__esModule ? e : { default: e };
12
12
  const styled__default = /* @__PURE__ */ _interopDefault(styled);
13
13
  const theme = {
@@ -3,10 +3,11 @@ import { useState, useEffect } from "react";
3
3
  import { useIntl } from "react-intl";
4
4
  import { useFetchClient, useNotification } from "@strapi/strapi/admin";
5
5
  import styled, { css, keyframes } from "styled-components";
6
- import { p as parseUserAgent, a as pluginId, g as getTranslation } from "./index-CUSrDKCG.mjs";
7
- import { Modal, Flex, Box, Typography, Badge, Divider, Button, Loader, SingleSelect, SingleSelectOption, Thead, Tr, Th, Tbody, Td, Table, TextInput } from "@strapi/design-system";
6
+ import { p as parseUserAgent, a as pluginId, g as getTranslation } from "./index-Ij0JRf9W.mjs";
7
+ import { Modal, Flex, Box, Typography, Divider, Button, Loader, SingleSelect, SingleSelectOption, Thead, Tr, Th, Tbody, Td, Table, TextInput } from "@strapi/design-system";
8
8
  import { Check, Information, Monitor, Server, Clock, Cross, Earth, Shield, Crown, Phone, Download, User, Eye, Trash, Search, Key } from "@strapi/icons";
9
- import { u as useLicense } from "./useLicense-xjKLHcVq.mjs";
9
+ import { u as useLicense } from "./useLicense-DJEDGSap.mjs";
10
+ import { S as ShowHideButton, T as TertiaryButton, D as DangerButton, I as IconButtonPrimary, a as IconButtonWarning, b as IconButtonDanger } from "./StyledButtons-fbNVRlMY.mjs";
10
11
  import { useNavigate } from "react-router-dom";
11
12
  const theme = {
12
13
  colors: {
@@ -85,6 +86,74 @@ const SectionTitle = styled(Typography)`
85
86
  const Section = styled(Box)`
86
87
  margin-bottom: 24px;
87
88
  `;
89
+ const ModalStatusBadge = styled.span`
90
+ display: inline-flex;
91
+ align-items: center;
92
+ gap: 8px;
93
+ padding: 10px 24px;
94
+ border-radius: 24px;
95
+ font-size: 14px;
96
+ font-weight: 700;
97
+ letter-spacing: 0.5px;
98
+ text-transform: uppercase;
99
+
100
+ ${(props) => props.$online && `
101
+ background: linear-gradient(135deg, #DCFCE7 0%, #BBF7D0 100%);
102
+ color: #166534;
103
+ border: 2px solid #86EFAC;
104
+ box-shadow: 0 4px 12px rgba(34, 197, 94, 0.2);
105
+ `}
106
+
107
+ ${(props) => !props.$online && `
108
+ background: linear-gradient(135deg, #F3F4F6 0%, #E5E7EB 100%);
109
+ color: #4B5563;
110
+ border: 2px solid #D1D5DB;
111
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
112
+ `}
113
+ `;
114
+ const StatusDot$1 = styled.span`
115
+ width: 10px;
116
+ height: 10px;
117
+ border-radius: 50%;
118
+
119
+ ${(props) => props.$online && `
120
+ background: #22C55E;
121
+ box-shadow: 0 0 8px rgba(34, 197, 94, 0.6);
122
+ animation: pulse-green 2s ease-in-out infinite;
123
+ `}
124
+
125
+ ${(props) => !props.$online && `
126
+ background: #9CA3AF;
127
+ `}
128
+
129
+ @keyframes pulse-green {
130
+ 0%, 100% { opacity: 1; transform: scale(1); }
131
+ 50% { opacity: 0.7; transform: scale(1.15); }
132
+ }
133
+ `;
134
+ const PremiumButton = styled.button`
135
+ background: linear-gradient(135deg, #F59E0B 0%, #D97706 100%);
136
+ color: white;
137
+ border: none;
138
+ padding: 12px 24px;
139
+ border-radius: 10px;
140
+ font-weight: 700;
141
+ font-size: 14px;
142
+ cursor: pointer;
143
+ transition: all 0.2s ease;
144
+ box-shadow: 0 4px 12px rgba(245, 158, 11, 0.3);
145
+ margin-top: 8px;
146
+
147
+ &:hover {
148
+ background: linear-gradient(135deg, #D97706 0%, #B45309 100%);
149
+ transform: translateY(-2px);
150
+ box-shadow: 0 6px 16px rgba(245, 158, 11, 0.4);
151
+ }
152
+
153
+ &:active {
154
+ transform: translateY(0);
155
+ }
156
+ `;
88
157
  const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
89
158
  const { formatMessage } = useIntl();
90
159
  const { get, post } = useFetchClient();
@@ -196,16 +265,10 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
196
265
  ] })
197
266
  ] }) }),
198
267
  /* @__PURE__ */ jsx(Modal.Body, { children: /* @__PURE__ */ jsxs(Box, { padding: 6, children: [
199
- /* @__PURE__ */ jsx(Flex, { justifyContent: "center", style: { marginBottom: "24px" }, children: /* @__PURE__ */ jsx(
200
- Badge,
201
- {
202
- backgroundColor: isOnline ? "success600" : "neutral600",
203
- textColor: "neutral0",
204
- size: "M",
205
- style: { fontSize: "14px", padding: "8px 20px", fontWeight: "600" },
206
- children: isOnline ? t("modal.status.online", "ONLINE") : t("modal.status.offline", "OFFLINE")
207
- }
208
- ) }),
268
+ /* @__PURE__ */ jsx(Flex, { justifyContent: "center", style: { marginBottom: "24px" }, children: /* @__PURE__ */ jsxs(ModalStatusBadge, { $online: isOnline, children: [
269
+ /* @__PURE__ */ jsx(StatusDot$1, { $online: isOnline }),
270
+ isOnline ? t("modal.status.online", "ONLINE") : t("modal.status.offline", "OFFLINE")
271
+ ] }) }),
209
272
  /* @__PURE__ */ jsx(Divider, { style: { marginBottom: "24px" } }),
210
273
  /* @__PURE__ */ jsxs(TwoColumnGrid, { children: [
211
274
  /* @__PURE__ */ jsxs(Box, { children: [
@@ -339,19 +402,9 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
339
402
  /* @__PURE__ */ jsx(Typography, { variant: "beta", style: { color: "#92400e", fontWeight: "700" }, children: t("modal.premium.title", "Location and Security Analysis") }),
340
403
  /* @__PURE__ */ jsx(Typography, { variant: "omega", style: { color: "#78350f", fontSize: "14px", lineHeight: "1.6" }, children: t("modal.premium.description", "Unlock premium features to get IP geolocation, security scoring, and VPN/Proxy detection for every session") }),
341
404
  /* @__PURE__ */ jsx(
342
- Button,
405
+ PremiumButton,
343
406
  {
344
- variant: "secondary",
345
- size: "M",
346
407
  onClick: () => window.open("https://magicapi.fitlex.me", "_blank"),
347
- style: {
348
- background: "linear-gradient(135deg, #f59e0b 0%, #d97706 100%)",
349
- color: "white",
350
- border: "none",
351
- fontWeight: "600",
352
- marginTop: "8px",
353
- boxShadow: "0 4px 12px rgba(245, 158, 11, 0.3)"
354
- },
355
408
  children: t("modal.premium.upgrade", "Upgrade to Premium")
356
409
  }
357
410
  )
@@ -362,13 +415,11 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
362
415
  /* @__PURE__ */ jsxs(Flex, { justifyContent: "space-between", alignItems: "center", style: { marginBottom: "12px" }, children: [
363
416
  /* @__PURE__ */ jsx(SectionTitle, { style: { marginBottom: 0, paddingBottom: 0, border: "none" }, children: t("modal.section.technical", "Technical Details") }),
364
417
  /* @__PURE__ */ jsx(
365
- Button,
418
+ ShowHideButton,
366
419
  {
367
- variant: "tertiary",
368
420
  size: "S",
369
421
  onClick: () => setShowUserAgent(!showUserAgent),
370
- style: { fontSize: "12px" },
371
- children: showUserAgent ? `▲ ${t("modal.technical.hide", "Hide Details")}` : `▼ ${t("modal.technical.show", "Show Details")}`
422
+ children: showUserAgent ? t("modal.technical.hide", "Hide Details") : t("modal.technical.show", "Show Details")
372
423
  }
373
424
  )
374
425
  ] }),
@@ -393,12 +444,11 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
393
444
  ] })
394
445
  ] }) }),
395
446
  /* @__PURE__ */ jsx(Modal.Footer, { children: /* @__PURE__ */ jsxs(Flex, { justifyContent: "space-between", style: { width: "100%" }, children: [
396
- /* @__PURE__ */ jsx(Button, { onClick: onClose, variant: "tertiary", children: t("modal.actions.close", "Close") }),
447
+ /* @__PURE__ */ jsx(TertiaryButton, { onClick: onClose, children: t("modal.actions.close", "Close") }),
397
448
  /* @__PURE__ */ jsx(
398
- Button,
449
+ DangerButton,
399
450
  {
400
451
  onClick: handleTerminate,
401
- variant: "danger",
402
452
  disabled: !session.isActive || terminating,
403
453
  loading: terminating,
404
454
  startIcon: /* @__PURE__ */ jsx(Cross, {}),
@@ -690,7 +740,7 @@ const StyledTable = styled(Table)`
690
740
  }
691
741
  }
692
742
  `;
693
- const OnlineIndicator = styled.div`
743
+ styled.div`
694
744
  width: 10px;
695
745
  height: 10px;
696
746
  border-radius: 50%;
@@ -744,11 +794,76 @@ const StyledSearchInput = styled.input`
744
794
  }
745
795
  `;
746
796
  const ActionButtons = styled(Flex)`
747
- opacity: 0.7;
797
+ opacity: 0.85;
748
798
  transition: all ${theme.transitions.fast};
749
- gap: ${theme.spacing.xs};
799
+ gap: 8px;
750
800
  justify-content: flex-end;
751
801
  `;
802
+ const StatusBadge = styled.span`
803
+ display: inline-flex;
804
+ align-items: center;
805
+ gap: 6px;
806
+ padding: 6px 12px;
807
+ border-radius: 20px;
808
+ font-size: 12px;
809
+ font-weight: 600;
810
+ letter-spacing: 0.3px;
811
+ text-transform: uppercase;
812
+ transition: all 0.2s ease;
813
+
814
+ ${(props) => props.$status === "active" && `
815
+ background: linear-gradient(135deg, #DCFCE7 0%, #BBF7D0 100%);
816
+ color: #15803D;
817
+ border: 1px solid #86EFAC;
818
+ `}
819
+
820
+ ${(props) => props.$status === "idle" && `
821
+ background: linear-gradient(135deg, #FEF3C7 0%, #FDE68A 100%);
822
+ color: #A16207;
823
+ border: 1px solid #FCD34D;
824
+ `}
825
+
826
+ ${(props) => props.$status === "loggedout" && `
827
+ background: linear-gradient(135deg, #FEE2E2 0%, #FECACA 100%);
828
+ color: #B91C1C;
829
+ border: 1px solid #FCA5A5;
830
+ `}
831
+
832
+ ${(props) => props.$status === "terminated" && `
833
+ background: linear-gradient(135deg, #F3F4F6 0%, #E5E7EB 100%);
834
+ color: #4B5563;
835
+ border: 1px solid #D1D5DB;
836
+ `}
837
+ `;
838
+ const StatusDot = styled.span`
839
+ width: 8px;
840
+ height: 8px;
841
+ border-radius: 50%;
842
+ flex-shrink: 0;
843
+
844
+ ${(props) => props.$status === "active" && `
845
+ background: #22C55E;
846
+ box-shadow: 0 0 6px rgba(34, 197, 94, 0.6);
847
+ animation: pulse-green 2s ease-in-out infinite;
848
+ `}
849
+
850
+ ${(props) => props.$status === "idle" && `
851
+ background: #F59E0B;
852
+ `}
853
+
854
+ ${(props) => props.$status === "loggedout" && `
855
+ background: #EF4444;
856
+ `}
857
+
858
+ ${(props) => props.$status === "terminated" && `
859
+ background: #9CA3AF;
860
+ `}
861
+
862
+ @keyframes pulse-green {
863
+ 0%, 100% { opacity: 1; transform: scale(1); }
864
+ 50% { opacity: 0.7; transform: scale(1.1); }
865
+ }
866
+ `;
752
867
  const ClickableRow = styled(Tr)`
753
868
  cursor: pointer;
754
869
 
@@ -1163,17 +1278,9 @@ const HomePage = () => {
1163
1278
  opacity: config.opacity || 1
1164
1279
  },
1165
1280
  children: [
1166
- /* @__PURE__ */ jsx(Td, { children: /* @__PURE__ */ jsxs(Flex, { alignItems: "center", gap: 2, children: [
1167
- /* @__PURE__ */ jsx(OnlineIndicator, { $online: config.indicator }),
1168
- /* @__PURE__ */ jsx(
1169
- Badge,
1170
- {
1171
- backgroundColor: config.badgeColor,
1172
- textColor: "neutral0",
1173
- size: "S",
1174
- children: config.label
1175
- }
1176
- )
1281
+ /* @__PURE__ */ jsx(Td, { children: /* @__PURE__ */ jsxs(StatusBadge, { $status: sessionStatus, children: [
1282
+ /* @__PURE__ */ jsx(StatusDot, { $status: sessionStatus }),
1283
+ config.label
1177
1284
  ] }) }),
1178
1285
  /* @__PURE__ */ jsx(Td, { children: /* @__PURE__ */ jsxs(Flex, { direction: "column", alignItems: "flex-start", children: [
1179
1286
  /* @__PURE__ */ jsx(Typography, { fontWeight: "semiBold", ellipsis: true, children: session.user?.username || session.user?.email || t("homepage.user.unknown", "Unknown") }),
@@ -1198,10 +1305,8 @@ const HomePage = () => {
1198
1305
  ] }) }),
1199
1306
  /* @__PURE__ */ jsx(Td, { onClick: (e) => e.stopPropagation(), children: /* @__PURE__ */ jsxs(ActionButtons, { className: "action-buttons", children: [
1200
1307
  /* @__PURE__ */ jsx(
1201
- Button,
1308
+ IconButtonPrimary,
1202
1309
  {
1203
- variant: "secondary",
1204
- size: "S",
1205
1310
  onClick: (e) => {
1206
1311
  e.stopPropagation();
1207
1312
  handleSessionClick(session);
@@ -1211,10 +1316,8 @@ const HomePage = () => {
1211
1316
  }
1212
1317
  ),
1213
1318
  /* @__PURE__ */ jsx(
1214
- Button,
1319
+ IconButtonWarning,
1215
1320
  {
1216
- variant: "danger-light",
1217
- size: "S",
1218
1321
  onClick: (e) => {
1219
1322
  e.stopPropagation();
1220
1323
  handleTerminateSession(session.id);
@@ -1225,10 +1328,8 @@ const HomePage = () => {
1225
1328
  }
1226
1329
  ),
1227
1330
  /* @__PURE__ */ jsx(
1228
- Button,
1331
+ IconButtonDanger,
1229
1332
  {
1230
- variant: "danger",
1231
- size: "S",
1232
1333
  onClick: (e) => {
1233
1334
  e.stopPropagation();
1234
1335
  handleDeleteSession(session.id);
@@ -5,10 +5,11 @@ const react = require("react");
5
5
  const reactIntl = require("react-intl");
6
6
  const admin = require("@strapi/strapi/admin");
7
7
  const styled = require("styled-components");
8
- const index = require("./index-BuxWeACw.js");
8
+ const index = require("./index-DtBfKBne.js");
9
9
  const designSystem = require("@strapi/design-system");
10
10
  const icons = require("@strapi/icons");
11
- const useLicense = require("./useLicense-D7FSpX8c.js");
11
+ const useLicense = require("./useLicense-NCFYHpDd.js");
12
+ const StyledButtons = require("./StyledButtons-D2EbG_Zw.js");
12
13
  const reactRouterDom = require("react-router-dom");
13
14
  const _interopDefault = (e) => e && e.__esModule ? e : { default: e };
14
15
  const styled__default = /* @__PURE__ */ _interopDefault(styled);
@@ -89,6 +90,74 @@ const SectionTitle = styled__default.default(designSystem.Typography)`
89
90
  const Section = styled__default.default(designSystem.Box)`
90
91
  margin-bottom: 24px;
91
92
  `;
93
+ const ModalStatusBadge = styled__default.default.span`
94
+ display: inline-flex;
95
+ align-items: center;
96
+ gap: 8px;
97
+ padding: 10px 24px;
98
+ border-radius: 24px;
99
+ font-size: 14px;
100
+ font-weight: 700;
101
+ letter-spacing: 0.5px;
102
+ text-transform: uppercase;
103
+
104
+ ${(props) => props.$online && `
105
+ background: linear-gradient(135deg, #DCFCE7 0%, #BBF7D0 100%);
106
+ color: #166534;
107
+ border: 2px solid #86EFAC;
108
+ box-shadow: 0 4px 12px rgba(34, 197, 94, 0.2);
109
+ `}
110
+
111
+ ${(props) => !props.$online && `
112
+ background: linear-gradient(135deg, #F3F4F6 0%, #E5E7EB 100%);
113
+ color: #4B5563;
114
+ border: 2px solid #D1D5DB;
115
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
116
+ `}
117
+ `;
118
+ const StatusDot$1 = styled__default.default.span`
119
+ width: 10px;
120
+ height: 10px;
121
+ border-radius: 50%;
122
+
123
+ ${(props) => props.$online && `
124
+ background: #22C55E;
125
+ box-shadow: 0 0 8px rgba(34, 197, 94, 0.6);
126
+ animation: pulse-green 2s ease-in-out infinite;
127
+ `}
128
+
129
+ ${(props) => !props.$online && `
130
+ background: #9CA3AF;
131
+ `}
132
+
133
+ @keyframes pulse-green {
134
+ 0%, 100% { opacity: 1; transform: scale(1); }
135
+ 50% { opacity: 0.7; transform: scale(1.15); }
136
+ }
137
+ `;
138
+ const PremiumButton = styled__default.default.button`
139
+ background: linear-gradient(135deg, #F59E0B 0%, #D97706 100%);
140
+ color: white;
141
+ border: none;
142
+ padding: 12px 24px;
143
+ border-radius: 10px;
144
+ font-weight: 700;
145
+ font-size: 14px;
146
+ cursor: pointer;
147
+ transition: all 0.2s ease;
148
+ box-shadow: 0 4px 12px rgba(245, 158, 11, 0.3);
149
+ margin-top: 8px;
150
+
151
+ &:hover {
152
+ background: linear-gradient(135deg, #D97706 0%, #B45309 100%);
153
+ transform: translateY(-2px);
154
+ box-shadow: 0 6px 16px rgba(245, 158, 11, 0.4);
155
+ }
156
+
157
+ &:active {
158
+ transform: translateY(0);
159
+ }
160
+ `;
92
161
  const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
93
162
  const { formatMessage } = reactIntl.useIntl();
94
163
  const { get, post } = admin.useFetchClient();
@@ -200,16 +269,10 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
200
269
  ] })
201
270
  ] }) }),
202
271
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Modal.Body, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Box, { padding: 6, children: [
203
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.Flex, { justifyContent: "center", style: { marginBottom: "24px" }, children: /* @__PURE__ */ jsxRuntime.jsx(
204
- designSystem.Badge,
205
- {
206
- backgroundColor: isOnline ? "success600" : "neutral600",
207
- textColor: "neutral0",
208
- size: "M",
209
- style: { fontSize: "14px", padding: "8px 20px", fontWeight: "600" },
210
- children: isOnline ? t("modal.status.online", "ONLINE") : t("modal.status.offline", "OFFLINE")
211
- }
212
- ) }),
272
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Flex, { justifyContent: "center", style: { marginBottom: "24px" }, children: /* @__PURE__ */ jsxRuntime.jsxs(ModalStatusBadge, { $online: isOnline, children: [
273
+ /* @__PURE__ */ jsxRuntime.jsx(StatusDot$1, { $online: isOnline }),
274
+ isOnline ? t("modal.status.online", "ONLINE") : t("modal.status.offline", "OFFLINE")
275
+ ] }) }),
213
276
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Divider, { style: { marginBottom: "24px" } }),
214
277
  /* @__PURE__ */ jsxRuntime.jsxs(TwoColumnGrid, { children: [
215
278
  /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Box, { children: [
@@ -343,19 +406,9 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
343
406
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { variant: "beta", style: { color: "#92400e", fontWeight: "700" }, children: t("modal.premium.title", "Location and Security Analysis") }),
344
407
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { variant: "omega", style: { color: "#78350f", fontSize: "14px", lineHeight: "1.6" }, children: t("modal.premium.description", "Unlock premium features to get IP geolocation, security scoring, and VPN/Proxy detection for every session") }),
345
408
  /* @__PURE__ */ jsxRuntime.jsx(
346
- designSystem.Button,
409
+ PremiumButton,
347
410
  {
348
- variant: "secondary",
349
- size: "M",
350
411
  onClick: () => window.open("https://magicapi.fitlex.me", "_blank"),
351
- style: {
352
- background: "linear-gradient(135deg, #f59e0b 0%, #d97706 100%)",
353
- color: "white",
354
- border: "none",
355
- fontWeight: "600",
356
- marginTop: "8px",
357
- boxShadow: "0 4px 12px rgba(245, 158, 11, 0.3)"
358
- },
359
412
  children: t("modal.premium.upgrade", "Upgrade to Premium")
360
413
  }
361
414
  )
@@ -366,13 +419,11 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
366
419
  /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { justifyContent: "space-between", alignItems: "center", style: { marginBottom: "12px" }, children: [
367
420
  /* @__PURE__ */ jsxRuntime.jsx(SectionTitle, { style: { marginBottom: 0, paddingBottom: 0, border: "none" }, children: t("modal.section.technical", "Technical Details") }),
368
421
  /* @__PURE__ */ jsxRuntime.jsx(
369
- designSystem.Button,
422
+ StyledButtons.ShowHideButton,
370
423
  {
371
- variant: "tertiary",
372
424
  size: "S",
373
425
  onClick: () => setShowUserAgent(!showUserAgent),
374
- style: { fontSize: "12px" },
375
- children: showUserAgent ? `▲ ${t("modal.technical.hide", "Hide Details")}` : `▼ ${t("modal.technical.show", "Show Details")}`
426
+ children: showUserAgent ? t("modal.technical.hide", "Hide Details") : t("modal.technical.show", "Show Details")
376
427
  }
377
428
  )
378
429
  ] }),
@@ -397,12 +448,11 @@ const SessionDetailModal = ({ session, onClose, onSessionTerminated }) => {
397
448
  ] })
398
449
  ] }) }),
399
450
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Modal.Footer, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { justifyContent: "space-between", style: { width: "100%" }, children: [
400
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.Button, { onClick: onClose, variant: "tertiary", children: t("modal.actions.close", "Close") }),
451
+ /* @__PURE__ */ jsxRuntime.jsx(StyledButtons.TertiaryButton, { onClick: onClose, children: t("modal.actions.close", "Close") }),
401
452
  /* @__PURE__ */ jsxRuntime.jsx(
402
- designSystem.Button,
453
+ StyledButtons.DangerButton,
403
454
  {
404
455
  onClick: handleTerminate,
405
- variant: "danger",
406
456
  disabled: !session.isActive || terminating,
407
457
  loading: terminating,
408
458
  startIcon: /* @__PURE__ */ jsxRuntime.jsx(icons.Cross, {}),
@@ -694,7 +744,7 @@ const StyledTable = styled__default.default(designSystem.Table)`
694
744
  }
695
745
  }
696
746
  `;
697
- const OnlineIndicator = styled__default.default.div`
747
+ styled__default.default.div`
698
748
  width: 10px;
699
749
  height: 10px;
700
750
  border-radius: 50%;
@@ -748,11 +798,76 @@ const StyledSearchInput = styled__default.default.input`
748
798
  }
749
799
  `;
750
800
  const ActionButtons = styled__default.default(designSystem.Flex)`
751
- opacity: 0.7;
801
+ opacity: 0.85;
752
802
  transition: all ${theme.transitions.fast};
753
- gap: ${theme.spacing.xs};
803
+ gap: 8px;
754
804
  justify-content: flex-end;
755
805
  `;
806
+ const StatusBadge = styled__default.default.span`
807
+ display: inline-flex;
808
+ align-items: center;
809
+ gap: 6px;
810
+ padding: 6px 12px;
811
+ border-radius: 20px;
812
+ font-size: 12px;
813
+ font-weight: 600;
814
+ letter-spacing: 0.3px;
815
+ text-transform: uppercase;
816
+ transition: all 0.2s ease;
817
+
818
+ ${(props) => props.$status === "active" && `
819
+ background: linear-gradient(135deg, #DCFCE7 0%, #BBF7D0 100%);
820
+ color: #15803D;
821
+ border: 1px solid #86EFAC;
822
+ `}
823
+
824
+ ${(props) => props.$status === "idle" && `
825
+ background: linear-gradient(135deg, #FEF3C7 0%, #FDE68A 100%);
826
+ color: #A16207;
827
+ border: 1px solid #FCD34D;
828
+ `}
829
+
830
+ ${(props) => props.$status === "loggedout" && `
831
+ background: linear-gradient(135deg, #FEE2E2 0%, #FECACA 100%);
832
+ color: #B91C1C;
833
+ border: 1px solid #FCA5A5;
834
+ `}
835
+
836
+ ${(props) => props.$status === "terminated" && `
837
+ background: linear-gradient(135deg, #F3F4F6 0%, #E5E7EB 100%);
838
+ color: #4B5563;
839
+ border: 1px solid #D1D5DB;
840
+ `}
841
+ `;
842
+ const StatusDot = styled__default.default.span`
843
+ width: 8px;
844
+ height: 8px;
845
+ border-radius: 50%;
846
+ flex-shrink: 0;
847
+
848
+ ${(props) => props.$status === "active" && `
849
+ background: #22C55E;
850
+ box-shadow: 0 0 6px rgba(34, 197, 94, 0.6);
851
+ animation: pulse-green 2s ease-in-out infinite;
852
+ `}
853
+
854
+ ${(props) => props.$status === "idle" && `
855
+ background: #F59E0B;
856
+ `}
857
+
858
+ ${(props) => props.$status === "loggedout" && `
859
+ background: #EF4444;
860
+ `}
861
+
862
+ ${(props) => props.$status === "terminated" && `
863
+ background: #9CA3AF;
864
+ `}
865
+
866
+ @keyframes pulse-green {
867
+ 0%, 100% { opacity: 1; transform: scale(1); }
868
+ 50% { opacity: 0.7; transform: scale(1.1); }
869
+ }
870
+ `;
756
871
  const ClickableRow = styled__default.default(designSystem.Tr)`
757
872
  cursor: pointer;
758
873
 
@@ -1167,17 +1282,9 @@ const HomePage = () => {
1167
1282
  opacity: config.opacity || 1
1168
1283
  },
1169
1284
  children: [
1170
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.Td, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { alignItems: "center", gap: 2, children: [
1171
- /* @__PURE__ */ jsxRuntime.jsx(OnlineIndicator, { $online: config.indicator }),
1172
- /* @__PURE__ */ jsxRuntime.jsx(
1173
- designSystem.Badge,
1174
- {
1175
- backgroundColor: config.badgeColor,
1176
- textColor: "neutral0",
1177
- size: "S",
1178
- children: config.label
1179
- }
1180
- )
1285
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Td, { children: /* @__PURE__ */ jsxRuntime.jsxs(StatusBadge, { $status: sessionStatus, children: [
1286
+ /* @__PURE__ */ jsxRuntime.jsx(StatusDot, { $status: sessionStatus }),
1287
+ config.label
1181
1288
  ] }) }),
1182
1289
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Td, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { direction: "column", alignItems: "flex-start", children: [
1183
1290
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { fontWeight: "semiBold", ellipsis: true, children: session.user?.username || session.user?.email || t("homepage.user.unknown", "Unknown") }),
@@ -1202,10 +1309,8 @@ const HomePage = () => {
1202
1309
  ] }) }),
1203
1310
  /* @__PURE__ */ jsxRuntime.jsx(designSystem.Td, { onClick: (e) => e.stopPropagation(), children: /* @__PURE__ */ jsxRuntime.jsxs(ActionButtons, { className: "action-buttons", children: [
1204
1311
  /* @__PURE__ */ jsxRuntime.jsx(
1205
- designSystem.Button,
1312
+ StyledButtons.IconButtonPrimary,
1206
1313
  {
1207
- variant: "secondary",
1208
- size: "S",
1209
1314
  onClick: (e) => {
1210
1315
  e.stopPropagation();
1211
1316
  handleSessionClick(session);
@@ -1215,10 +1320,8 @@ const HomePage = () => {
1215
1320
  }
1216
1321
  ),
1217
1322
  /* @__PURE__ */ jsxRuntime.jsx(
1218
- designSystem.Button,
1323
+ StyledButtons.IconButtonWarning,
1219
1324
  {
1220
- variant: "danger-light",
1221
- size: "S",
1222
1325
  onClick: (e) => {
1223
1326
  e.stopPropagation();
1224
1327
  handleTerminateSession(session.id);
@@ -1229,10 +1332,8 @@ const HomePage = () => {
1229
1332
  }
1230
1333
  ),
1231
1334
  /* @__PURE__ */ jsxRuntime.jsx(
1232
- designSystem.Button,
1335
+ StyledButtons.IconButtonDanger,
1233
1336
  {
1234
- variant: "danger",
1235
- size: "S",
1236
1337
  onClick: (e) => {
1237
1338
  e.stopPropagation();
1238
1339
  handleDeleteSession(session.id);
@@ -4,7 +4,7 @@ import { Loader, Box, Alert, Flex, Typography, Button, Badge, Accordion } from "
4
4
  import { useFetchClient, useNotification } from "@strapi/strapi/admin";
5
5
  import { ArrowClockwise, Duplicate, Download, User, Shield, Sparkle, ChartBubble } from "@strapi/icons";
6
6
  import styled, { css, keyframes } from "styled-components";
7
- import { a as pluginId } from "./index-CUSrDKCG.mjs";
7
+ import { a as pluginId } from "./index-Ij0JRf9W.mjs";
8
8
  const theme = {
9
9
  borderRadius: { lg: "12px" }
10
10
  };
@@ -6,7 +6,7 @@ const designSystem = require("@strapi/design-system");
6
6
  const admin = require("@strapi/strapi/admin");
7
7
  const icons = require("@strapi/icons");
8
8
  const styled = require("styled-components");
9
- const index = require("./index-BuxWeACw.js");
9
+ const index = require("./index-DtBfKBne.js");
10
10
  const _interopDefault = (e) => e && e.__esModule ? e : { default: e };
11
11
  const styled__default = /* @__PURE__ */ _interopDefault(styled);
12
12
  const theme = {
@@ -6,7 +6,7 @@ const reactIntl = require("react-intl");
6
6
  const designSystem = require("@strapi/design-system");
7
7
  const icons = require("@strapi/icons");
8
8
  const admin = require("@strapi/strapi/admin");
9
- const index = require("./index-BuxWeACw.js");
9
+ const index = require("./index-DtBfKBne.js");
10
10
  const OnlineUsersWidget = () => {
11
11
  const { formatMessage } = reactIntl.useIntl();
12
12
  const { get } = admin.useFetchClient();
@@ -4,7 +4,7 @@ import { useIntl } from "react-intl";
4
4
  import { Box, Typography, Flex, Grid } from "@strapi/design-system";
5
5
  import { Check, Cross, Clock, User } from "@strapi/icons";
6
6
  import { useFetchClient } from "@strapi/strapi/admin";
7
- import { g as getTranslation } from "./index-CUSrDKCG.mjs";
7
+ import { g as getTranslation } from "./index-Ij0JRf9W.mjs";
8
8
  const OnlineUsersWidget = () => {
9
9
  const { formatMessage } = useIntl();
10
10
  const { get } = useFetchClient();