strapi-plugin-oidc 1.3.2 → 1.4.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.
@@ -1,11 +1,11 @@
1
1
  import { jsxs, Fragment, jsx } from "react/jsx-runtime";
2
- import { Routes, Route } from "react-router-dom";
2
+ import { useBlocker, Routes, Route } from "react-router-dom";
3
3
  import { useNotification, useFetchClient, Page, Layouts } from "@strapi/strapi/admin";
4
- import { useState, useCallback, useEffect, memo } from "react";
5
- import { Typography, Flex, Box, MultiSelect, MultiSelectOption, Field, Button, Divider, Thead, Tr, Th, Tbody, Td, Dialog, IconButton, Pagination, PreviousLink, PageLink, NextLink, Table, Alert } from "@strapi/design-system";
6
- import { Plus, Trash, WarningCircle, Information } from "@strapi/icons";
4
+ import { useState, useRef, useCallback, useEffect, memo } from "react";
5
+ import { Typography, Flex, Box, MultiSelect, MultiSelectOption, Button, Dialog, Field, Divider, Thead, Tr, Th, Tbody, Td, IconButton, Pagination, PreviousLink, PageLink, NextLink, Table, Alert } from "@strapi/design-system";
6
+ import { Download, Upload, Trash, WarningCircle, Plus, Information } from "@strapi/icons";
7
7
  import { useIntl } from "react-intl";
8
- import { g as getTrad } from "./index-D1ypRUlq.mjs";
8
+ import { g as getTrad } from "./index-ZRaWWFUL.mjs";
9
9
  import styled from "styled-components";
10
10
  function Role({ oidcRoles, roles, onChangeRole }) {
11
11
  const { formatMessage } = useIntl();
@@ -35,7 +35,7 @@ const CustomTable = styled(Table)`
35
35
  font-size: 1.3rem !important;
36
36
  }
37
37
  `;
38
- const LocalizedDate = ({ date }) => {
38
+ function LocalizedDate({ date }) {
39
39
  const userLocale = navigator.language || "en-US";
40
40
  return new Intl.DateTimeFormat(userLocale, {
41
41
  year: "numeric",
@@ -44,7 +44,7 @@ const LocalizedDate = ({ date }) => {
44
44
  hour: "2-digit",
45
45
  minute: "2-digit"
46
46
  }).format(new Date(date));
47
- };
47
+ }
48
48
  function Whitelist({
49
49
  users,
50
50
  roles,
@@ -52,17 +52,28 @@ function Whitelist({
52
52
  useWhitelist,
53
53
  loading,
54
54
  onSave,
55
- onDelete
55
+ onDelete,
56
+ onDeleteAll,
57
+ onImport,
58
+ onExport
56
59
  }) {
57
60
  const [email, setEmail] = useState("");
58
61
  const [selectedRoles, setSelectedRoles] = useState([]);
59
62
  const [page, setPage] = useState(1);
60
63
  const { formatMessage } = useIntl();
61
64
  const { toggleNotification } = useNotification();
65
+ const fileInputRef = useRef(null);
62
66
  const PAGE_SIZE = 10;
63
67
  const pageCount = Math.ceil(users.length / PAGE_SIZE) || 1;
64
68
  const paginatedUsers = users.slice((page - 1) * PAGE_SIZE, page * PAGE_SIZE);
65
- const onSaveEmail = useCallback(async () => {
69
+ const getRoleNames = (roleIds) => roleIds.map((roleId) => {
70
+ const r = roles.find((ro) => String(ro.id) === String(roleId));
71
+ return r ? r.name : roleId;
72
+ }).join(", ");
73
+ const defaultRoleNames = getRoleNames(oidcRoles.flatMap((oidc) => oidc.role ?? []));
74
+ const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
75
+ const isValidEmail = emailRegex.test(email);
76
+ const onSaveEmail = useCallback(() => {
66
77
  const emailText = email.trim();
67
78
  if (users.some((user) => user.email === emailText)) {
68
79
  toggleNotification({
@@ -70,18 +81,98 @@ function Whitelist({
70
81
  message: formatMessage(getTrad("whitelist.error.unique"))
71
82
  });
72
83
  } else {
73
- await onSave(emailText, selectedRoles);
84
+ onSave(emailText, selectedRoles);
74
85
  setEmail("");
75
86
  setSelectedRoles([]);
76
87
  }
77
88
  }, [email, selectedRoles, users, onSave, formatMessage, toggleNotification]);
78
- const isValidEmail = useCallback(() => {
79
- const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
80
- return emailRegex.test(email);
81
- }, [email]);
89
+ const handleImport = useCallback(
90
+ async (e) => {
91
+ const file = e.target.files?.[0];
92
+ if (!fileInputRef.current) return;
93
+ fileInputRef.current.value = "";
94
+ if (!file) return;
95
+ try {
96
+ const text = await file.text();
97
+ const parsed = JSON.parse(text);
98
+ if (!Array.isArray(parsed)) throw new Error();
99
+ const entries = parsed.filter((item) => item?.email).map((item) => ({
100
+ email: String(item.email),
101
+ roles: Array.isArray(item.roles) ? item.roles : []
102
+ }));
103
+ const count = await onImport(entries);
104
+ if (count === 0) {
105
+ toggleNotification({
106
+ type: "info",
107
+ message: formatMessage(getTrad("whitelist.import.none"))
108
+ });
109
+ } else {
110
+ toggleNotification({
111
+ type: "success",
112
+ message: formatMessage(getTrad("whitelist.import.success"), { count })
113
+ });
114
+ }
115
+ } catch {
116
+ toggleNotification({
117
+ type: "warning",
118
+ message: formatMessage(getTrad("whitelist.import.error"))
119
+ });
120
+ }
121
+ },
122
+ [onImport, formatMessage, toggleNotification]
123
+ );
82
124
  return /* @__PURE__ */ jsxs(Box, { children: [
83
125
  /* @__PURE__ */ jsx(Typography, { tag: "p", variant: "omega", textColor: "neutral600", marginBottom: 4, children: formatMessage(getTrad("whitelist.description")) }),
84
126
  useWhitelist && /* @__PURE__ */ jsxs(Fragment, { children: [
127
+ /* @__PURE__ */ jsxs(Flex, { justifyContent: "space-between", alignItems: "center", marginBottom: 4, children: [
128
+ /* @__PURE__ */ jsx(Typography, { variant: "pi", textColor: "neutral600", children: formatMessage(getTrad("whitelist.count"), { count: users.length }) }),
129
+ /* @__PURE__ */ jsxs(Flex, { gap: 2, children: [
130
+ /* @__PURE__ */ jsx(
131
+ Button,
132
+ {
133
+ size: "S",
134
+ variant: "tertiary",
135
+ startIcon: /* @__PURE__ */ jsx(Download, {}),
136
+ onClick: onExport,
137
+ disabled: users.length === 0,
138
+ children: formatMessage(getTrad("whitelist.export"))
139
+ }
140
+ ),
141
+ /* @__PURE__ */ jsx(
142
+ Button,
143
+ {
144
+ size: "S",
145
+ variant: "tertiary",
146
+ startIcon: /* @__PURE__ */ jsx(Upload, {}),
147
+ onClick: () => fileInputRef.current?.click(),
148
+ children: formatMessage(getTrad("whitelist.import"))
149
+ }
150
+ ),
151
+ /* @__PURE__ */ jsx(
152
+ "input",
153
+ {
154
+ ref: fileInputRef,
155
+ type: "file",
156
+ accept: ".json,application/json",
157
+ style: { display: "none" },
158
+ onChange: handleImport
159
+ }
160
+ ),
161
+ users.length > 0 && /* @__PURE__ */ jsxs(Dialog.Root, { children: [
162
+ /* @__PURE__ */ jsx(Dialog.Trigger, { children: /* @__PURE__ */ jsx(Button, { size: "S", variant: "danger-light", startIcon: /* @__PURE__ */ jsx(Trash, {}), children: formatMessage(getTrad("whitelist.delete.all.label")) }) }),
163
+ /* @__PURE__ */ jsxs(Dialog.Content, { children: [
164
+ /* @__PURE__ */ jsx(Dialog.Header, { children: formatMessage(getTrad("whitelist.delete.all.title")) }),
165
+ /* @__PURE__ */ jsx(Dialog.Body, { icon: /* @__PURE__ */ jsx(WarningCircle, { fill: "danger600" }), children: /* @__PURE__ */ jsx(Flex, { justifyContent: "center", children: /* @__PURE__ */ jsx(Typography, { textColor: "neutral800", textAlign: "center", children: formatMessage(getTrad("whitelist.delete.all.description"), {
166
+ count: users.length
167
+ }) }) }) }),
168
+ /* @__PURE__ */ jsxs(Dialog.Footer, { children: [
169
+ /* @__PURE__ */ jsx(Dialog.Cancel, { children: /* @__PURE__ */ jsx(Button, { fullWidth: true, variant: "tertiary", children: formatMessage(getTrad("page.cancel")) }) }),
170
+ /* @__PURE__ */ jsx(Dialog.Action, { children: /* @__PURE__ */ jsx(Button, { fullWidth: true, variant: "danger", onClick: onDeleteAll, children: formatMessage(getTrad("whitelist.delete.all.label")) }) })
171
+ ] })
172
+ ] })
173
+ ] })
174
+ ] })
175
+ ] }),
85
176
  /* @__PURE__ */ jsxs(Flex, { gap: 4, marginTop: 5, marginBottom: 5, alignItems: "flex-start", children: [
86
177
  /* @__PURE__ */ jsx(Box, { style: { flex: 1 }, children: /* @__PURE__ */ jsx(Field.Root, { children: /* @__PURE__ */ jsx(
87
178
  Field.Input,
@@ -89,7 +180,7 @@ function Whitelist({
89
180
  type: "text",
90
181
  disabled: loading,
91
182
  value: email,
92
- hasError: Boolean(email && !isValidEmail()),
183
+ hasError: Boolean(email && !isValidEmail),
93
184
  onChange: (e) => setEmail(e.currentTarget.value),
94
185
  placeholder: formatMessage(getTrad("whitelist.email.placeholder"))
95
186
  }
@@ -111,7 +202,7 @@ function Whitelist({
111
202
  {
112
203
  size: "L",
113
204
  startIcon: /* @__PURE__ */ jsx(Plus, {}),
114
- disabled: loading || email.trim() === "" || !isValidEmail(),
205
+ disabled: loading || email.trim() === "" || !isValidEmail,
115
206
  loading,
116
207
  onClick: onSaveEmail,
117
208
  children: formatMessage(getTrad("page.add"))
@@ -128,22 +219,16 @@ function Whitelist({
128
219
  /* @__PURE__ */ jsx(Th, { style: { paddingRight: 0 }, children: " " })
129
220
  ] }) }),
130
221
  /* @__PURE__ */ jsx(Tbody, { children: users.length === 0 ? /* @__PURE__ */ jsx(Tr, { children: /* @__PURE__ */ jsx(Td, { colSpan: 5, children: /* @__PURE__ */ jsx(Flex, { justifyContent: "center", padding: 4, children: /* @__PURE__ */ jsx(Typography, { textColor: "neutral600", children: formatMessage(getTrad("whitelist.table.empty")) }) }) }) }) : paginatedUsers.map((user, index) => {
131
- const getRoleNames = (roleIds) => roleIds.map((roleId) => {
132
- const r = roles.find((ro) => String(ro.id) === String(roleId));
133
- return r ? r.name : roleId;
134
- }).join(", ");
135
- let userRolesNames = getRoleNames(user.roles || []);
136
- if (!userRolesNames) {
137
- const defaultRolesIds = oidcRoles.reduce((acc, oidc) => {
138
- if (oidc.role) acc.push(...oidc.role);
139
- return acc;
140
- }, []);
141
- userRolesNames = getRoleNames(defaultRolesIds);
142
- }
222
+ const explicitRoleNames = getRoleNames(user.roles || []);
223
+ const isDefault = !explicitRoleNames && Boolean(defaultRoleNames);
224
+ const userRolesNames = explicitRoleNames || defaultRoleNames;
143
225
  return /* @__PURE__ */ jsxs(Tr, { children: [
144
226
  /* @__PURE__ */ jsx(Td, { children: index + 1 + (page - 1) * PAGE_SIZE }),
145
227
  /* @__PURE__ */ jsx(Td, { children: user.email }),
146
- /* @__PURE__ */ jsx(Td, { children: userRolesNames || "-" }),
228
+ /* @__PURE__ */ jsx(Td, { children: userRolesNames ? /* @__PURE__ */ jsxs(Flex, { gap: 2, alignItems: "center", children: [
229
+ /* @__PURE__ */ jsx("span", { children: userRolesNames }),
230
+ isDefault && /* @__PURE__ */ jsx(Typography, { variant: "pi", textColor: "neutral500", children: "(Default)" })
231
+ ] }) : "-" }),
147
232
  /* @__PURE__ */ jsx(Td, { children: /* @__PURE__ */ jsx(LocalizedDate, { date: user.createdAt }) }),
148
233
  /* @__PURE__ */ jsx(Td, { style: { paddingRight: 0 }, children: /* @__PURE__ */ jsx(
149
234
  Flex,
@@ -346,8 +431,11 @@ function CustomSwitch({ checked, onChange, label, disabled }) {
346
431
  label && /* @__PURE__ */ jsx(Typography, { variant: "pi", fontWeight: "bold", textColor: disabled ? "neutral500" : "neutral800", children: label })
347
432
  ] });
348
433
  }
434
+ function deepClone(value) {
435
+ return JSON.parse(JSON.stringify(value));
436
+ }
349
437
  function useOidcSettings() {
350
- const { get, put } = useFetchClient();
438
+ const { get, put, post } = useFetchClient();
351
439
  const [loading, setLoading] = useState(false);
352
440
  const [showSuccess, setSuccess] = useState(false);
353
441
  const [showError, setError] = useState(false);
@@ -365,14 +453,14 @@ function useOidcSettings() {
365
453
  useEffect(() => {
366
454
  get(`/strapi-plugin-oidc/oidc-roles`).then((response) => {
367
455
  setOIDCRoles(response.data);
368
- setInitialOIDCRoles(JSON.parse(JSON.stringify(response.data)));
456
+ setInitialOIDCRoles(deepClone(response.data));
369
457
  });
370
458
  get(`/admin/roles`).then((response) => {
371
459
  setRoles(response.data.data);
372
460
  });
373
461
  get("/strapi-plugin-oidc/whitelist").then((response) => {
374
462
  setUsers(response.data.whitelistUsers);
375
- setInitialUsers(JSON.parse(JSON.stringify(response.data.whitelistUsers)));
463
+ setInitialUsers(deepClone(response.data.whitelistUsers));
376
464
  setUseWhitelist(response.data.useWhitelist);
377
465
  setInitialUseWhitelist(response.data.useWhitelist);
378
466
  setEnforceOIDC(response.data.enforceOIDC);
@@ -386,17 +474,44 @@ function useOidcSettings() {
386
474
  );
387
475
  setOIDCRoles(updatedRoles);
388
476
  };
389
- const onRegisterWhitelist = async (email, selectedRoles) => {
477
+ const onRegisterWhitelist = (email, selectedRoles) => {
390
478
  const newUser = { email, roles: selectedRoles, createdAt: (/* @__PURE__ */ new Date()).toISOString() };
391
479
  setUsers([...users, newUser]);
392
480
  };
393
- const onDeleteWhitelist = async (email) => {
481
+ const onDeleteWhitelist = (email) => {
394
482
  const updatedUsers = users.filter((u) => u.email !== email);
395
483
  setUsers(updatedUsers);
396
484
  if (useWhitelist && updatedUsers.length === 0) {
397
485
  setEnforceOIDC(false);
398
486
  }
399
487
  };
488
+ const onDeleteAll = () => {
489
+ setUsers([]);
490
+ if (useWhitelist) setEnforceOIDC(false);
491
+ };
492
+ const onImport = async (entries) => {
493
+ const response = await post("/strapi-plugin-oidc/whitelist/import", { users: entries });
494
+ const refreshed = await get("/strapi-plugin-oidc/whitelist");
495
+ setUsers(refreshed.data.whitelistUsers);
496
+ setInitialUsers(deepClone(refreshed.data.whitelistUsers));
497
+ return response.data.importedCount;
498
+ };
499
+ const onExport = () => {
500
+ const roleMap = new Map(roles.map((r) => [String(r.id), r.name]));
501
+ const data = users.map(({ email, roles: userRoles }) => ({
502
+ email,
503
+ roles: (userRoles || []).map((id) => roleMap.get(String(id)) ?? id)
504
+ }));
505
+ const now = /* @__PURE__ */ new Date();
506
+ const datetime = `${now.getFullYear()}${String(now.getMonth() + 1).padStart(2, "0")}${String(now.getDate()).padStart(2, "0")}_${String(now.getHours()).padStart(2, "0")}${String(now.getMinutes()).padStart(2, "0")}${String(now.getSeconds()).padStart(2, "0")}`;
507
+ const blob = new Blob([JSON.stringify(data, null, 2)], { type: "application/json" });
508
+ const url = URL.createObjectURL(blob);
509
+ const a = document.createElement("a");
510
+ a.href = url;
511
+ a.download = `strapi-oidc-whitelist-${datetime}.json`;
512
+ a.click();
513
+ URL.revokeObjectURL(url);
514
+ };
400
515
  const onToggleWhitelist = (e) => {
401
516
  const checked = e.target.checked;
402
517
  setUseWhitelist(checked);
@@ -424,12 +539,12 @@ function useOidcSettings() {
424
539
  useWhitelist,
425
540
  enforceOIDC
426
541
  });
427
- setInitialOIDCRoles(JSON.parse(JSON.stringify(oidcRoles)));
542
+ setInitialOIDCRoles(deepClone(oidcRoles));
428
543
  setInitialUseWhitelist(useWhitelist);
429
544
  setInitialEnforceOIDC(enforceOIDC);
430
545
  get("/strapi-plugin-oidc/whitelist").then((getResponse) => {
431
546
  setUsers(getResponse.data.whitelistUsers);
432
- setInitialUsers(JSON.parse(JSON.stringify(getResponse.data.whitelistUsers)));
547
+ setInitialUsers(deepClone(getResponse.data.whitelistUsers));
433
548
  });
434
549
  if (syncResponse.data?.matchedExistingUsersCount > 0) {
435
550
  setMatched(syncResponse.data.matchedExistingUsersCount);
@@ -468,6 +583,9 @@ function useOidcSettings() {
468
583
  onChangeRole,
469
584
  onRegisterWhitelist,
470
585
  onDeleteWhitelist,
586
+ onDeleteAll,
587
+ onImport,
588
+ onExport,
471
589
  onToggleWhitelist,
472
590
  onToggleEnforce,
473
591
  onSaveAll
@@ -477,6 +595,7 @@ function useOidcSettings() {
477
595
  function HomePage() {
478
596
  const { formatMessage } = useIntl();
479
597
  const { state, actions } = useOidcSettings();
598
+ const blocker = useBlocker(state.isDirty);
480
599
  return /* @__PURE__ */ jsxs(Page.Protect, { permissions: [{ action: "plugin::strapi-plugin-oidc.read", subject: null }], children: [
481
600
  /* @__PURE__ */ jsx(
482
601
  Layouts.Header,
@@ -521,7 +640,10 @@ function HomePage() {
521
640
  oidcRoles: state.oidcRoles,
522
641
  useWhitelist: state.useWhitelist,
523
642
  onSave: actions.onRegisterWhitelist,
524
- onDelete: actions.onDeleteWhitelist
643
+ onDelete: actions.onDeleteWhitelist,
644
+ onDeleteAll: actions.onDeleteAll,
645
+ onImport: actions.onImport,
646
+ onExport: actions.onExport
525
647
  }
526
648
  )
527
649
  ] }),
@@ -560,6 +682,14 @@ function HomePage() {
560
682
  children: formatMessage(getTrad("page.save"))
561
683
  }
562
684
  ) })
685
+ ] }) }),
686
+ /* @__PURE__ */ jsx(Dialog.Root, { open: blocker.state === "blocked", children: /* @__PURE__ */ jsxs(Dialog.Content, { children: [
687
+ /* @__PURE__ */ jsx(Dialog.Header, { children: formatMessage(getTrad("unsaved.title")) }),
688
+ /* @__PURE__ */ jsx(Dialog.Body, { children: formatMessage(getTrad("unsaved.description")) }),
689
+ /* @__PURE__ */ jsxs(Dialog.Footer, { children: [
690
+ /* @__PURE__ */ jsx(Dialog.Cancel, { children: /* @__PURE__ */ jsx(Button, { variant: "tertiary", onClick: () => blocker.reset?.(), children: formatMessage(getTrad("unsaved.cancel")) }) }),
691
+ /* @__PURE__ */ jsx(Dialog.Action, { children: /* @__PURE__ */ jsx(Button, { variant: "danger", onClick: () => blocker.proceed?.(), children: formatMessage(getTrad("unsaved.confirm")) }) })
692
+ ] })
563
693
  ] }) })
564
694
  ] });
565
695
  }
@@ -79,7 +79,20 @@ const en = {
79
79
  "enforce.warning": "Make sure OIDC is setup correctly before saving changes, you won't be able to login normally.",
80
80
  "enforce.config.info": "Enforcement is controlled by the OIDC_ENFORCE config variable and cannot be changed here.",
81
81
  "login.settings.title": "Login Settings",
82
- "login.sso": "Login via SSO"
82
+ "login.sso": "Login via SSO",
83
+ "whitelist.count": "{count, plural, one {# entry} other {# entries}}",
84
+ "whitelist.import": "Import",
85
+ "whitelist.export": "Export",
86
+ "whitelist.delete.all.label": "Delete All",
87
+ "whitelist.delete.all.title": "Delete All Entries",
88
+ "whitelist.delete.all.description": "This will permanently remove all {count, plural, one {# entry} other {# entries}} from the whitelist. Unsaved changes will be lost.",
89
+ "whitelist.import.error": "Invalid file — expected a JSON array of objects with an email field.",
90
+ "whitelist.import.success": "Imported {count, plural, one {# new entry} other {# new entries}}.",
91
+ "whitelist.import.none": "No new entries — all emails are already in the whitelist.",
92
+ "unsaved.title": "Unsaved Changes",
93
+ "unsaved.description": "You have unsaved changes that will be lost if you leave. Do you want to continue?",
94
+ "unsaved.confirm": "Leave",
95
+ "unsaved.cancel": "Stay"
83
96
  };
84
97
  function getTrad(id) {
85
98
  const pluginIdWithId = `${pluginId}.${id}`;
@@ -110,7 +123,7 @@ const index = {
110
123
  defaultMessage: "Configuration"
111
124
  },
112
125
  Component: async () => {
113
- return await Promise.resolve().then(() => require("./index-BqyGGX8X.js"));
126
+ return await Promise.resolve().then(() => require("./index-BnFRueNv.js"));
114
127
  },
115
128
  permissions: [{ action: "plugin::strapi-plugin-oidc.read", subject: null }]
116
129
  }
@@ -78,7 +78,20 @@ const en = {
78
78
  "enforce.warning": "Make sure OIDC is setup correctly before saving changes, you won't be able to login normally.",
79
79
  "enforce.config.info": "Enforcement is controlled by the OIDC_ENFORCE config variable and cannot be changed here.",
80
80
  "login.settings.title": "Login Settings",
81
- "login.sso": "Login via SSO"
81
+ "login.sso": "Login via SSO",
82
+ "whitelist.count": "{count, plural, one {# entry} other {# entries}}",
83
+ "whitelist.import": "Import",
84
+ "whitelist.export": "Export",
85
+ "whitelist.delete.all.label": "Delete All",
86
+ "whitelist.delete.all.title": "Delete All Entries",
87
+ "whitelist.delete.all.description": "This will permanently remove all {count, plural, one {# entry} other {# entries}} from the whitelist. Unsaved changes will be lost.",
88
+ "whitelist.import.error": "Invalid file — expected a JSON array of objects with an email field.",
89
+ "whitelist.import.success": "Imported {count, plural, one {# new entry} other {# new entries}}.",
90
+ "whitelist.import.none": "No new entries — all emails are already in the whitelist.",
91
+ "unsaved.title": "Unsaved Changes",
92
+ "unsaved.description": "You have unsaved changes that will be lost if you leave. Do you want to continue?",
93
+ "unsaved.confirm": "Leave",
94
+ "unsaved.cancel": "Stay"
82
95
  };
83
96
  function getTrad(id) {
84
97
  const pluginIdWithId = `${pluginId}.${id}`;
@@ -109,7 +122,7 @@ const index = {
109
122
  defaultMessage: "Configuration"
110
123
  },
111
124
  Component: async () => {
112
- return await import("./index-CFmg9Kxl.mjs");
125
+ return await import("./index-CY4s-vtv.mjs");
113
126
  },
114
127
  permissions: [{ action: "plugin::strapi-plugin-oidc.read", subject: null }]
115
128
  }
@@ -1,4 +1,4 @@
1
1
  "use strict";
2
2
  Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: "Module" } });
3
- const index = require("./index-Cse9ex24.js");
3
+ const index = require("./index-RMgj1w0B.js");
4
4
  exports.default = index.index;
@@ -1,4 +1,4 @@
1
- import { i } from "./index-D1ypRUlq.mjs";
1
+ import { i } from "./index-ZRaWWFUL.mjs";
2
2
  export {
3
3
  i as default
4
4
  };