@idp.global/catalog 1.1.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.
- package/assets/v2/draw-41d55381-b162-433d-956c-fe4cd400212e.png +0 -0
- package/assets/v2/draw-bd386bf3-ce94-4452-88da-05ae372fae35.png +0 -0
- package/assets/v2/draw-be69231a-f491-4bd3-9a47-71561ce14c15.png +0 -0
- package/assets/v2/draw-d58859a8-0615-44ec-80fe-626033c888f7.png +0 -0
- package/assets/v2/draw-db67b502-d987-4226-a5f8-d57e3f8d7ba9.png +0 -0
- package/assets/v2/draw-e6ac3ef5-5a93-464d-9d3f-5ae7b7278bdd.png +0 -0
- package/changelog.md +26 -0
- package/dist_bundle/bundle.js +6385 -0
- package/dist_ts_web/00_commitinfo_data.d.ts +8 -0
- package/dist_ts_web/00_commitinfo_data.js +9 -0
- package/dist_ts_web/elements/idp-admin-shell.d.ts +292 -0
- package/dist_ts_web/elements/idp-admin-shell.js +2615 -0
- package/dist_ts_web/elements/idp-approval-card.d.ts +25 -0
- package/dist_ts_web/elements/idp-approval-card.js +274 -0
- package/dist_ts_web/elements/idp-badge.d.ts +14 -0
- package/dist_ts_web/elements/idp-badge.js +135 -0
- package/dist_ts_web/elements/idp-button.d.ts +21 -0
- package/dist_ts_web/elements/idp-button.js +234 -0
- package/dist_ts_web/elements/idp-card.d.ts +15 -0
- package/dist_ts_web/elements/idp-card.js +139 -0
- package/dist_ts_web/elements/idp-checkbox.d.ts +23 -0
- package/dist_ts_web/elements/idp-checkbox.js +233 -0
- package/dist_ts_web/elements/idp-dashboard-window.d.ts +23 -0
- package/dist_ts_web/elements/idp-dashboard-window.js +587 -0
- package/dist_ts_web/elements/idp-data-table.d.ts +45 -0
- package/dist_ts_web/elements/idp-data-table.js +472 -0
- package/dist_ts_web/elements/idp-form-submit.d.ts +20 -0
- package/dist_ts_web/elements/idp-form-submit.js +136 -0
- package/dist_ts_web/elements/idp-form.d.ts +31 -0
- package/dist_ts_web/elements/idp-form.js +197 -0
- package/dist_ts_web/elements/idp-icon.d.ts +18 -0
- package/dist_ts_web/elements/idp-icon.js +204 -0
- package/dist_ts_web/elements/idp-inbox-preview.d.ts +18 -0
- package/dist_ts_web/elements/idp-inbox-preview.js +245 -0
- package/dist_ts_web/elements/idp-input.d.ts +26 -0
- package/dist_ts_web/elements/idp-input.js +249 -0
- package/dist_ts_web/elements/idp-landing-hero.d.ts +15 -0
- package/dist_ts_web/elements/idp-landing-hero.js +209 -0
- package/dist_ts_web/elements/idp-landing-page.d.ts +21 -0
- package/dist_ts_web/elements/idp-landing-page.js +694 -0
- package/dist_ts_web/elements/idp-mobile-frame.d.ts +14 -0
- package/dist_ts_web/elements/idp-mobile-frame.js +195 -0
- package/dist_ts_web/elements/idp-mobile-showcase.d.ts +16 -0
- package/dist_ts_web/elements/idp-mobile-showcase.js +339 -0
- package/dist_ts_web/elements/idp-select.d.ts +28 -0
- package/dist_ts_web/elements/idp-select.js +179 -0
- package/dist_ts_web/elements/idp-toggle.d.ts +15 -0
- package/dist_ts_web/elements/idp-toggle.js +134 -0
- package/dist_ts_web/elements/index.d.ts +20 -0
- package/dist_ts_web/elements/index.js +21 -0
- package/dist_ts_web/elements/tokens.d.ts +21 -0
- package/dist_ts_web/elements/tokens.js +190 -0
- package/dist_ts_web/index.d.ts +1 -0
- package/dist_ts_web/index.js +2 -0
- package/dist_ts_web/pages/index.d.ts +5 -0
- package/dist_ts_web/pages/index.js +23 -0
- package/dist_watch/bundle.js +120699 -0
- package/dist_watch/bundle.js.map +7 -0
- package/dist_watch/index.html +29 -0
- package/html/index.html +29 -0
- package/html/index.ts +39 -0
- package/license +21 -0
- package/package.json +64 -0
- package/readme.md +103 -0
- package/ts_web/00_commitinfo_data.ts +8 -0
- package/ts_web/elements/idp-admin-shell.ts +2664 -0
- package/ts_web/elements/idp-approval-card.ts +182 -0
- package/ts_web/elements/idp-badge.ts +84 -0
- package/ts_web/elements/idp-button.ts +166 -0
- package/ts_web/elements/idp-card.ts +76 -0
- package/ts_web/elements/idp-checkbox.ts +143 -0
- package/ts_web/elements/idp-dashboard-window.ts +564 -0
- package/ts_web/elements/idp-data-table.ts +407 -0
- package/ts_web/elements/idp-form-submit.ts +65 -0
- package/ts_web/elements/idp-form.ts +159 -0
- package/ts_web/elements/idp-icon.ts +263 -0
- package/ts_web/elements/idp-inbox-preview.ts +192 -0
- package/ts_web/elements/idp-input.ts +151 -0
- package/ts_web/elements/idp-landing-hero.ts +165 -0
- package/ts_web/elements/idp-landing-page.ts +655 -0
- package/ts_web/elements/idp-mobile-frame.ts +137 -0
- package/ts_web/elements/idp-mobile-showcase.ts +295 -0
- package/ts_web/elements/idp-select.ts +119 -0
- package/ts_web/elements/idp-toggle.ts +77 -0
- package/ts_web/elements/index.ts +20 -0
- package/ts_web/elements/tokens.ts +193 -0
- package/ts_web/index.ts +1 -0
- package/ts_web/pages/index.ts +26 -0
|
@@ -0,0 +1,2615 @@
|
|
|
1
|
+
var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
|
|
2
|
+
function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
|
|
3
|
+
var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
|
|
4
|
+
var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
|
|
5
|
+
var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
|
|
6
|
+
var _, done = false;
|
|
7
|
+
for (var i = decorators.length - 1; i >= 0; i--) {
|
|
8
|
+
var context = {};
|
|
9
|
+
for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
|
|
10
|
+
for (var p in contextIn.access) context.access[p] = contextIn.access[p];
|
|
11
|
+
context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
|
|
12
|
+
var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
|
|
13
|
+
if (kind === "accessor") {
|
|
14
|
+
if (result === void 0) continue;
|
|
15
|
+
if (result === null || typeof result !== "object") throw new TypeError("Object expected");
|
|
16
|
+
if (_ = accept(result.get)) descriptor.get = _;
|
|
17
|
+
if (_ = accept(result.set)) descriptor.set = _;
|
|
18
|
+
if (_ = accept(result.init)) initializers.unshift(_);
|
|
19
|
+
}
|
|
20
|
+
else if (_ = accept(result)) {
|
|
21
|
+
if (kind === "field") initializers.unshift(_);
|
|
22
|
+
else descriptor[key] = _;
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
if (target) Object.defineProperty(target, contextIn.name, descriptor);
|
|
26
|
+
done = true;
|
|
27
|
+
};
|
|
28
|
+
var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
|
|
29
|
+
var useValue = arguments.length > 2;
|
|
30
|
+
for (var i = 0; i < initializers.length; i++) {
|
|
31
|
+
value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
|
|
32
|
+
}
|
|
33
|
+
return useValue ? value : void 0;
|
|
34
|
+
};
|
|
35
|
+
import { DeesElement, html, property, state, customElement, css } from '@design.estate/dees-element';
|
|
36
|
+
import { idpElementStyles } from './tokens.js';
|
|
37
|
+
import './idp-badge.js';
|
|
38
|
+
import './idp-icon.js';
|
|
39
|
+
import './idp-data-table.js';
|
|
40
|
+
let IdpAdminShell = (() => {
|
|
41
|
+
let _classDecorators = [customElement('idp-admin-shell')];
|
|
42
|
+
let _classDescriptor;
|
|
43
|
+
let _classExtraInitializers = [];
|
|
44
|
+
let _classThis;
|
|
45
|
+
let _classSuper = DeesElement;
|
|
46
|
+
let _page_decorators;
|
|
47
|
+
let _page_initializers = [];
|
|
48
|
+
let _page_extraInitializers = [];
|
|
49
|
+
let _user_decorators;
|
|
50
|
+
let _user_initializers = [];
|
|
51
|
+
let _user_extraInitializers = [];
|
|
52
|
+
let _orgs_decorators;
|
|
53
|
+
let _orgs_initializers = [];
|
|
54
|
+
let _orgs_extraInitializers = [];
|
|
55
|
+
let _selectedOrgId_decorators;
|
|
56
|
+
let _selectedOrgId_initializers = [];
|
|
57
|
+
let _selectedOrgId_extraInitializers = [];
|
|
58
|
+
let _globalAdmin_decorators;
|
|
59
|
+
let _globalAdmin_initializers = [];
|
|
60
|
+
let _globalAdmin_extraInitializers = [];
|
|
61
|
+
let _dataLoading_decorators;
|
|
62
|
+
let _dataLoading_initializers = [];
|
|
63
|
+
let _dataLoading_extraInitializers = [];
|
|
64
|
+
let _dataError_decorators;
|
|
65
|
+
let _dataError_initializers = [];
|
|
66
|
+
let _dataError_extraInitializers = [];
|
|
67
|
+
let _sessions_decorators;
|
|
68
|
+
let _sessions_initializers = [];
|
|
69
|
+
let _sessions_extraInitializers = [];
|
|
70
|
+
let _activities_decorators;
|
|
71
|
+
let _activities_initializers = [];
|
|
72
|
+
let _activities_extraInitializers = [];
|
|
73
|
+
let _orgMembers_decorators;
|
|
74
|
+
let _orgMembers_initializers = [];
|
|
75
|
+
let _orgMembers_extraInitializers = [];
|
|
76
|
+
let _orgInvitations_decorators;
|
|
77
|
+
let _orgInvitations_initializers = [];
|
|
78
|
+
let _orgInvitations_extraInitializers = [];
|
|
79
|
+
let _orgRoleDefinitions_decorators;
|
|
80
|
+
let _orgRoleDefinitions_initializers = [];
|
|
81
|
+
let _orgRoleDefinitions_extraInitializers = [];
|
|
82
|
+
let _orgApps_decorators;
|
|
83
|
+
let _orgApps_initializers = [];
|
|
84
|
+
let _orgApps_extraInitializers = [];
|
|
85
|
+
let _accountApps_decorators;
|
|
86
|
+
let _accountApps_initializers = [];
|
|
87
|
+
let _accountApps_extraInitializers = [];
|
|
88
|
+
let _adminApps_decorators;
|
|
89
|
+
let _adminApps_initializers = [];
|
|
90
|
+
let _adminApps_extraInitializers = [];
|
|
91
|
+
let _passportDevices_decorators;
|
|
92
|
+
let _passportDevices_initializers = [];
|
|
93
|
+
let _passportDevices_extraInitializers = [];
|
|
94
|
+
let _passportEnrollment_decorators;
|
|
95
|
+
let _passportEnrollment_initializers = [];
|
|
96
|
+
let _passportEnrollment_extraInitializers = [];
|
|
97
|
+
let _credentialMessage_decorators;
|
|
98
|
+
let _credentialMessage_initializers = [];
|
|
99
|
+
let _credentialMessage_extraInitializers = [];
|
|
100
|
+
let _orgMenuOpen_decorators;
|
|
101
|
+
let _orgMenuOpen_initializers = [];
|
|
102
|
+
let _orgMenuOpen_extraInitializers = [];
|
|
103
|
+
let _currentPassword_decorators;
|
|
104
|
+
let _currentPassword_initializers = [];
|
|
105
|
+
let _currentPassword_extraInitializers = [];
|
|
106
|
+
let _newPassword_decorators;
|
|
107
|
+
let _newPassword_initializers = [];
|
|
108
|
+
let _newPassword_extraInitializers = [];
|
|
109
|
+
let _confirmPassword_decorators;
|
|
110
|
+
let _confirmPassword_initializers = [];
|
|
111
|
+
let _confirmPassword_extraInitializers = [];
|
|
112
|
+
let _credentialError_decorators;
|
|
113
|
+
let _credentialError_initializers = [];
|
|
114
|
+
let _credentialError_extraInitializers = [];
|
|
115
|
+
let _orgSettingsOrgId_decorators;
|
|
116
|
+
let _orgSettingsOrgId_initializers = [];
|
|
117
|
+
let _orgSettingsOrgId_extraInitializers = [];
|
|
118
|
+
let _orgNameDraft_decorators;
|
|
119
|
+
let _orgNameDraft_initializers = [];
|
|
120
|
+
let _orgNameDraft_extraInitializers = [];
|
|
121
|
+
let _orgSlugDraft_decorators;
|
|
122
|
+
let _orgSlugDraft_initializers = [];
|
|
123
|
+
let _orgSlugDraft_extraInitializers = [];
|
|
124
|
+
let _orgSettingsConfirmation_decorators;
|
|
125
|
+
let _orgSettingsConfirmation_initializers = [];
|
|
126
|
+
let _orgSettingsConfirmation_extraInitializers = [];
|
|
127
|
+
let _transferOwnerId_decorators;
|
|
128
|
+
let _transferOwnerId_initializers = [];
|
|
129
|
+
let _transferOwnerId_extraInitializers = [];
|
|
130
|
+
let _transferConfirmation_decorators;
|
|
131
|
+
let _transferConfirmation_initializers = [];
|
|
132
|
+
let _transferConfirmation_extraInitializers = [];
|
|
133
|
+
let _deleteConfirmation_decorators;
|
|
134
|
+
let _deleteConfirmation_initializers = [];
|
|
135
|
+
let _deleteConfirmation_extraInitializers = [];
|
|
136
|
+
let _orgSettingsError_decorators;
|
|
137
|
+
let _orgSettingsError_initializers = [];
|
|
138
|
+
let _orgSettingsError_extraInitializers = [];
|
|
139
|
+
let _dialogMode_decorators;
|
|
140
|
+
let _dialogMode_initializers = [];
|
|
141
|
+
let _dialogMode_extraInitializers = [];
|
|
142
|
+
let _dialogError_decorators;
|
|
143
|
+
let _dialogError_initializers = [];
|
|
144
|
+
let _dialogError_extraInitializers = [];
|
|
145
|
+
let _dialogRoleKey_decorators;
|
|
146
|
+
let _dialogRoleKey_initializers = [];
|
|
147
|
+
let _dialogRoleKey_extraInitializers = [];
|
|
148
|
+
let _dialogRoleName_decorators;
|
|
149
|
+
let _dialogRoleName_initializers = [];
|
|
150
|
+
let _dialogRoleName_extraInitializers = [];
|
|
151
|
+
let _dialogRoleDescription_decorators;
|
|
152
|
+
let _dialogRoleDescription_initializers = [];
|
|
153
|
+
let _dialogRoleDescription_extraInitializers = [];
|
|
154
|
+
let _dialogRoleDeleteConfirmation_decorators;
|
|
155
|
+
let _dialogRoleDeleteConfirmation_initializers = [];
|
|
156
|
+
let _dialogRoleDeleteConfirmation_extraInitializers = [];
|
|
157
|
+
let _dialogMember_decorators;
|
|
158
|
+
let _dialogMember_initializers = [];
|
|
159
|
+
let _dialogMember_extraInitializers = [];
|
|
160
|
+
let _dialogMemberRoles_decorators;
|
|
161
|
+
let _dialogMemberRoles_initializers = [];
|
|
162
|
+
let _dialogMemberRoles_extraInitializers = [];
|
|
163
|
+
let _dialogApp_decorators;
|
|
164
|
+
let _dialogApp_initializers = [];
|
|
165
|
+
let _dialogApp_extraInitializers = [];
|
|
166
|
+
let _dialogAppMappings_decorators;
|
|
167
|
+
let _dialogAppMappings_initializers = [];
|
|
168
|
+
let _dialogAppMappings_extraInitializers = [];
|
|
169
|
+
var IdpAdminShell = class extends _classSuper {
|
|
170
|
+
static { _classThis = this; }
|
|
171
|
+
static {
|
|
172
|
+
const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
|
|
173
|
+
_page_decorators = [property({ type: String })];
|
|
174
|
+
_user_decorators = [property({ type: Object })];
|
|
175
|
+
_orgs_decorators = [property({ type: Array })];
|
|
176
|
+
_selectedOrgId_decorators = [property({ type: String, attribute: 'selected-org-id' })];
|
|
177
|
+
_globalAdmin_decorators = [property({ type: Boolean, attribute: 'global-admin', reflect: true })];
|
|
178
|
+
_dataLoading_decorators = [property({ type: Boolean, attribute: 'data-loading', reflect: true })];
|
|
179
|
+
_dataError_decorators = [property({ type: String, attribute: 'data-error' })];
|
|
180
|
+
_sessions_decorators = [property({ type: Array })];
|
|
181
|
+
_activities_decorators = [property({ type: Array })];
|
|
182
|
+
_orgMembers_decorators = [property({ type: Array })];
|
|
183
|
+
_orgInvitations_decorators = [property({ type: Array })];
|
|
184
|
+
_orgRoleDefinitions_decorators = [property({ type: Array })];
|
|
185
|
+
_orgApps_decorators = [property({ type: Array })];
|
|
186
|
+
_accountApps_decorators = [property({ type: Array })];
|
|
187
|
+
_adminApps_decorators = [property({ type: Array })];
|
|
188
|
+
_passportDevices_decorators = [property({ type: Array })];
|
|
189
|
+
_passportEnrollment_decorators = [property({ type: Object })];
|
|
190
|
+
_credentialMessage_decorators = [property({ type: String, attribute: 'credential-message' })];
|
|
191
|
+
_orgMenuOpen_decorators = [state()];
|
|
192
|
+
_currentPassword_decorators = [state()];
|
|
193
|
+
_newPassword_decorators = [state()];
|
|
194
|
+
_confirmPassword_decorators = [state()];
|
|
195
|
+
_credentialError_decorators = [state()];
|
|
196
|
+
_orgSettingsOrgId_decorators = [state()];
|
|
197
|
+
_orgNameDraft_decorators = [state()];
|
|
198
|
+
_orgSlugDraft_decorators = [state()];
|
|
199
|
+
_orgSettingsConfirmation_decorators = [state()];
|
|
200
|
+
_transferOwnerId_decorators = [state()];
|
|
201
|
+
_transferConfirmation_decorators = [state()];
|
|
202
|
+
_deleteConfirmation_decorators = [state()];
|
|
203
|
+
_orgSettingsError_decorators = [state()];
|
|
204
|
+
_dialogMode_decorators = [state()];
|
|
205
|
+
_dialogError_decorators = [state()];
|
|
206
|
+
_dialogRoleKey_decorators = [state()];
|
|
207
|
+
_dialogRoleName_decorators = [state()];
|
|
208
|
+
_dialogRoleDescription_decorators = [state()];
|
|
209
|
+
_dialogRoleDeleteConfirmation_decorators = [state()];
|
|
210
|
+
_dialogMember_decorators = [state()];
|
|
211
|
+
_dialogMemberRoles_decorators = [state()];
|
|
212
|
+
_dialogApp_decorators = [state()];
|
|
213
|
+
_dialogAppMappings_decorators = [state()];
|
|
214
|
+
__esDecorate(this, null, _page_decorators, { kind: "accessor", name: "page", static: false, private: false, access: { has: obj => "page" in obj, get: obj => obj.page, set: (obj, value) => { obj.page = value; } }, metadata: _metadata }, _page_initializers, _page_extraInitializers);
|
|
215
|
+
__esDecorate(this, null, _user_decorators, { kind: "accessor", name: "user", static: false, private: false, access: { has: obj => "user" in obj, get: obj => obj.user, set: (obj, value) => { obj.user = value; } }, metadata: _metadata }, _user_initializers, _user_extraInitializers);
|
|
216
|
+
__esDecorate(this, null, _orgs_decorators, { kind: "accessor", name: "orgs", static: false, private: false, access: { has: obj => "orgs" in obj, get: obj => obj.orgs, set: (obj, value) => { obj.orgs = value; } }, metadata: _metadata }, _orgs_initializers, _orgs_extraInitializers);
|
|
217
|
+
__esDecorate(this, null, _selectedOrgId_decorators, { kind: "accessor", name: "selectedOrgId", static: false, private: false, access: { has: obj => "selectedOrgId" in obj, get: obj => obj.selectedOrgId, set: (obj, value) => { obj.selectedOrgId = value; } }, metadata: _metadata }, _selectedOrgId_initializers, _selectedOrgId_extraInitializers);
|
|
218
|
+
__esDecorate(this, null, _globalAdmin_decorators, { kind: "accessor", name: "globalAdmin", static: false, private: false, access: { has: obj => "globalAdmin" in obj, get: obj => obj.globalAdmin, set: (obj, value) => { obj.globalAdmin = value; } }, metadata: _metadata }, _globalAdmin_initializers, _globalAdmin_extraInitializers);
|
|
219
|
+
__esDecorate(this, null, _dataLoading_decorators, { kind: "accessor", name: "dataLoading", static: false, private: false, access: { has: obj => "dataLoading" in obj, get: obj => obj.dataLoading, set: (obj, value) => { obj.dataLoading = value; } }, metadata: _metadata }, _dataLoading_initializers, _dataLoading_extraInitializers);
|
|
220
|
+
__esDecorate(this, null, _dataError_decorators, { kind: "accessor", name: "dataError", static: false, private: false, access: { has: obj => "dataError" in obj, get: obj => obj.dataError, set: (obj, value) => { obj.dataError = value; } }, metadata: _metadata }, _dataError_initializers, _dataError_extraInitializers);
|
|
221
|
+
__esDecorate(this, null, _sessions_decorators, { kind: "accessor", name: "sessions", static: false, private: false, access: { has: obj => "sessions" in obj, get: obj => obj.sessions, set: (obj, value) => { obj.sessions = value; } }, metadata: _metadata }, _sessions_initializers, _sessions_extraInitializers);
|
|
222
|
+
__esDecorate(this, null, _activities_decorators, { kind: "accessor", name: "activities", static: false, private: false, access: { has: obj => "activities" in obj, get: obj => obj.activities, set: (obj, value) => { obj.activities = value; } }, metadata: _metadata }, _activities_initializers, _activities_extraInitializers);
|
|
223
|
+
__esDecorate(this, null, _orgMembers_decorators, { kind: "accessor", name: "orgMembers", static: false, private: false, access: { has: obj => "orgMembers" in obj, get: obj => obj.orgMembers, set: (obj, value) => { obj.orgMembers = value; } }, metadata: _metadata }, _orgMembers_initializers, _orgMembers_extraInitializers);
|
|
224
|
+
__esDecorate(this, null, _orgInvitations_decorators, { kind: "accessor", name: "orgInvitations", static: false, private: false, access: { has: obj => "orgInvitations" in obj, get: obj => obj.orgInvitations, set: (obj, value) => { obj.orgInvitations = value; } }, metadata: _metadata }, _orgInvitations_initializers, _orgInvitations_extraInitializers);
|
|
225
|
+
__esDecorate(this, null, _orgRoleDefinitions_decorators, { kind: "accessor", name: "orgRoleDefinitions", static: false, private: false, access: { has: obj => "orgRoleDefinitions" in obj, get: obj => obj.orgRoleDefinitions, set: (obj, value) => { obj.orgRoleDefinitions = value; } }, metadata: _metadata }, _orgRoleDefinitions_initializers, _orgRoleDefinitions_extraInitializers);
|
|
226
|
+
__esDecorate(this, null, _orgApps_decorators, { kind: "accessor", name: "orgApps", static: false, private: false, access: { has: obj => "orgApps" in obj, get: obj => obj.orgApps, set: (obj, value) => { obj.orgApps = value; } }, metadata: _metadata }, _orgApps_initializers, _orgApps_extraInitializers);
|
|
227
|
+
__esDecorate(this, null, _accountApps_decorators, { kind: "accessor", name: "accountApps", static: false, private: false, access: { has: obj => "accountApps" in obj, get: obj => obj.accountApps, set: (obj, value) => { obj.accountApps = value; } }, metadata: _metadata }, _accountApps_initializers, _accountApps_extraInitializers);
|
|
228
|
+
__esDecorate(this, null, _adminApps_decorators, { kind: "accessor", name: "adminApps", static: false, private: false, access: { has: obj => "adminApps" in obj, get: obj => obj.adminApps, set: (obj, value) => { obj.adminApps = value; } }, metadata: _metadata }, _adminApps_initializers, _adminApps_extraInitializers);
|
|
229
|
+
__esDecorate(this, null, _passportDevices_decorators, { kind: "accessor", name: "passportDevices", static: false, private: false, access: { has: obj => "passportDevices" in obj, get: obj => obj.passportDevices, set: (obj, value) => { obj.passportDevices = value; } }, metadata: _metadata }, _passportDevices_initializers, _passportDevices_extraInitializers);
|
|
230
|
+
__esDecorate(this, null, _passportEnrollment_decorators, { kind: "accessor", name: "passportEnrollment", static: false, private: false, access: { has: obj => "passportEnrollment" in obj, get: obj => obj.passportEnrollment, set: (obj, value) => { obj.passportEnrollment = value; } }, metadata: _metadata }, _passportEnrollment_initializers, _passportEnrollment_extraInitializers);
|
|
231
|
+
__esDecorate(this, null, _credentialMessage_decorators, { kind: "accessor", name: "credentialMessage", static: false, private: false, access: { has: obj => "credentialMessage" in obj, get: obj => obj.credentialMessage, set: (obj, value) => { obj.credentialMessage = value; } }, metadata: _metadata }, _credentialMessage_initializers, _credentialMessage_extraInitializers);
|
|
232
|
+
__esDecorate(this, null, _orgMenuOpen_decorators, { kind: "accessor", name: "orgMenuOpen", static: false, private: false, access: { has: obj => "orgMenuOpen" in obj, get: obj => obj.orgMenuOpen, set: (obj, value) => { obj.orgMenuOpen = value; } }, metadata: _metadata }, _orgMenuOpen_initializers, _orgMenuOpen_extraInitializers);
|
|
233
|
+
__esDecorate(this, null, _currentPassword_decorators, { kind: "accessor", name: "currentPassword", static: false, private: false, access: { has: obj => "currentPassword" in obj, get: obj => obj.currentPassword, set: (obj, value) => { obj.currentPassword = value; } }, metadata: _metadata }, _currentPassword_initializers, _currentPassword_extraInitializers);
|
|
234
|
+
__esDecorate(this, null, _newPassword_decorators, { kind: "accessor", name: "newPassword", static: false, private: false, access: { has: obj => "newPassword" in obj, get: obj => obj.newPassword, set: (obj, value) => { obj.newPassword = value; } }, metadata: _metadata }, _newPassword_initializers, _newPassword_extraInitializers);
|
|
235
|
+
__esDecorate(this, null, _confirmPassword_decorators, { kind: "accessor", name: "confirmPassword", static: false, private: false, access: { has: obj => "confirmPassword" in obj, get: obj => obj.confirmPassword, set: (obj, value) => { obj.confirmPassword = value; } }, metadata: _metadata }, _confirmPassword_initializers, _confirmPassword_extraInitializers);
|
|
236
|
+
__esDecorate(this, null, _credentialError_decorators, { kind: "accessor", name: "credentialError", static: false, private: false, access: { has: obj => "credentialError" in obj, get: obj => obj.credentialError, set: (obj, value) => { obj.credentialError = value; } }, metadata: _metadata }, _credentialError_initializers, _credentialError_extraInitializers);
|
|
237
|
+
__esDecorate(this, null, _orgSettingsOrgId_decorators, { kind: "accessor", name: "orgSettingsOrgId", static: false, private: false, access: { has: obj => "orgSettingsOrgId" in obj, get: obj => obj.orgSettingsOrgId, set: (obj, value) => { obj.orgSettingsOrgId = value; } }, metadata: _metadata }, _orgSettingsOrgId_initializers, _orgSettingsOrgId_extraInitializers);
|
|
238
|
+
__esDecorate(this, null, _orgNameDraft_decorators, { kind: "accessor", name: "orgNameDraft", static: false, private: false, access: { has: obj => "orgNameDraft" in obj, get: obj => obj.orgNameDraft, set: (obj, value) => { obj.orgNameDraft = value; } }, metadata: _metadata }, _orgNameDraft_initializers, _orgNameDraft_extraInitializers);
|
|
239
|
+
__esDecorate(this, null, _orgSlugDraft_decorators, { kind: "accessor", name: "orgSlugDraft", static: false, private: false, access: { has: obj => "orgSlugDraft" in obj, get: obj => obj.orgSlugDraft, set: (obj, value) => { obj.orgSlugDraft = value; } }, metadata: _metadata }, _orgSlugDraft_initializers, _orgSlugDraft_extraInitializers);
|
|
240
|
+
__esDecorate(this, null, _orgSettingsConfirmation_decorators, { kind: "accessor", name: "orgSettingsConfirmation", static: false, private: false, access: { has: obj => "orgSettingsConfirmation" in obj, get: obj => obj.orgSettingsConfirmation, set: (obj, value) => { obj.orgSettingsConfirmation = value; } }, metadata: _metadata }, _orgSettingsConfirmation_initializers, _orgSettingsConfirmation_extraInitializers);
|
|
241
|
+
__esDecorate(this, null, _transferOwnerId_decorators, { kind: "accessor", name: "transferOwnerId", static: false, private: false, access: { has: obj => "transferOwnerId" in obj, get: obj => obj.transferOwnerId, set: (obj, value) => { obj.transferOwnerId = value; } }, metadata: _metadata }, _transferOwnerId_initializers, _transferOwnerId_extraInitializers);
|
|
242
|
+
__esDecorate(this, null, _transferConfirmation_decorators, { kind: "accessor", name: "transferConfirmation", static: false, private: false, access: { has: obj => "transferConfirmation" in obj, get: obj => obj.transferConfirmation, set: (obj, value) => { obj.transferConfirmation = value; } }, metadata: _metadata }, _transferConfirmation_initializers, _transferConfirmation_extraInitializers);
|
|
243
|
+
__esDecorate(this, null, _deleteConfirmation_decorators, { kind: "accessor", name: "deleteConfirmation", static: false, private: false, access: { has: obj => "deleteConfirmation" in obj, get: obj => obj.deleteConfirmation, set: (obj, value) => { obj.deleteConfirmation = value; } }, metadata: _metadata }, _deleteConfirmation_initializers, _deleteConfirmation_extraInitializers);
|
|
244
|
+
__esDecorate(this, null, _orgSettingsError_decorators, { kind: "accessor", name: "orgSettingsError", static: false, private: false, access: { has: obj => "orgSettingsError" in obj, get: obj => obj.orgSettingsError, set: (obj, value) => { obj.orgSettingsError = value; } }, metadata: _metadata }, _orgSettingsError_initializers, _orgSettingsError_extraInitializers);
|
|
245
|
+
__esDecorate(this, null, _dialogMode_decorators, { kind: "accessor", name: "dialogMode", static: false, private: false, access: { has: obj => "dialogMode" in obj, get: obj => obj.dialogMode, set: (obj, value) => { obj.dialogMode = value; } }, metadata: _metadata }, _dialogMode_initializers, _dialogMode_extraInitializers);
|
|
246
|
+
__esDecorate(this, null, _dialogError_decorators, { kind: "accessor", name: "dialogError", static: false, private: false, access: { has: obj => "dialogError" in obj, get: obj => obj.dialogError, set: (obj, value) => { obj.dialogError = value; } }, metadata: _metadata }, _dialogError_initializers, _dialogError_extraInitializers);
|
|
247
|
+
__esDecorate(this, null, _dialogRoleKey_decorators, { kind: "accessor", name: "dialogRoleKey", static: false, private: false, access: { has: obj => "dialogRoleKey" in obj, get: obj => obj.dialogRoleKey, set: (obj, value) => { obj.dialogRoleKey = value; } }, metadata: _metadata }, _dialogRoleKey_initializers, _dialogRoleKey_extraInitializers);
|
|
248
|
+
__esDecorate(this, null, _dialogRoleName_decorators, { kind: "accessor", name: "dialogRoleName", static: false, private: false, access: { has: obj => "dialogRoleName" in obj, get: obj => obj.dialogRoleName, set: (obj, value) => { obj.dialogRoleName = value; } }, metadata: _metadata }, _dialogRoleName_initializers, _dialogRoleName_extraInitializers);
|
|
249
|
+
__esDecorate(this, null, _dialogRoleDescription_decorators, { kind: "accessor", name: "dialogRoleDescription", static: false, private: false, access: { has: obj => "dialogRoleDescription" in obj, get: obj => obj.dialogRoleDescription, set: (obj, value) => { obj.dialogRoleDescription = value; } }, metadata: _metadata }, _dialogRoleDescription_initializers, _dialogRoleDescription_extraInitializers);
|
|
250
|
+
__esDecorate(this, null, _dialogRoleDeleteConfirmation_decorators, { kind: "accessor", name: "dialogRoleDeleteConfirmation", static: false, private: false, access: { has: obj => "dialogRoleDeleteConfirmation" in obj, get: obj => obj.dialogRoleDeleteConfirmation, set: (obj, value) => { obj.dialogRoleDeleteConfirmation = value; } }, metadata: _metadata }, _dialogRoleDeleteConfirmation_initializers, _dialogRoleDeleteConfirmation_extraInitializers);
|
|
251
|
+
__esDecorate(this, null, _dialogMember_decorators, { kind: "accessor", name: "dialogMember", static: false, private: false, access: { has: obj => "dialogMember" in obj, get: obj => obj.dialogMember, set: (obj, value) => { obj.dialogMember = value; } }, metadata: _metadata }, _dialogMember_initializers, _dialogMember_extraInitializers);
|
|
252
|
+
__esDecorate(this, null, _dialogMemberRoles_decorators, { kind: "accessor", name: "dialogMemberRoles", static: false, private: false, access: { has: obj => "dialogMemberRoles" in obj, get: obj => obj.dialogMemberRoles, set: (obj, value) => { obj.dialogMemberRoles = value; } }, metadata: _metadata }, _dialogMemberRoles_initializers, _dialogMemberRoles_extraInitializers);
|
|
253
|
+
__esDecorate(this, null, _dialogApp_decorators, { kind: "accessor", name: "dialogApp", static: false, private: false, access: { has: obj => "dialogApp" in obj, get: obj => obj.dialogApp, set: (obj, value) => { obj.dialogApp = value; } }, metadata: _metadata }, _dialogApp_initializers, _dialogApp_extraInitializers);
|
|
254
|
+
__esDecorate(this, null, _dialogAppMappings_decorators, { kind: "accessor", name: "dialogAppMappings", static: false, private: false, access: { has: obj => "dialogAppMappings" in obj, get: obj => obj.dialogAppMappings, set: (obj, value) => { obj.dialogAppMappings = value; } }, metadata: _metadata }, _dialogAppMappings_initializers, _dialogAppMappings_extraInitializers);
|
|
255
|
+
__esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
|
|
256
|
+
IdpAdminShell = _classThis = _classDescriptor.value;
|
|
257
|
+
if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
|
|
258
|
+
}
|
|
259
|
+
static demo = () => html `<idp-admin-shell global-admin></idp-admin-shell>`;
|
|
260
|
+
static demoGroups = ['idp.global v3 full pages'];
|
|
261
|
+
static styles = [
|
|
262
|
+
...idpElementStyles,
|
|
263
|
+
css `
|
|
264
|
+
:host {
|
|
265
|
+
display: block;
|
|
266
|
+
height: 100vh;
|
|
267
|
+
max-height: 100vh;
|
|
268
|
+
min-height: 0;
|
|
269
|
+
overflow: hidden;
|
|
270
|
+
color: var(--idp-fg);
|
|
271
|
+
}
|
|
272
|
+
.shell {
|
|
273
|
+
height: 100%;
|
|
274
|
+
min-height: 0;
|
|
275
|
+
display: grid;
|
|
276
|
+
grid-template-columns: 220px minmax(0, 1fr);
|
|
277
|
+
overflow: hidden;
|
|
278
|
+
border: 0;
|
|
279
|
+
background: var(--idp-bg);
|
|
280
|
+
}
|
|
281
|
+
.sidebar {
|
|
282
|
+
height: 100%;
|
|
283
|
+
min-height: 0;
|
|
284
|
+
display: flex;
|
|
285
|
+
flex-direction: column;
|
|
286
|
+
overflow: hidden;
|
|
287
|
+
border-right: 1px solid var(--idp-border);
|
|
288
|
+
background: var(--idp-bg);
|
|
289
|
+
}
|
|
290
|
+
.logo-block {
|
|
291
|
+
padding: 14px 16px 10px;
|
|
292
|
+
border-bottom: 1px solid var(--idp-border);
|
|
293
|
+
}
|
|
294
|
+
.logo {
|
|
295
|
+
display: flex;
|
|
296
|
+
align-items: center;
|
|
297
|
+
gap: 8px;
|
|
298
|
+
}
|
|
299
|
+
.logo-icon {
|
|
300
|
+
width: 26px;
|
|
301
|
+
height: 26px;
|
|
302
|
+
display: flex;
|
|
303
|
+
align-items: center;
|
|
304
|
+
justify-content: center;
|
|
305
|
+
flex-shrink: 0;
|
|
306
|
+
border-radius: 7px;
|
|
307
|
+
background: var(--idp-primary);
|
|
308
|
+
color: var(--idp-primary-fg);
|
|
309
|
+
}
|
|
310
|
+
.logo-text {
|
|
311
|
+
color: var(--idp-fg);
|
|
312
|
+
font-size: 13px;
|
|
313
|
+
font-weight: 700;
|
|
314
|
+
letter-spacing: -0.3px;
|
|
315
|
+
}
|
|
316
|
+
.nav-wrap {
|
|
317
|
+
flex: 1;
|
|
318
|
+
min-height: 0;
|
|
319
|
+
overflow: auto;
|
|
320
|
+
padding: 10px 8px;
|
|
321
|
+
}
|
|
322
|
+
.state-card {
|
|
323
|
+
padding: 42px 24px;
|
|
324
|
+
border: 1px solid var(--idp-border);
|
|
325
|
+
border-radius: var(--idp-radius);
|
|
326
|
+
background: var(--idp-card);
|
|
327
|
+
color: var(--idp-muted-fg);
|
|
328
|
+
text-align: center;
|
|
329
|
+
}
|
|
330
|
+
.state-icon {
|
|
331
|
+
width: 38px;
|
|
332
|
+
height: 38px;
|
|
333
|
+
display: inline-flex;
|
|
334
|
+
align-items: center;
|
|
335
|
+
justify-content: center;
|
|
336
|
+
margin-bottom: 12px;
|
|
337
|
+
border: 1px solid var(--idp-border);
|
|
338
|
+
border-radius: 10px;
|
|
339
|
+
background: var(--idp-muted);
|
|
340
|
+
color: var(--idp-muted-fg);
|
|
341
|
+
}
|
|
342
|
+
.state-title {
|
|
343
|
+
margin-bottom: 4px;
|
|
344
|
+
color: var(--idp-fg);
|
|
345
|
+
font-size: 14px;
|
|
346
|
+
font-weight: 600;
|
|
347
|
+
}
|
|
348
|
+
.state-description {
|
|
349
|
+
max-width: 420px;
|
|
350
|
+
margin: 0 auto;
|
|
351
|
+
font-size: 12px;
|
|
352
|
+
line-height: 1.5;
|
|
353
|
+
}
|
|
354
|
+
.notice-card {
|
|
355
|
+
display: flex;
|
|
356
|
+
align-items: flex-start;
|
|
357
|
+
gap: 12px;
|
|
358
|
+
padding: 14px 16px;
|
|
359
|
+
border: 1px solid var(--idp-info-border);
|
|
360
|
+
border-radius: var(--idp-radius);
|
|
361
|
+
background: var(--idp-info-bg);
|
|
362
|
+
color: var(--idp-info);
|
|
363
|
+
}
|
|
364
|
+
.notice-card .muted {
|
|
365
|
+
color: var(--idp-muted-fg);
|
|
366
|
+
}
|
|
367
|
+
.nav-section {
|
|
368
|
+
margin-bottom: 20px;
|
|
369
|
+
}
|
|
370
|
+
.nav-title {
|
|
371
|
+
padding: 0 8px;
|
|
372
|
+
margin-bottom: 4px;
|
|
373
|
+
color: var(--idp-muted-fg);
|
|
374
|
+
font-size: 10px;
|
|
375
|
+
font-weight: 600;
|
|
376
|
+
letter-spacing: 0.8px;
|
|
377
|
+
text-transform: uppercase;
|
|
378
|
+
}
|
|
379
|
+
.nav-list {
|
|
380
|
+
display: grid;
|
|
381
|
+
}
|
|
382
|
+
.nav-item,
|
|
383
|
+
.org-switch,
|
|
384
|
+
.plain-button {
|
|
385
|
+
border: 0;
|
|
386
|
+
font-family: inherit;
|
|
387
|
+
}
|
|
388
|
+
.nav-item {
|
|
389
|
+
width: 100%;
|
|
390
|
+
display: flex;
|
|
391
|
+
align-items: center;
|
|
392
|
+
gap: 8px;
|
|
393
|
+
padding: 6px 8px;
|
|
394
|
+
border-radius: 7px;
|
|
395
|
+
background: transparent;
|
|
396
|
+
color: var(--idp-muted-fg);
|
|
397
|
+
font-size: 13px;
|
|
398
|
+
font-weight: 400;
|
|
399
|
+
text-align: left;
|
|
400
|
+
}
|
|
401
|
+
.nav-item.active {
|
|
402
|
+
background: var(--idp-muted);
|
|
403
|
+
color: var(--idp-fg);
|
|
404
|
+
font-weight: 500;
|
|
405
|
+
}
|
|
406
|
+
.nav-item idp-icon {
|
|
407
|
+
color: currentColor;
|
|
408
|
+
}
|
|
409
|
+
.nav-item.active idp-icon {
|
|
410
|
+
color: var(--idp-accent);
|
|
411
|
+
}
|
|
412
|
+
.org-switch-wrap {
|
|
413
|
+
position: relative;
|
|
414
|
+
margin-bottom: 2px;
|
|
415
|
+
}
|
|
416
|
+
.org-switch {
|
|
417
|
+
width: 100%;
|
|
418
|
+
display: flex;
|
|
419
|
+
align-items: center;
|
|
420
|
+
gap: 8px;
|
|
421
|
+
padding: 6px 8px;
|
|
422
|
+
border-radius: 7px;
|
|
423
|
+
background: transparent;
|
|
424
|
+
color: var(--idp-muted-fg);
|
|
425
|
+
cursor: pointer;
|
|
426
|
+
}
|
|
427
|
+
.org-switch:hover {
|
|
428
|
+
background: var(--idp-muted);
|
|
429
|
+
}
|
|
430
|
+
.org-switch.open {
|
|
431
|
+
background: var(--idp-muted);
|
|
432
|
+
}
|
|
433
|
+
.org-switch.open .org-name {
|
|
434
|
+
color: var(--idp-accent);
|
|
435
|
+
}
|
|
436
|
+
.org-switch.open idp-icon {
|
|
437
|
+
transform: rotate(180deg);
|
|
438
|
+
}
|
|
439
|
+
.org-menu {
|
|
440
|
+
position: absolute;
|
|
441
|
+
top: calc(100% + 4px);
|
|
442
|
+
left: 0;
|
|
443
|
+
right: 0;
|
|
444
|
+
z-index: 40;
|
|
445
|
+
overflow: hidden;
|
|
446
|
+
border: 1px solid var(--idp-border);
|
|
447
|
+
border-radius: 10px;
|
|
448
|
+
background: var(--idp-card);
|
|
449
|
+
box-shadow: 0 8px 24px rgba(0, 0, 0, 0.1);
|
|
450
|
+
}
|
|
451
|
+
.org-menu-title {
|
|
452
|
+
padding: 6px 8px 3px;
|
|
453
|
+
color: var(--idp-muted-fg);
|
|
454
|
+
font-size: 10px;
|
|
455
|
+
font-weight: 600;
|
|
456
|
+
letter-spacing: 0.7px;
|
|
457
|
+
text-transform: uppercase;
|
|
458
|
+
}
|
|
459
|
+
.org-menu-item,
|
|
460
|
+
.org-create {
|
|
461
|
+
width: 100%;
|
|
462
|
+
display: flex;
|
|
463
|
+
align-items: center;
|
|
464
|
+
gap: 8px;
|
|
465
|
+
border: 0;
|
|
466
|
+
background: transparent;
|
|
467
|
+
font-family: inherit;
|
|
468
|
+
text-align: left;
|
|
469
|
+
}
|
|
470
|
+
.org-menu-item {
|
|
471
|
+
padding: 6px 8px;
|
|
472
|
+
cursor: pointer;
|
|
473
|
+
}
|
|
474
|
+
.org-menu-item.selected {
|
|
475
|
+
background: var(--idp-accent-soft);
|
|
476
|
+
}
|
|
477
|
+
.org-menu-item .org-avatar {
|
|
478
|
+
width: 20px;
|
|
479
|
+
height: 20px;
|
|
480
|
+
font-size: 7px;
|
|
481
|
+
}
|
|
482
|
+
.org-menu-name {
|
|
483
|
+
overflow: hidden;
|
|
484
|
+
color: var(--idp-fg);
|
|
485
|
+
font-size: 12px;
|
|
486
|
+
font-weight: 400;
|
|
487
|
+
text-overflow: ellipsis;
|
|
488
|
+
white-space: nowrap;
|
|
489
|
+
}
|
|
490
|
+
.org-menu-item.selected .org-menu-name {
|
|
491
|
+
color: var(--idp-accent);
|
|
492
|
+
}
|
|
493
|
+
.org-menu-role {
|
|
494
|
+
color: var(--idp-muted-fg);
|
|
495
|
+
font-size: 10px;
|
|
496
|
+
}
|
|
497
|
+
.org-menu-divider {
|
|
498
|
+
height: 1px;
|
|
499
|
+
margin: 3px 0;
|
|
500
|
+
background: var(--idp-border);
|
|
501
|
+
}
|
|
502
|
+
.org-create {
|
|
503
|
+
padding: 6px 8px 8px;
|
|
504
|
+
color: var(--idp-muted-fg);
|
|
505
|
+
cursor: pointer;
|
|
506
|
+
font-size: 12px;
|
|
507
|
+
}
|
|
508
|
+
.org-create-icon {
|
|
509
|
+
width: 20px;
|
|
510
|
+
height: 20px;
|
|
511
|
+
display: flex;
|
|
512
|
+
align-items: center;
|
|
513
|
+
justify-content: center;
|
|
514
|
+
flex-shrink: 0;
|
|
515
|
+
border: 1.5px dashed var(--idp-border);
|
|
516
|
+
border-radius: 5px;
|
|
517
|
+
}
|
|
518
|
+
.org-name {
|
|
519
|
+
flex: 1;
|
|
520
|
+
min-width: 0;
|
|
521
|
+
overflow: hidden;
|
|
522
|
+
color: var(--idp-muted-fg);
|
|
523
|
+
font-size: 13px;
|
|
524
|
+
font-weight: 400;
|
|
525
|
+
text-align: left;
|
|
526
|
+
text-overflow: ellipsis;
|
|
527
|
+
white-space: nowrap;
|
|
528
|
+
}
|
|
529
|
+
.org-avatar,
|
|
530
|
+
.user-avatar {
|
|
531
|
+
display: flex;
|
|
532
|
+
align-items: center;
|
|
533
|
+
justify-content: center;
|
|
534
|
+
flex-shrink: 0;
|
|
535
|
+
font-family: var(--idp-mono);
|
|
536
|
+
font-weight: 700;
|
|
537
|
+
}
|
|
538
|
+
.org-avatar {
|
|
539
|
+
width: 14px;
|
|
540
|
+
height: 14px;
|
|
541
|
+
border: 1px solid var(--idp-border);
|
|
542
|
+
border-radius: 6px;
|
|
543
|
+
background: var(--idp-accent-soft);
|
|
544
|
+
color: var(--idp-accent);
|
|
545
|
+
font-size: 5px;
|
|
546
|
+
}
|
|
547
|
+
.user-footer {
|
|
548
|
+
display: flex;
|
|
549
|
+
align-items: center;
|
|
550
|
+
gap: 9px;
|
|
551
|
+
padding: 10px 12px;
|
|
552
|
+
border-top: 1px solid var(--idp-border);
|
|
553
|
+
}
|
|
554
|
+
.user-avatar {
|
|
555
|
+
width: 26px;
|
|
556
|
+
height: 26px;
|
|
557
|
+
border-radius: 50%;
|
|
558
|
+
background: oklch(0.85 0.08 240);
|
|
559
|
+
color: oklch(0.3 0.08 240);
|
|
560
|
+
font-size: 9px;
|
|
561
|
+
}
|
|
562
|
+
.user-meta {
|
|
563
|
+
flex: 1;
|
|
564
|
+
min-width: 0;
|
|
565
|
+
}
|
|
566
|
+
.user-name,
|
|
567
|
+
.user-email {
|
|
568
|
+
overflow: hidden;
|
|
569
|
+
text-overflow: ellipsis;
|
|
570
|
+
white-space: nowrap;
|
|
571
|
+
}
|
|
572
|
+
.user-name {
|
|
573
|
+
color: var(--idp-fg);
|
|
574
|
+
font-size: 12px;
|
|
575
|
+
font-weight: 500;
|
|
576
|
+
}
|
|
577
|
+
.user-email {
|
|
578
|
+
color: var(--idp-muted-fg);
|
|
579
|
+
font-size: 10px;
|
|
580
|
+
}
|
|
581
|
+
main {
|
|
582
|
+
height: 100%;
|
|
583
|
+
min-height: 0;
|
|
584
|
+
min-width: 0;
|
|
585
|
+
overflow: auto;
|
|
586
|
+
background: var(--idp-bg);
|
|
587
|
+
}
|
|
588
|
+
.page-head {
|
|
589
|
+
display: flex;
|
|
590
|
+
align-items: flex-end;
|
|
591
|
+
justify-content: space-between;
|
|
592
|
+
gap: 16px;
|
|
593
|
+
flex-wrap: wrap;
|
|
594
|
+
padding: 24px 28px 18px;
|
|
595
|
+
border-bottom: 1px solid var(--idp-border);
|
|
596
|
+
background: var(--idp-bg);
|
|
597
|
+
}
|
|
598
|
+
.eyebrow-row {
|
|
599
|
+
display: flex;
|
|
600
|
+
align-items: center;
|
|
601
|
+
gap: 8px;
|
|
602
|
+
margin-bottom: 4px;
|
|
603
|
+
}
|
|
604
|
+
.eyebrow {
|
|
605
|
+
color: var(--idp-muted-fg);
|
|
606
|
+
font-family: var(--idp-mono);
|
|
607
|
+
font-size: 10px;
|
|
608
|
+
font-weight: 600;
|
|
609
|
+
letter-spacing: 0.08em;
|
|
610
|
+
text-transform: uppercase;
|
|
611
|
+
}
|
|
612
|
+
.live-pill {
|
|
613
|
+
display: inline-flex;
|
|
614
|
+
align-items: center;
|
|
615
|
+
gap: 4px;
|
|
616
|
+
padding: 1px 7px;
|
|
617
|
+
border: 1px solid var(--idp-ok-border);
|
|
618
|
+
border-radius: 999px;
|
|
619
|
+
background: var(--idp-ok-bg);
|
|
620
|
+
color: var(--idp-ok);
|
|
621
|
+
font-family: var(--idp-mono);
|
|
622
|
+
font-size: 10px;
|
|
623
|
+
font-weight: 500;
|
|
624
|
+
}
|
|
625
|
+
.live-dot,
|
|
626
|
+
.feed-dot {
|
|
627
|
+
width: 6px;
|
|
628
|
+
height: 6px;
|
|
629
|
+
border-radius: 50%;
|
|
630
|
+
background: var(--idp-ok);
|
|
631
|
+
box-shadow: 0 0 6px var(--idp-ok);
|
|
632
|
+
animation: idp-blink 1.6s ease-in-out infinite;
|
|
633
|
+
}
|
|
634
|
+
@keyframes idp-blink {
|
|
635
|
+
0%, 100% { opacity: 1; }
|
|
636
|
+
50% { opacity: 0.35; }
|
|
637
|
+
}
|
|
638
|
+
h1,
|
|
639
|
+
h2 {
|
|
640
|
+
margin: 0;
|
|
641
|
+
color: var(--idp-fg);
|
|
642
|
+
font-family: var(--idp-display);
|
|
643
|
+
letter-spacing: -0.025em;
|
|
644
|
+
}
|
|
645
|
+
h1 {
|
|
646
|
+
font-size: 26px;
|
|
647
|
+
font-weight: 700;
|
|
648
|
+
line-height: 1.1;
|
|
649
|
+
}
|
|
650
|
+
.lead {
|
|
651
|
+
margin-top: 4px;
|
|
652
|
+
color: var(--idp-muted-fg);
|
|
653
|
+
font-size: 13px;
|
|
654
|
+
}
|
|
655
|
+
.lead code,
|
|
656
|
+
.mono {
|
|
657
|
+
color: var(--idp-info);
|
|
658
|
+
font-family: var(--idp-mono);
|
|
659
|
+
}
|
|
660
|
+
.page-actions {
|
|
661
|
+
display: flex;
|
|
662
|
+
align-items: center;
|
|
663
|
+
gap: 12px;
|
|
664
|
+
}
|
|
665
|
+
.tabs {
|
|
666
|
+
display: inline-flex;
|
|
667
|
+
gap: 1px;
|
|
668
|
+
padding: 2px;
|
|
669
|
+
border: 1px solid var(--idp-border);
|
|
670
|
+
border-radius: 6px;
|
|
671
|
+
background: var(--idp-bg-2);
|
|
672
|
+
}
|
|
673
|
+
.tab {
|
|
674
|
+
padding: 4px 10px;
|
|
675
|
+
border-radius: 4px;
|
|
676
|
+
color: var(--idp-muted-fg);
|
|
677
|
+
font-family: var(--idp-mono);
|
|
678
|
+
font-size: 11px;
|
|
679
|
+
font-weight: 500;
|
|
680
|
+
}
|
|
681
|
+
.tab.active {
|
|
682
|
+
background: var(--idp-muted);
|
|
683
|
+
color: var(--idp-fg);
|
|
684
|
+
}
|
|
685
|
+
.plain-button {
|
|
686
|
+
display: inline-flex;
|
|
687
|
+
align-items: center;
|
|
688
|
+
gap: 6px;
|
|
689
|
+
height: 28px;
|
|
690
|
+
padding: 5px 10px;
|
|
691
|
+
border-radius: 8px;
|
|
692
|
+
background: transparent;
|
|
693
|
+
color: var(--idp-fg);
|
|
694
|
+
font-size: 12px;
|
|
695
|
+
font-weight: 500;
|
|
696
|
+
white-space: nowrap;
|
|
697
|
+
}
|
|
698
|
+
.plain-button.outline {
|
|
699
|
+
border: 1px solid var(--idp-border);
|
|
700
|
+
}
|
|
701
|
+
.plain-button.primary {
|
|
702
|
+
background: var(--idp-accent);
|
|
703
|
+
color: var(--idp-accent-fg);
|
|
704
|
+
}
|
|
705
|
+
.plain-button.destructive {
|
|
706
|
+
background: var(--idp-destructive);
|
|
707
|
+
color: var(--idp-accent-fg);
|
|
708
|
+
}
|
|
709
|
+
.plain-button.ghost {
|
|
710
|
+
color: var(--idp-fg);
|
|
711
|
+
}
|
|
712
|
+
.plain-button:disabled {
|
|
713
|
+
opacity: 0.45;
|
|
714
|
+
cursor: not-allowed;
|
|
715
|
+
}
|
|
716
|
+
.body {
|
|
717
|
+
display: flex;
|
|
718
|
+
flex-direction: column;
|
|
719
|
+
gap: 16px;
|
|
720
|
+
padding: 20px 28px 32px;
|
|
721
|
+
}
|
|
722
|
+
.narrow-body {
|
|
723
|
+
max-width: 700px;
|
|
724
|
+
}
|
|
725
|
+
.wide-body {
|
|
726
|
+
max-width: 860px;
|
|
727
|
+
}
|
|
728
|
+
.section-card {
|
|
729
|
+
margin-bottom: 16px;
|
|
730
|
+
padding: 20px;
|
|
731
|
+
border: 1px solid var(--idp-border);
|
|
732
|
+
border-radius: var(--idp-radius);
|
|
733
|
+
background: var(--idp-card);
|
|
734
|
+
}
|
|
735
|
+
.section-card.compact {
|
|
736
|
+
padding: 14px;
|
|
737
|
+
}
|
|
738
|
+
.section-headline {
|
|
739
|
+
display: flex;
|
|
740
|
+
align-items: flex-start;
|
|
741
|
+
justify-content: space-between;
|
|
742
|
+
gap: 16px;
|
|
743
|
+
margin-bottom: 16px;
|
|
744
|
+
}
|
|
745
|
+
.section-title {
|
|
746
|
+
color: var(--idp-fg);
|
|
747
|
+
font-size: 14px;
|
|
748
|
+
font-weight: 600;
|
|
749
|
+
}
|
|
750
|
+
.section-description,
|
|
751
|
+
.muted {
|
|
752
|
+
color: var(--idp-muted-fg);
|
|
753
|
+
font-size: 12px;
|
|
754
|
+
line-height: 1.5;
|
|
755
|
+
}
|
|
756
|
+
.form-row {
|
|
757
|
+
display: grid;
|
|
758
|
+
grid-template-columns: 180px 1fr;
|
|
759
|
+
gap: 16px;
|
|
760
|
+
align-items: start;
|
|
761
|
+
padding: 12px 0;
|
|
762
|
+
border-bottom: 1px solid var(--idp-border);
|
|
763
|
+
}
|
|
764
|
+
.form-row:last-child {
|
|
765
|
+
border-bottom: 0;
|
|
766
|
+
}
|
|
767
|
+
.form-label {
|
|
768
|
+
display: flex;
|
|
769
|
+
gap: 3px;
|
|
770
|
+
color: var(--idp-fg);
|
|
771
|
+
font-size: 13px;
|
|
772
|
+
font-weight: 500;
|
|
773
|
+
}
|
|
774
|
+
.form-hint {
|
|
775
|
+
margin-top: 2px;
|
|
776
|
+
color: var(--idp-muted-fg);
|
|
777
|
+
font-size: 12px;
|
|
778
|
+
line-height: 1.4;
|
|
779
|
+
}
|
|
780
|
+
.input,
|
|
781
|
+
.select,
|
|
782
|
+
.textarea {
|
|
783
|
+
box-sizing: border-box;
|
|
784
|
+
width: 100%;
|
|
785
|
+
border: 1px solid var(--idp-border);
|
|
786
|
+
border-radius: 8px;
|
|
787
|
+
outline: none;
|
|
788
|
+
background: var(--idp-bg);
|
|
789
|
+
color: var(--idp-fg);
|
|
790
|
+
font-family: inherit;
|
|
791
|
+
font-size: 13px;
|
|
792
|
+
}
|
|
793
|
+
.input,
|
|
794
|
+
.select {
|
|
795
|
+
height: 34px;
|
|
796
|
+
padding: 0 10px;
|
|
797
|
+
}
|
|
798
|
+
.textarea {
|
|
799
|
+
min-height: 96px;
|
|
800
|
+
padding: 8px 10px;
|
|
801
|
+
resize: vertical;
|
|
802
|
+
}
|
|
803
|
+
.input-group {
|
|
804
|
+
display: flex;
|
|
805
|
+
overflow: hidden;
|
|
806
|
+
border: 1px solid var(--idp-border);
|
|
807
|
+
border-radius: 8px;
|
|
808
|
+
background: var(--idp-bg);
|
|
809
|
+
}
|
|
810
|
+
.input-prefix {
|
|
811
|
+
height: 34px;
|
|
812
|
+
display: flex;
|
|
813
|
+
align-items: center;
|
|
814
|
+
padding: 0 8px;
|
|
815
|
+
border-right: 1px solid var(--idp-border);
|
|
816
|
+
background: var(--idp-muted);
|
|
817
|
+
color: var(--idp-muted-fg);
|
|
818
|
+
font-family: var(--idp-mono);
|
|
819
|
+
font-size: 12px;
|
|
820
|
+
white-space: nowrap;
|
|
821
|
+
}
|
|
822
|
+
.input-group .input {
|
|
823
|
+
border: 0;
|
|
824
|
+
border-radius: 0;
|
|
825
|
+
background: transparent;
|
|
826
|
+
}
|
|
827
|
+
.divider {
|
|
828
|
+
height: 1px;
|
|
829
|
+
margin: 16px 0;
|
|
830
|
+
background: var(--idp-border);
|
|
831
|
+
}
|
|
832
|
+
.code-block {
|
|
833
|
+
display: flex;
|
|
834
|
+
align-items: center;
|
|
835
|
+
gap: 8px;
|
|
836
|
+
padding: 6px 10px;
|
|
837
|
+
border: 1px solid var(--idp-border);
|
|
838
|
+
border-radius: 7px;
|
|
839
|
+
background: var(--idp-muted);
|
|
840
|
+
}
|
|
841
|
+
.code-block code {
|
|
842
|
+
flex: 1;
|
|
843
|
+
overflow-wrap: anywhere;
|
|
844
|
+
color: var(--idp-fg);
|
|
845
|
+
font-family: var(--idp-mono);
|
|
846
|
+
font-size: 12px;
|
|
847
|
+
}
|
|
848
|
+
.avatar,
|
|
849
|
+
.app-avatar,
|
|
850
|
+
.icon-tile {
|
|
851
|
+
display: flex;
|
|
852
|
+
align-items: center;
|
|
853
|
+
justify-content: center;
|
|
854
|
+
flex-shrink: 0;
|
|
855
|
+
}
|
|
856
|
+
.avatar {
|
|
857
|
+
border-radius: 50%;
|
|
858
|
+
background: oklch(0.85 0.08 240);
|
|
859
|
+
color: oklch(0.3 0.08 240);
|
|
860
|
+
font-family: var(--idp-mono);
|
|
861
|
+
font-weight: 600;
|
|
862
|
+
}
|
|
863
|
+
.app-avatar,
|
|
864
|
+
.icon-tile {
|
|
865
|
+
border: 1px solid var(--idp-border);
|
|
866
|
+
border-radius: 10px;
|
|
867
|
+
background: var(--idp-muted);
|
|
868
|
+
color: var(--idp-muted-fg);
|
|
869
|
+
}
|
|
870
|
+
.app-avatar {
|
|
871
|
+
width: 40px;
|
|
872
|
+
height: 40px;
|
|
873
|
+
background: var(--idp-accent-soft);
|
|
874
|
+
color: var(--idp-accent);
|
|
875
|
+
font-size: 14px;
|
|
876
|
+
font-weight: 700;
|
|
877
|
+
}
|
|
878
|
+
.icon-tile {
|
|
879
|
+
width: 38px;
|
|
880
|
+
height: 38px;
|
|
881
|
+
}
|
|
882
|
+
.list-stack {
|
|
883
|
+
display: grid;
|
|
884
|
+
gap: 12px;
|
|
885
|
+
}
|
|
886
|
+
.row-card {
|
|
887
|
+
display: flex;
|
|
888
|
+
align-items: flex-start;
|
|
889
|
+
gap: 14px;
|
|
890
|
+
padding: 16px;
|
|
891
|
+
border: 1px solid var(--idp-border);
|
|
892
|
+
border-radius: var(--idp-radius);
|
|
893
|
+
background: var(--idp-card);
|
|
894
|
+
}
|
|
895
|
+
.split-row {
|
|
896
|
+
display: flex;
|
|
897
|
+
align-items: center;
|
|
898
|
+
justify-content: space-between;
|
|
899
|
+
gap: 16px;
|
|
900
|
+
}
|
|
901
|
+
.chip-row {
|
|
902
|
+
display: flex;
|
|
903
|
+
flex-wrap: wrap;
|
|
904
|
+
gap: 4px;
|
|
905
|
+
}
|
|
906
|
+
.switch {
|
|
907
|
+
width: 36px;
|
|
908
|
+
height: 20px;
|
|
909
|
+
position: relative;
|
|
910
|
+
flex-shrink: 0;
|
|
911
|
+
border-radius: 10px;
|
|
912
|
+
background: var(--idp-accent);
|
|
913
|
+
}
|
|
914
|
+
.switch::after {
|
|
915
|
+
content: '';
|
|
916
|
+
position: absolute;
|
|
917
|
+
top: 2px;
|
|
918
|
+
left: 18px;
|
|
919
|
+
width: 16px;
|
|
920
|
+
height: 16px;
|
|
921
|
+
border-radius: 8px;
|
|
922
|
+
background: #fff;
|
|
923
|
+
box-shadow: 0 1px 3px rgba(0, 0, 0, 0.2);
|
|
924
|
+
}
|
|
925
|
+
.sub-tabs {
|
|
926
|
+
width: fit-content;
|
|
927
|
+
display: flex;
|
|
928
|
+
gap: 2px;
|
|
929
|
+
margin-bottom: 16px;
|
|
930
|
+
padding: 3px;
|
|
931
|
+
border-radius: 8px;
|
|
932
|
+
background: var(--idp-muted);
|
|
933
|
+
}
|
|
934
|
+
.sub-tab {
|
|
935
|
+
padding: 5px 12px;
|
|
936
|
+
border-radius: 6px;
|
|
937
|
+
color: var(--idp-muted-fg);
|
|
938
|
+
font-size: 12px;
|
|
939
|
+
}
|
|
940
|
+
.sub-tab.active {
|
|
941
|
+
background: var(--idp-bg);
|
|
942
|
+
color: var(--idp-fg);
|
|
943
|
+
font-weight: 500;
|
|
944
|
+
box-shadow: 0 1px 3px rgba(0,0,0,0.06);
|
|
945
|
+
}
|
|
946
|
+
.kpis {
|
|
947
|
+
display: grid;
|
|
948
|
+
grid-template-columns: repeat(4, 1fr);
|
|
949
|
+
gap: 12px;
|
|
950
|
+
}
|
|
951
|
+
.kpi,
|
|
952
|
+
.card {
|
|
953
|
+
border: 1px solid var(--idp-border);
|
|
954
|
+
background: var(--idp-card);
|
|
955
|
+
}
|
|
956
|
+
.kpi {
|
|
957
|
+
position: relative;
|
|
958
|
+
min-height: 132px;
|
|
959
|
+
display: flex;
|
|
960
|
+
flex-direction: column;
|
|
961
|
+
gap: 4px;
|
|
962
|
+
overflow: hidden;
|
|
963
|
+
padding: 18px 20px 14px;
|
|
964
|
+
border-radius: 10px;
|
|
965
|
+
}
|
|
966
|
+
.kpi::before {
|
|
967
|
+
content: '';
|
|
968
|
+
position: absolute;
|
|
969
|
+
top: 0;
|
|
970
|
+
left: 0;
|
|
971
|
+
right: 0;
|
|
972
|
+
height: 2px;
|
|
973
|
+
background: var(--kpi-accent);
|
|
974
|
+
}
|
|
975
|
+
.kpi-label {
|
|
976
|
+
color: var(--idp-muted-fg);
|
|
977
|
+
font-size: 11.5px;
|
|
978
|
+
font-weight: 500;
|
|
979
|
+
letter-spacing: 0.02em;
|
|
980
|
+
}
|
|
981
|
+
.kpi-value {
|
|
982
|
+
color: var(--idp-fg);
|
|
983
|
+
font-family: var(--idp-display);
|
|
984
|
+
font-size: 30px;
|
|
985
|
+
font-weight: 700;
|
|
986
|
+
font-variant-numeric: tabular-nums;
|
|
987
|
+
letter-spacing: -0.025em;
|
|
988
|
+
line-height: 1.1;
|
|
989
|
+
}
|
|
990
|
+
.kpi-value span {
|
|
991
|
+
margin-left: 2px;
|
|
992
|
+
color: var(--idp-muted-fg);
|
|
993
|
+
font-size: 14px;
|
|
994
|
+
font-weight: 500;
|
|
995
|
+
}
|
|
996
|
+
.kpi-sub {
|
|
997
|
+
color: var(--idp-fg-3);
|
|
998
|
+
font-family: var(--idp-mono);
|
|
999
|
+
font-size: 11px;
|
|
1000
|
+
}
|
|
1001
|
+
.kpi-foot {
|
|
1002
|
+
display: flex;
|
|
1003
|
+
align-items: flex-end;
|
|
1004
|
+
justify-content: space-between;
|
|
1005
|
+
gap: 8px;
|
|
1006
|
+
margin-top: auto;
|
|
1007
|
+
}
|
|
1008
|
+
.delta {
|
|
1009
|
+
display: inline-flex;
|
|
1010
|
+
align-items: center;
|
|
1011
|
+
gap: 4px;
|
|
1012
|
+
color: var(--idp-ok);
|
|
1013
|
+
font-family: var(--idp-mono);
|
|
1014
|
+
font-size: 11px;
|
|
1015
|
+
font-weight: 600;
|
|
1016
|
+
}
|
|
1017
|
+
.sparkline {
|
|
1018
|
+
width: 84px;
|
|
1019
|
+
opacity: 0.85;
|
|
1020
|
+
}
|
|
1021
|
+
.primary-grid,
|
|
1022
|
+
.secondary-grid {
|
|
1023
|
+
display: grid;
|
|
1024
|
+
grid-template-columns: minmax(0, 1.6fr) minmax(300px, 1fr);
|
|
1025
|
+
gap: 16px;
|
|
1026
|
+
}
|
|
1027
|
+
.card {
|
|
1028
|
+
overflow: hidden;
|
|
1029
|
+
border-radius: 8px;
|
|
1030
|
+
}
|
|
1031
|
+
.card-head {
|
|
1032
|
+
display: flex;
|
|
1033
|
+
align-items: center;
|
|
1034
|
+
gap: 10px;
|
|
1035
|
+
padding: 12px 16px;
|
|
1036
|
+
border-bottom: 1px solid var(--idp-border-soft);
|
|
1037
|
+
}
|
|
1038
|
+
.card-title {
|
|
1039
|
+
color: var(--idp-fg);
|
|
1040
|
+
font-size: 13px;
|
|
1041
|
+
font-weight: 600;
|
|
1042
|
+
}
|
|
1043
|
+
.feed-dot {
|
|
1044
|
+
display: inline-block;
|
|
1045
|
+
width: 8px;
|
|
1046
|
+
height: 8px;
|
|
1047
|
+
border-radius: 4px;
|
|
1048
|
+
background: var(--dot-color);
|
|
1049
|
+
box-shadow: var(--dot-glow, none);
|
|
1050
|
+
}
|
|
1051
|
+
.feed-meta {
|
|
1052
|
+
color: var(--idp-muted-fg);
|
|
1053
|
+
font-family: var(--idp-mono);
|
|
1054
|
+
font-size: 11.5px;
|
|
1055
|
+
}
|
|
1056
|
+
.feed-item {
|
|
1057
|
+
display: grid;
|
|
1058
|
+
grid-template-columns: 14px 1fr auto;
|
|
1059
|
+
gap: 12px;
|
|
1060
|
+
align-items: center;
|
|
1061
|
+
padding: 11px 16px;
|
|
1062
|
+
border-bottom: 1px solid var(--idp-border-soft);
|
|
1063
|
+
}
|
|
1064
|
+
.feed-item:last-child {
|
|
1065
|
+
border-bottom: 0;
|
|
1066
|
+
}
|
|
1067
|
+
.feed-text {
|
|
1068
|
+
color: var(--idp-fg-2);
|
|
1069
|
+
font-size: 12.5px;
|
|
1070
|
+
}
|
|
1071
|
+
.feed-text strong {
|
|
1072
|
+
color: var(--idp-fg);
|
|
1073
|
+
font-weight: 600;
|
|
1074
|
+
}
|
|
1075
|
+
.dialog-backdrop {
|
|
1076
|
+
position: fixed;
|
|
1077
|
+
inset: 0;
|
|
1078
|
+
z-index: 100;
|
|
1079
|
+
display: flex;
|
|
1080
|
+
align-items: center;
|
|
1081
|
+
justify-content: center;
|
|
1082
|
+
padding: 20px;
|
|
1083
|
+
background: rgba(0, 0, 0, 0.42);
|
|
1084
|
+
}
|
|
1085
|
+
.dialog-card {
|
|
1086
|
+
width: min(720px, 100%);
|
|
1087
|
+
max-height: min(760px, calc(100vh - 40px));
|
|
1088
|
+
display: flex;
|
|
1089
|
+
flex-direction: column;
|
|
1090
|
+
overflow: hidden;
|
|
1091
|
+
border: 1px solid var(--idp-border);
|
|
1092
|
+
border-radius: 12px;
|
|
1093
|
+
background: var(--idp-card);
|
|
1094
|
+
box-shadow: 0 24px 80px rgba(0, 0, 0, 0.28);
|
|
1095
|
+
}
|
|
1096
|
+
.dialog-card.wide {
|
|
1097
|
+
width: min(980px, 100%);
|
|
1098
|
+
}
|
|
1099
|
+
.dialog-head {
|
|
1100
|
+
display: flex;
|
|
1101
|
+
align-items: flex-start;
|
|
1102
|
+
justify-content: space-between;
|
|
1103
|
+
gap: 16px;
|
|
1104
|
+
padding: 18px 20px 14px;
|
|
1105
|
+
border-bottom: 1px solid var(--idp-border);
|
|
1106
|
+
}
|
|
1107
|
+
.dialog-title {
|
|
1108
|
+
color: var(--idp-fg);
|
|
1109
|
+
font-size: 15px;
|
|
1110
|
+
font-weight: 700;
|
|
1111
|
+
}
|
|
1112
|
+
.dialog-body {
|
|
1113
|
+
display: grid;
|
|
1114
|
+
gap: 14px;
|
|
1115
|
+
overflow: auto;
|
|
1116
|
+
padding: 18px 20px;
|
|
1117
|
+
}
|
|
1118
|
+
.dialog-actions {
|
|
1119
|
+
display: flex;
|
|
1120
|
+
align-items: center;
|
|
1121
|
+
justify-content: flex-end;
|
|
1122
|
+
gap: 10px;
|
|
1123
|
+
padding: 14px 20px;
|
|
1124
|
+
border-top: 1px solid var(--idp-border);
|
|
1125
|
+
}
|
|
1126
|
+
.role-grid {
|
|
1127
|
+
display: grid;
|
|
1128
|
+
grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
|
|
1129
|
+
gap: 8px;
|
|
1130
|
+
}
|
|
1131
|
+
.role-option {
|
|
1132
|
+
display: flex;
|
|
1133
|
+
align-items: flex-start;
|
|
1134
|
+
gap: 8px;
|
|
1135
|
+
padding: 9px;
|
|
1136
|
+
border: 1px solid var(--idp-border);
|
|
1137
|
+
border-radius: 8px;
|
|
1138
|
+
background: var(--idp-bg);
|
|
1139
|
+
}
|
|
1140
|
+
.role-option input {
|
|
1141
|
+
margin-top: 2px;
|
|
1142
|
+
}
|
|
1143
|
+
.mapping-row {
|
|
1144
|
+
display: grid;
|
|
1145
|
+
grid-template-columns: 160px repeat(3, minmax(0, 1fr));
|
|
1146
|
+
gap: 8px;
|
|
1147
|
+
align-items: start;
|
|
1148
|
+
padding: 10px;
|
|
1149
|
+
border: 1px solid var(--idp-border);
|
|
1150
|
+
border-radius: 8px;
|
|
1151
|
+
background: var(--idp-bg);
|
|
1152
|
+
}
|
|
1153
|
+
.mapping-role {
|
|
1154
|
+
color: var(--idp-fg);
|
|
1155
|
+
font-size: 12px;
|
|
1156
|
+
font-weight: 600;
|
|
1157
|
+
}
|
|
1158
|
+
.mapping-role .muted {
|
|
1159
|
+
display: block;
|
|
1160
|
+
margin-top: 2px;
|
|
1161
|
+
}
|
|
1162
|
+
.mapping-row .form-row {
|
|
1163
|
+
display: block;
|
|
1164
|
+
padding: 0;
|
|
1165
|
+
border-bottom: 0;
|
|
1166
|
+
}
|
|
1167
|
+
.mapping-row .form-label {
|
|
1168
|
+
margin-bottom: 4px;
|
|
1169
|
+
}
|
|
1170
|
+
@media (max-width: 1120px) {
|
|
1171
|
+
.shell {
|
|
1172
|
+
grid-template-columns: 1fr;
|
|
1173
|
+
}
|
|
1174
|
+
.sidebar {
|
|
1175
|
+
display: none;
|
|
1176
|
+
}
|
|
1177
|
+
.kpis {
|
|
1178
|
+
grid-template-columns: repeat(2, 1fr);
|
|
1179
|
+
}
|
|
1180
|
+
.primary-grid,
|
|
1181
|
+
.secondary-grid {
|
|
1182
|
+
grid-template-columns: 1fr;
|
|
1183
|
+
}
|
|
1184
|
+
}
|
|
1185
|
+
@media (max-width: 720px) {
|
|
1186
|
+
.page-head,
|
|
1187
|
+
.body {
|
|
1188
|
+
padding-left: 20px;
|
|
1189
|
+
padding-right: 20px;
|
|
1190
|
+
}
|
|
1191
|
+
.page-actions {
|
|
1192
|
+
flex-wrap: wrap;
|
|
1193
|
+
}
|
|
1194
|
+
.kpis {
|
|
1195
|
+
grid-template-columns: 1fr;
|
|
1196
|
+
}
|
|
1197
|
+
.mapping-row {
|
|
1198
|
+
grid-template-columns: 1fr;
|
|
1199
|
+
}
|
|
1200
|
+
}
|
|
1201
|
+
`,
|
|
1202
|
+
];
|
|
1203
|
+
#page_accessor_storage = __runInitializers(this, _page_initializers, 'overview');
|
|
1204
|
+
get page() { return this.#page_accessor_storage; }
|
|
1205
|
+
set page(value) { this.#page_accessor_storage = value; }
|
|
1206
|
+
#user_accessor_storage = (__runInitializers(this, _page_extraInitializers), __runInitializers(this, _user_initializers, {
|
|
1207
|
+
name: '',
|
|
1208
|
+
email: '',
|
|
1209
|
+
}));
|
|
1210
|
+
get user() { return this.#user_accessor_storage; }
|
|
1211
|
+
set user(value) { this.#user_accessor_storage = value; }
|
|
1212
|
+
#orgs_accessor_storage = (__runInitializers(this, _user_extraInitializers), __runInitializers(this, _orgs_initializers, []));
|
|
1213
|
+
get orgs() { return this.#orgs_accessor_storage; }
|
|
1214
|
+
set orgs(value) { this.#orgs_accessor_storage = value; }
|
|
1215
|
+
#selectedOrgId_accessor_storage = (__runInitializers(this, _orgs_extraInitializers), __runInitializers(this, _selectedOrgId_initializers, ''));
|
|
1216
|
+
get selectedOrgId() { return this.#selectedOrgId_accessor_storage; }
|
|
1217
|
+
set selectedOrgId(value) { this.#selectedOrgId_accessor_storage = value; }
|
|
1218
|
+
#globalAdmin_accessor_storage = (__runInitializers(this, _selectedOrgId_extraInitializers), __runInitializers(this, _globalAdmin_initializers, false));
|
|
1219
|
+
get globalAdmin() { return this.#globalAdmin_accessor_storage; }
|
|
1220
|
+
set globalAdmin(value) { this.#globalAdmin_accessor_storage = value; }
|
|
1221
|
+
#dataLoading_accessor_storage = (__runInitializers(this, _globalAdmin_extraInitializers), __runInitializers(this, _dataLoading_initializers, false));
|
|
1222
|
+
get dataLoading() { return this.#dataLoading_accessor_storage; }
|
|
1223
|
+
set dataLoading(value) { this.#dataLoading_accessor_storage = value; }
|
|
1224
|
+
#dataError_accessor_storage = (__runInitializers(this, _dataLoading_extraInitializers), __runInitializers(this, _dataError_initializers, ''));
|
|
1225
|
+
get dataError() { return this.#dataError_accessor_storage; }
|
|
1226
|
+
set dataError(value) { this.#dataError_accessor_storage = value; }
|
|
1227
|
+
#sessions_accessor_storage = (__runInitializers(this, _dataError_extraInitializers), __runInitializers(this, _sessions_initializers, []));
|
|
1228
|
+
get sessions() { return this.#sessions_accessor_storage; }
|
|
1229
|
+
set sessions(value) { this.#sessions_accessor_storage = value; }
|
|
1230
|
+
#activities_accessor_storage = (__runInitializers(this, _sessions_extraInitializers), __runInitializers(this, _activities_initializers, []));
|
|
1231
|
+
get activities() { return this.#activities_accessor_storage; }
|
|
1232
|
+
set activities(value) { this.#activities_accessor_storage = value; }
|
|
1233
|
+
#orgMembers_accessor_storage = (__runInitializers(this, _activities_extraInitializers), __runInitializers(this, _orgMembers_initializers, []));
|
|
1234
|
+
get orgMembers() { return this.#orgMembers_accessor_storage; }
|
|
1235
|
+
set orgMembers(value) { this.#orgMembers_accessor_storage = value; }
|
|
1236
|
+
#orgInvitations_accessor_storage = (__runInitializers(this, _orgMembers_extraInitializers), __runInitializers(this, _orgInvitations_initializers, []));
|
|
1237
|
+
get orgInvitations() { return this.#orgInvitations_accessor_storage; }
|
|
1238
|
+
set orgInvitations(value) { this.#orgInvitations_accessor_storage = value; }
|
|
1239
|
+
#orgRoleDefinitions_accessor_storage = (__runInitializers(this, _orgInvitations_extraInitializers), __runInitializers(this, _orgRoleDefinitions_initializers, []));
|
|
1240
|
+
get orgRoleDefinitions() { return this.#orgRoleDefinitions_accessor_storage; }
|
|
1241
|
+
set orgRoleDefinitions(value) { this.#orgRoleDefinitions_accessor_storage = value; }
|
|
1242
|
+
#orgApps_accessor_storage = (__runInitializers(this, _orgRoleDefinitions_extraInitializers), __runInitializers(this, _orgApps_initializers, []));
|
|
1243
|
+
get orgApps() { return this.#orgApps_accessor_storage; }
|
|
1244
|
+
set orgApps(value) { this.#orgApps_accessor_storage = value; }
|
|
1245
|
+
#accountApps_accessor_storage = (__runInitializers(this, _orgApps_extraInitializers), __runInitializers(this, _accountApps_initializers, []));
|
|
1246
|
+
get accountApps() { return this.#accountApps_accessor_storage; }
|
|
1247
|
+
set accountApps(value) { this.#accountApps_accessor_storage = value; }
|
|
1248
|
+
#adminApps_accessor_storage = (__runInitializers(this, _accountApps_extraInitializers), __runInitializers(this, _adminApps_initializers, []));
|
|
1249
|
+
get adminApps() { return this.#adminApps_accessor_storage; }
|
|
1250
|
+
set adminApps(value) { this.#adminApps_accessor_storage = value; }
|
|
1251
|
+
#passportDevices_accessor_storage = (__runInitializers(this, _adminApps_extraInitializers), __runInitializers(this, _passportDevices_initializers, []));
|
|
1252
|
+
get passportDevices() { return this.#passportDevices_accessor_storage; }
|
|
1253
|
+
set passportDevices(value) { this.#passportDevices_accessor_storage = value; }
|
|
1254
|
+
#passportEnrollment_accessor_storage = (__runInitializers(this, _passportDevices_extraInitializers), __runInitializers(this, _passportEnrollment_initializers, null));
|
|
1255
|
+
get passportEnrollment() { return this.#passportEnrollment_accessor_storage; }
|
|
1256
|
+
set passportEnrollment(value) { this.#passportEnrollment_accessor_storage = value; }
|
|
1257
|
+
#credentialMessage_accessor_storage = (__runInitializers(this, _passportEnrollment_extraInitializers), __runInitializers(this, _credentialMessage_initializers, ''));
|
|
1258
|
+
get credentialMessage() { return this.#credentialMessage_accessor_storage; }
|
|
1259
|
+
set credentialMessage(value) { this.#credentialMessage_accessor_storage = value; }
|
|
1260
|
+
#orgMenuOpen_accessor_storage = (__runInitializers(this, _credentialMessage_extraInitializers), __runInitializers(this, _orgMenuOpen_initializers, false));
|
|
1261
|
+
get orgMenuOpen() { return this.#orgMenuOpen_accessor_storage; }
|
|
1262
|
+
set orgMenuOpen(value) { this.#orgMenuOpen_accessor_storage = value; }
|
|
1263
|
+
#currentPassword_accessor_storage = (__runInitializers(this, _orgMenuOpen_extraInitializers), __runInitializers(this, _currentPassword_initializers, ''));
|
|
1264
|
+
get currentPassword() { return this.#currentPassword_accessor_storage; }
|
|
1265
|
+
set currentPassword(value) { this.#currentPassword_accessor_storage = value; }
|
|
1266
|
+
#newPassword_accessor_storage = (__runInitializers(this, _currentPassword_extraInitializers), __runInitializers(this, _newPassword_initializers, ''));
|
|
1267
|
+
get newPassword() { return this.#newPassword_accessor_storage; }
|
|
1268
|
+
set newPassword(value) { this.#newPassword_accessor_storage = value; }
|
|
1269
|
+
#confirmPassword_accessor_storage = (__runInitializers(this, _newPassword_extraInitializers), __runInitializers(this, _confirmPassword_initializers, ''));
|
|
1270
|
+
get confirmPassword() { return this.#confirmPassword_accessor_storage; }
|
|
1271
|
+
set confirmPassword(value) { this.#confirmPassword_accessor_storage = value; }
|
|
1272
|
+
#credentialError_accessor_storage = (__runInitializers(this, _confirmPassword_extraInitializers), __runInitializers(this, _credentialError_initializers, ''));
|
|
1273
|
+
get credentialError() { return this.#credentialError_accessor_storage; }
|
|
1274
|
+
set credentialError(value) { this.#credentialError_accessor_storage = value; }
|
|
1275
|
+
#orgSettingsOrgId_accessor_storage = (__runInitializers(this, _credentialError_extraInitializers), __runInitializers(this, _orgSettingsOrgId_initializers, ''));
|
|
1276
|
+
get orgSettingsOrgId() { return this.#orgSettingsOrgId_accessor_storage; }
|
|
1277
|
+
set orgSettingsOrgId(value) { this.#orgSettingsOrgId_accessor_storage = value; }
|
|
1278
|
+
#orgNameDraft_accessor_storage = (__runInitializers(this, _orgSettingsOrgId_extraInitializers), __runInitializers(this, _orgNameDraft_initializers, ''));
|
|
1279
|
+
get orgNameDraft() { return this.#orgNameDraft_accessor_storage; }
|
|
1280
|
+
set orgNameDraft(value) { this.#orgNameDraft_accessor_storage = value; }
|
|
1281
|
+
#orgSlugDraft_accessor_storage = (__runInitializers(this, _orgNameDraft_extraInitializers), __runInitializers(this, _orgSlugDraft_initializers, ''));
|
|
1282
|
+
get orgSlugDraft() { return this.#orgSlugDraft_accessor_storage; }
|
|
1283
|
+
set orgSlugDraft(value) { this.#orgSlugDraft_accessor_storage = value; }
|
|
1284
|
+
#orgSettingsConfirmation_accessor_storage = (__runInitializers(this, _orgSlugDraft_extraInitializers), __runInitializers(this, _orgSettingsConfirmation_initializers, ''));
|
|
1285
|
+
get orgSettingsConfirmation() { return this.#orgSettingsConfirmation_accessor_storage; }
|
|
1286
|
+
set orgSettingsConfirmation(value) { this.#orgSettingsConfirmation_accessor_storage = value; }
|
|
1287
|
+
#transferOwnerId_accessor_storage = (__runInitializers(this, _orgSettingsConfirmation_extraInitializers), __runInitializers(this, _transferOwnerId_initializers, ''));
|
|
1288
|
+
get transferOwnerId() { return this.#transferOwnerId_accessor_storage; }
|
|
1289
|
+
set transferOwnerId(value) { this.#transferOwnerId_accessor_storage = value; }
|
|
1290
|
+
#transferConfirmation_accessor_storage = (__runInitializers(this, _transferOwnerId_extraInitializers), __runInitializers(this, _transferConfirmation_initializers, ''));
|
|
1291
|
+
get transferConfirmation() { return this.#transferConfirmation_accessor_storage; }
|
|
1292
|
+
set transferConfirmation(value) { this.#transferConfirmation_accessor_storage = value; }
|
|
1293
|
+
#deleteConfirmation_accessor_storage = (__runInitializers(this, _transferConfirmation_extraInitializers), __runInitializers(this, _deleteConfirmation_initializers, ''));
|
|
1294
|
+
get deleteConfirmation() { return this.#deleteConfirmation_accessor_storage; }
|
|
1295
|
+
set deleteConfirmation(value) { this.#deleteConfirmation_accessor_storage = value; }
|
|
1296
|
+
#orgSettingsError_accessor_storage = (__runInitializers(this, _deleteConfirmation_extraInitializers), __runInitializers(this, _orgSettingsError_initializers, ''));
|
|
1297
|
+
get orgSettingsError() { return this.#orgSettingsError_accessor_storage; }
|
|
1298
|
+
set orgSettingsError(value) { this.#orgSettingsError_accessor_storage = value; }
|
|
1299
|
+
#dialogMode_accessor_storage = (__runInitializers(this, _orgSettingsError_extraInitializers), __runInitializers(this, _dialogMode_initializers, 'none'));
|
|
1300
|
+
get dialogMode() { return this.#dialogMode_accessor_storage; }
|
|
1301
|
+
set dialogMode(value) { this.#dialogMode_accessor_storage = value; }
|
|
1302
|
+
#dialogError_accessor_storage = (__runInitializers(this, _dialogMode_extraInitializers), __runInitializers(this, _dialogError_initializers, ''));
|
|
1303
|
+
get dialogError() { return this.#dialogError_accessor_storage; }
|
|
1304
|
+
set dialogError(value) { this.#dialogError_accessor_storage = value; }
|
|
1305
|
+
#dialogRoleKey_accessor_storage = (__runInitializers(this, _dialogError_extraInitializers), __runInitializers(this, _dialogRoleKey_initializers, ''));
|
|
1306
|
+
get dialogRoleKey() { return this.#dialogRoleKey_accessor_storage; }
|
|
1307
|
+
set dialogRoleKey(value) { this.#dialogRoleKey_accessor_storage = value; }
|
|
1308
|
+
#dialogRoleName_accessor_storage = (__runInitializers(this, _dialogRoleKey_extraInitializers), __runInitializers(this, _dialogRoleName_initializers, ''));
|
|
1309
|
+
get dialogRoleName() { return this.#dialogRoleName_accessor_storage; }
|
|
1310
|
+
set dialogRoleName(value) { this.#dialogRoleName_accessor_storage = value; }
|
|
1311
|
+
#dialogRoleDescription_accessor_storage = (__runInitializers(this, _dialogRoleName_extraInitializers), __runInitializers(this, _dialogRoleDescription_initializers, ''));
|
|
1312
|
+
get dialogRoleDescription() { return this.#dialogRoleDescription_accessor_storage; }
|
|
1313
|
+
set dialogRoleDescription(value) { this.#dialogRoleDescription_accessor_storage = value; }
|
|
1314
|
+
#dialogRoleDeleteConfirmation_accessor_storage = (__runInitializers(this, _dialogRoleDescription_extraInitializers), __runInitializers(this, _dialogRoleDeleteConfirmation_initializers, ''));
|
|
1315
|
+
get dialogRoleDeleteConfirmation() { return this.#dialogRoleDeleteConfirmation_accessor_storage; }
|
|
1316
|
+
set dialogRoleDeleteConfirmation(value) { this.#dialogRoleDeleteConfirmation_accessor_storage = value; }
|
|
1317
|
+
#dialogMember_accessor_storage = (__runInitializers(this, _dialogRoleDeleteConfirmation_extraInitializers), __runInitializers(this, _dialogMember_initializers, null));
|
|
1318
|
+
get dialogMember() { return this.#dialogMember_accessor_storage; }
|
|
1319
|
+
set dialogMember(value) { this.#dialogMember_accessor_storage = value; }
|
|
1320
|
+
#dialogMemberRoles_accessor_storage = (__runInitializers(this, _dialogMember_extraInitializers), __runInitializers(this, _dialogMemberRoles_initializers, []));
|
|
1321
|
+
get dialogMemberRoles() { return this.#dialogMemberRoles_accessor_storage; }
|
|
1322
|
+
set dialogMemberRoles(value) { this.#dialogMemberRoles_accessor_storage = value; }
|
|
1323
|
+
#dialogApp_accessor_storage = (__runInitializers(this, _dialogMemberRoles_extraInitializers), __runInitializers(this, _dialogApp_initializers, null));
|
|
1324
|
+
get dialogApp() { return this.#dialogApp_accessor_storage; }
|
|
1325
|
+
set dialogApp(value) { this.#dialogApp_accessor_storage = value; }
|
|
1326
|
+
#dialogAppMappings_accessor_storage = (__runInitializers(this, _dialogApp_extraInitializers), __runInitializers(this, _dialogAppMappings_initializers, []));
|
|
1327
|
+
get dialogAppMappings() { return this.#dialogAppMappings_accessor_storage; }
|
|
1328
|
+
set dialogAppMappings(value) { this.#dialogAppMappings_accessor_storage = value; }
|
|
1329
|
+
workspaceNav = (__runInitializers(this, _dialogAppMappings_extraInitializers), [
|
|
1330
|
+
{ id: 'overview', label: 'Overview', icon: 'grid' },
|
|
1331
|
+
]);
|
|
1332
|
+
accountNav = [
|
|
1333
|
+
{ id: 'profile', label: 'Profile', icon: 'user' },
|
|
1334
|
+
{ id: 'security', label: 'Security', icon: 'shield' },
|
|
1335
|
+
{ id: 'sessions', label: 'Sessions & Devices', icon: 'monitor' },
|
|
1336
|
+
{ id: 'apps', label: 'Connected Apps', icon: 'grid' },
|
|
1337
|
+
];
|
|
1338
|
+
orgNav = [
|
|
1339
|
+
{ id: 'org-general', label: 'General', icon: 'building' },
|
|
1340
|
+
{ id: 'org-settings', label: 'Settings', icon: 'settings' },
|
|
1341
|
+
{ id: 'org-members', label: 'Members', icon: 'users' },
|
|
1342
|
+
{ id: 'org-apps', label: 'OAuth Apps', icon: 'box' },
|
|
1343
|
+
];
|
|
1344
|
+
supportNav = [
|
|
1345
|
+
{ id: 'support', label: 'Support', icon: 'shield' },
|
|
1346
|
+
];
|
|
1347
|
+
adminNav = [
|
|
1348
|
+
{ id: 'ga-users', label: 'All Users', icon: 'users' },
|
|
1349
|
+
{ id: 'ga-orgs', label: 'All Organisations', icon: 'building' },
|
|
1350
|
+
{ id: 'ga-apps', label: 'Platform Apps', icon: 'globe' },
|
|
1351
|
+
];
|
|
1352
|
+
get safeOrgs() {
|
|
1353
|
+
return Array.isArray(this.orgs) ? this.orgs.filter(Boolean) : [];
|
|
1354
|
+
}
|
|
1355
|
+
get currentOrg() {
|
|
1356
|
+
const orgs = this.safeOrgs;
|
|
1357
|
+
return orgs.find((orgArg) => orgArg.id === this.selectedOrgId) || orgs[0] || {
|
|
1358
|
+
id: '',
|
|
1359
|
+
name: 'No organisation',
|
|
1360
|
+
slug: '',
|
|
1361
|
+
myRole: '',
|
|
1362
|
+
};
|
|
1363
|
+
}
|
|
1364
|
+
get userInitials() {
|
|
1365
|
+
if (this.user?.initials) {
|
|
1366
|
+
return this.user.initials;
|
|
1367
|
+
}
|
|
1368
|
+
const source = this.user?.name || this.user?.email || '?';
|
|
1369
|
+
return source
|
|
1370
|
+
.split(/\s+|@/)
|
|
1371
|
+
.filter(Boolean)
|
|
1372
|
+
.map((partArg) => partArg[0])
|
|
1373
|
+
.slice(0, 2)
|
|
1374
|
+
.join('')
|
|
1375
|
+
.toUpperCase();
|
|
1376
|
+
}
|
|
1377
|
+
getInitials(valueArg) {
|
|
1378
|
+
const source = valueArg || '?';
|
|
1379
|
+
return source
|
|
1380
|
+
.split(/\s+|@|-|\./)
|
|
1381
|
+
.filter(Boolean)
|
|
1382
|
+
.map((partArg) => partArg[0])
|
|
1383
|
+
.slice(0, 2)
|
|
1384
|
+
.join('')
|
|
1385
|
+
.toUpperCase();
|
|
1386
|
+
}
|
|
1387
|
+
setPasswordField(fieldArg, eventArg) {
|
|
1388
|
+
const value = eventArg.target.value;
|
|
1389
|
+
if (fieldArg === 'current')
|
|
1390
|
+
this.currentPassword = value;
|
|
1391
|
+
if (fieldArg === 'new')
|
|
1392
|
+
this.newPassword = value;
|
|
1393
|
+
if (fieldArg === 'confirm')
|
|
1394
|
+
this.confirmPassword = value;
|
|
1395
|
+
this.credentialError = '';
|
|
1396
|
+
}
|
|
1397
|
+
submitPasswordChange() {
|
|
1398
|
+
if (!this.currentPassword || !this.newPassword || !this.confirmPassword) {
|
|
1399
|
+
this.credentialError = 'Enter your current password and confirm the new password.';
|
|
1400
|
+
return;
|
|
1401
|
+
}
|
|
1402
|
+
if (this.newPassword.length < 12) {
|
|
1403
|
+
this.credentialError = 'Use at least 12 characters for the new password.';
|
|
1404
|
+
return;
|
|
1405
|
+
}
|
|
1406
|
+
if (this.newPassword !== this.confirmPassword) {
|
|
1407
|
+
this.credentialError = 'New password and confirmation do not match.';
|
|
1408
|
+
return;
|
|
1409
|
+
}
|
|
1410
|
+
this.dispatchShellEvent('idp-admin-password-change', {
|
|
1411
|
+
currentPassword: this.currentPassword,
|
|
1412
|
+
newPassword: this.newPassword,
|
|
1413
|
+
});
|
|
1414
|
+
}
|
|
1415
|
+
syncOrgSettingsState() {
|
|
1416
|
+
const org = this.currentOrg;
|
|
1417
|
+
if (this.orgSettingsOrgId === org.id) {
|
|
1418
|
+
return;
|
|
1419
|
+
}
|
|
1420
|
+
this.orgSettingsOrgId = org.id;
|
|
1421
|
+
this.orgNameDraft = org.name || '';
|
|
1422
|
+
this.orgSlugDraft = org.slug || '';
|
|
1423
|
+
this.orgSettingsConfirmation = '';
|
|
1424
|
+
this.transferOwnerId = '';
|
|
1425
|
+
this.transferConfirmation = '';
|
|
1426
|
+
this.deleteConfirmation = '';
|
|
1427
|
+
this.orgSettingsError = '';
|
|
1428
|
+
}
|
|
1429
|
+
setOrgSettingsField(fieldArg, eventArg) {
|
|
1430
|
+
const value = eventArg.target.value;
|
|
1431
|
+
if (fieldArg === 'name')
|
|
1432
|
+
this.orgNameDraft = value;
|
|
1433
|
+
if (fieldArg === 'slug')
|
|
1434
|
+
this.orgSlugDraft = value.trim().toLowerCase();
|
|
1435
|
+
if (fieldArg === 'settingsConfirmation')
|
|
1436
|
+
this.orgSettingsConfirmation = value;
|
|
1437
|
+
if (fieldArg === 'transferOwnerId')
|
|
1438
|
+
this.transferOwnerId = value;
|
|
1439
|
+
if (fieldArg === 'transferConfirmation')
|
|
1440
|
+
this.transferConfirmation = value;
|
|
1441
|
+
if (fieldArg === 'deleteConfirmation')
|
|
1442
|
+
this.deleteConfirmation = value;
|
|
1443
|
+
this.orgSettingsError = '';
|
|
1444
|
+
}
|
|
1445
|
+
submitOrgSettingsUpdate() {
|
|
1446
|
+
const org = this.currentOrg;
|
|
1447
|
+
const name = this.orgNameDraft.trim();
|
|
1448
|
+
const slug = this.orgSlugDraft.trim().toLowerCase();
|
|
1449
|
+
if (!org.id) {
|
|
1450
|
+
this.orgSettingsError = 'Select an organisation before updating settings.';
|
|
1451
|
+
return;
|
|
1452
|
+
}
|
|
1453
|
+
if (!name || !slug) {
|
|
1454
|
+
this.orgSettingsError = 'Organisation name and slug are required.';
|
|
1455
|
+
return;
|
|
1456
|
+
}
|
|
1457
|
+
if (name === org.name && slug === org.slug) {
|
|
1458
|
+
this.orgSettingsError = 'Change the organisation name or slug before applying settings.';
|
|
1459
|
+
return;
|
|
1460
|
+
}
|
|
1461
|
+
if (this.orgSettingsConfirmation.trim() !== org.slug) {
|
|
1462
|
+
this.orgSettingsError = `Type ${org.slug} to confirm organisation settings changes.`;
|
|
1463
|
+
return;
|
|
1464
|
+
}
|
|
1465
|
+
this.dispatchShellEvent('idp-admin-org-update', {
|
|
1466
|
+
organizationId: org.id,
|
|
1467
|
+
name,
|
|
1468
|
+
slug,
|
|
1469
|
+
confirmationText: this.orgSettingsConfirmation.trim(),
|
|
1470
|
+
});
|
|
1471
|
+
}
|
|
1472
|
+
submitOrgTransfer() {
|
|
1473
|
+
const org = this.currentOrg;
|
|
1474
|
+
const expectedText = `transfer ${org.slug}`;
|
|
1475
|
+
if (!org.id) {
|
|
1476
|
+
this.orgSettingsError = 'Select an organisation before transferring ownership.';
|
|
1477
|
+
return;
|
|
1478
|
+
}
|
|
1479
|
+
if (!this.transferOwnerId) {
|
|
1480
|
+
this.orgSettingsError = 'Select the member who should become the new owner.';
|
|
1481
|
+
return;
|
|
1482
|
+
}
|
|
1483
|
+
if (this.transferConfirmation.trim() !== expectedText) {
|
|
1484
|
+
this.orgSettingsError = `Type ${expectedText} to confirm ownership transfer.`;
|
|
1485
|
+
return;
|
|
1486
|
+
}
|
|
1487
|
+
this.dispatchShellEvent('idp-admin-org-transfer', {
|
|
1488
|
+
organizationId: org.id,
|
|
1489
|
+
newOwnerId: this.transferOwnerId,
|
|
1490
|
+
confirmationText: this.transferConfirmation.trim(),
|
|
1491
|
+
});
|
|
1492
|
+
}
|
|
1493
|
+
submitOrgDelete() {
|
|
1494
|
+
const org = this.currentOrg;
|
|
1495
|
+
const expectedText = `delete ${org.slug}`;
|
|
1496
|
+
if (!org.id) {
|
|
1497
|
+
this.orgSettingsError = 'Select an organisation before deleting it.';
|
|
1498
|
+
return;
|
|
1499
|
+
}
|
|
1500
|
+
if (this.deleteConfirmation.trim() !== expectedText) {
|
|
1501
|
+
this.orgSettingsError = `Type ${expectedText} to confirm organisation deletion.`;
|
|
1502
|
+
return;
|
|
1503
|
+
}
|
|
1504
|
+
this.dispatchShellEvent('idp-admin-org-delete', {
|
|
1505
|
+
organizationId: org.id,
|
|
1506
|
+
confirmationText: this.deleteConfirmation.trim(),
|
|
1507
|
+
});
|
|
1508
|
+
}
|
|
1509
|
+
requestPassportEnrollment() {
|
|
1510
|
+
const fallbackLabel = typeof navigator !== 'undefined'
|
|
1511
|
+
? navigator.userAgent.includes('Mobile') ? 'Mobile passport device' : 'Desktop passport device'
|
|
1512
|
+
: 'Passport device';
|
|
1513
|
+
const deviceLabel = globalThis.prompt?.('Device label', fallbackLabel)?.trim();
|
|
1514
|
+
if (!deviceLabel) {
|
|
1515
|
+
return;
|
|
1516
|
+
}
|
|
1517
|
+
this.dispatchShellEvent('idp-admin-passport-enroll', {
|
|
1518
|
+
deviceLabel,
|
|
1519
|
+
});
|
|
1520
|
+
}
|
|
1521
|
+
setPage(pageArg) {
|
|
1522
|
+
this.page = pageArg;
|
|
1523
|
+
this.orgMenuOpen = false;
|
|
1524
|
+
this.dispatchEvent(new CustomEvent('idp-admin-navigate', {
|
|
1525
|
+
detail: { page: pageArg },
|
|
1526
|
+
bubbles: true,
|
|
1527
|
+
composed: true,
|
|
1528
|
+
}));
|
|
1529
|
+
}
|
|
1530
|
+
selectOrg(orgIdArg) {
|
|
1531
|
+
this.selectedOrgId = orgIdArg;
|
|
1532
|
+
this.orgMenuOpen = false;
|
|
1533
|
+
this.page = 'org-general';
|
|
1534
|
+
this.dispatchEvent(new CustomEvent('idp-admin-org-select', {
|
|
1535
|
+
detail: {
|
|
1536
|
+
orgId: orgIdArg,
|
|
1537
|
+
org: this.orgs.find((orgArg) => orgArg.id === orgIdArg) || null,
|
|
1538
|
+
},
|
|
1539
|
+
bubbles: true,
|
|
1540
|
+
composed: true,
|
|
1541
|
+
}));
|
|
1542
|
+
}
|
|
1543
|
+
requestOrgCreate() {
|
|
1544
|
+
this.orgMenuOpen = false;
|
|
1545
|
+
this.dispatchEvent(new CustomEvent('idp-admin-org-create', {
|
|
1546
|
+
bubbles: true,
|
|
1547
|
+
composed: true,
|
|
1548
|
+
}));
|
|
1549
|
+
}
|
|
1550
|
+
dispatchShellEvent(eventNameArg, detailArg) {
|
|
1551
|
+
this.dispatchEvent(new CustomEvent(eventNameArg, {
|
|
1552
|
+
detail: detailArg,
|
|
1553
|
+
bubbles: true,
|
|
1554
|
+
composed: true,
|
|
1555
|
+
}));
|
|
1556
|
+
}
|
|
1557
|
+
formatTimeAgo(timestampArg) {
|
|
1558
|
+
if (!timestampArg) {
|
|
1559
|
+
return 'unknown';
|
|
1560
|
+
}
|
|
1561
|
+
const diff = Date.now() - timestampArg;
|
|
1562
|
+
const minutes = Math.floor(diff / 60000);
|
|
1563
|
+
const hours = Math.floor(diff / 3600000);
|
|
1564
|
+
const days = Math.floor(diff / 86400000);
|
|
1565
|
+
if (minutes < 1)
|
|
1566
|
+
return 'just now';
|
|
1567
|
+
if (minutes < 60)
|
|
1568
|
+
return `${minutes}m ago`;
|
|
1569
|
+
if (hours < 24)
|
|
1570
|
+
return `${hours}h ago`;
|
|
1571
|
+
if (days < 7)
|
|
1572
|
+
return `${days}d ago`;
|
|
1573
|
+
return new Date(timestampArg).toLocaleDateString();
|
|
1574
|
+
}
|
|
1575
|
+
renderStateCard(titleArg, descriptionArg, iconArg = 'box') {
|
|
1576
|
+
return html `
|
|
1577
|
+
<div class="state-card">
|
|
1578
|
+
<span class="state-icon"><idp-icon name=${iconArg} size="17"></idp-icon></span>
|
|
1579
|
+
<div class="state-title">${titleArg}</div>
|
|
1580
|
+
<div class="state-description">${descriptionArg}</div>
|
|
1581
|
+
</div>
|
|
1582
|
+
`;
|
|
1583
|
+
}
|
|
1584
|
+
renderDataState(emptyTitleArg, emptyDescriptionArg, iconArg = 'box') {
|
|
1585
|
+
if (this.dataLoading) {
|
|
1586
|
+
return this.renderStateCard('Loading data', 'Fetching the latest account and organisation data.', 'cloud');
|
|
1587
|
+
}
|
|
1588
|
+
if (this.dataError) {
|
|
1589
|
+
return this.renderStateCard('Data unavailable', this.dataError, 'alert');
|
|
1590
|
+
}
|
|
1591
|
+
return this.renderStateCard(emptyTitleArg, emptyDescriptionArg, iconArg);
|
|
1592
|
+
}
|
|
1593
|
+
roleVariant(roleArg) {
|
|
1594
|
+
if (roleArg === 'owner')
|
|
1595
|
+
return 'accent';
|
|
1596
|
+
if (roleArg === 'admin')
|
|
1597
|
+
return 'warn';
|
|
1598
|
+
if (roleArg === 'editor')
|
|
1599
|
+
return 'ok';
|
|
1600
|
+
if (roleArg === 'outlaw')
|
|
1601
|
+
return 'error';
|
|
1602
|
+
return 'outline';
|
|
1603
|
+
}
|
|
1604
|
+
get platformRoles() {
|
|
1605
|
+
return [
|
|
1606
|
+
{ key: 'owner', name: 'Owner', description: 'Protected idp.global owner role.' },
|
|
1607
|
+
{ key: 'admin', name: 'Admin', description: 'Protected idp.global admin role.' },
|
|
1608
|
+
{ key: 'editor', name: 'Editor', description: 'Standard organisation role.' },
|
|
1609
|
+
{ key: 'viewer', name: 'Viewer', description: 'Standard organisation role.' },
|
|
1610
|
+
{ key: 'guest', name: 'Guest', description: 'Standard organisation role.' },
|
|
1611
|
+
{ key: 'outlaw', name: 'Outlaw', description: 'Restricted organisation role.' },
|
|
1612
|
+
];
|
|
1613
|
+
}
|
|
1614
|
+
get availableOrgRoles() {
|
|
1615
|
+
const customRoles = this.orgRoleDefinitions || [];
|
|
1616
|
+
const customRoleKeys = new Set(customRoles.map((roleArg) => roleArg.key));
|
|
1617
|
+
return [
|
|
1618
|
+
...this.platformRoles.filter((roleArg) => !customRoleKeys.has(roleArg.key)),
|
|
1619
|
+
...customRoles,
|
|
1620
|
+
];
|
|
1621
|
+
}
|
|
1622
|
+
parseCsv(valueArg) {
|
|
1623
|
+
return [...new Set(valueArg.split(',').map((entryArg) => entryArg.trim()).filter(Boolean))];
|
|
1624
|
+
}
|
|
1625
|
+
normalizeRoleKey(valueArg) {
|
|
1626
|
+
return valueArg.trim().toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/^-+|-+$/g, '');
|
|
1627
|
+
}
|
|
1628
|
+
closeDialog() {
|
|
1629
|
+
this.dialogMode = 'none';
|
|
1630
|
+
this.dialogError = '';
|
|
1631
|
+
this.dialogRoleKey = '';
|
|
1632
|
+
this.dialogRoleName = '';
|
|
1633
|
+
this.dialogRoleDescription = '';
|
|
1634
|
+
this.dialogRoleDeleteConfirmation = '';
|
|
1635
|
+
this.dialogMember = null;
|
|
1636
|
+
this.dialogMemberRoles = [];
|
|
1637
|
+
this.dialogApp = null;
|
|
1638
|
+
this.dialogAppMappings = [];
|
|
1639
|
+
}
|
|
1640
|
+
openRoleUpsertDialog(roleArg) {
|
|
1641
|
+
this.dialogMode = 'role-upsert';
|
|
1642
|
+
this.dialogError = '';
|
|
1643
|
+
this.dialogRoleKey = roleArg?.key || '';
|
|
1644
|
+
this.dialogRoleName = roleArg?.name || '';
|
|
1645
|
+
this.dialogRoleDescription = roleArg?.description || '';
|
|
1646
|
+
}
|
|
1647
|
+
openRoleDeleteDialog(roleArg) {
|
|
1648
|
+
this.dialogMode = 'role-delete';
|
|
1649
|
+
this.dialogError = '';
|
|
1650
|
+
this.dialogRoleKey = roleArg.key;
|
|
1651
|
+
this.dialogRoleName = roleArg.name;
|
|
1652
|
+
this.dialogRoleDescription = roleArg.description || '';
|
|
1653
|
+
this.dialogRoleDeleteConfirmation = '';
|
|
1654
|
+
}
|
|
1655
|
+
openMemberRolesDialog(memberArg) {
|
|
1656
|
+
this.dialogMode = 'member-roles';
|
|
1657
|
+
this.dialogError = '';
|
|
1658
|
+
this.dialogMember = memberArg;
|
|
1659
|
+
this.dialogMemberRoles = [...memberArg.roles];
|
|
1660
|
+
}
|
|
1661
|
+
openAppRoleMappingsDialog(appArg) {
|
|
1662
|
+
this.dialogMode = 'app-role-mappings';
|
|
1663
|
+
this.dialogError = '';
|
|
1664
|
+
this.dialogApp = appArg;
|
|
1665
|
+
this.dialogAppMappings = this.availableOrgRoles.map((roleArg) => {
|
|
1666
|
+
const existingMapping = (appArg.roleMappings || []).find((mappingArg) => mappingArg.orgRoleKey === roleArg.key);
|
|
1667
|
+
return {
|
|
1668
|
+
orgRoleKey: roleArg.key,
|
|
1669
|
+
appRoles: [...(existingMapping?.appRoles || [])],
|
|
1670
|
+
permissions: [...(existingMapping?.permissions || [])],
|
|
1671
|
+
scopes: [...(existingMapping?.scopes || [])],
|
|
1672
|
+
};
|
|
1673
|
+
});
|
|
1674
|
+
}
|
|
1675
|
+
setDialogRoleField(fieldArg, eventArg) {
|
|
1676
|
+
const value = eventArg.target.value;
|
|
1677
|
+
if (fieldArg === 'key')
|
|
1678
|
+
this.dialogRoleKey = this.normalizeRoleKey(value);
|
|
1679
|
+
if (fieldArg === 'name') {
|
|
1680
|
+
this.dialogRoleName = value;
|
|
1681
|
+
if (!this.dialogRoleKey) {
|
|
1682
|
+
this.dialogRoleKey = this.normalizeRoleKey(value);
|
|
1683
|
+
}
|
|
1684
|
+
}
|
|
1685
|
+
if (fieldArg === 'description')
|
|
1686
|
+
this.dialogRoleDescription = value;
|
|
1687
|
+
if (fieldArg === 'deleteConfirmation')
|
|
1688
|
+
this.dialogRoleDeleteConfirmation = value;
|
|
1689
|
+
this.dialogError = '';
|
|
1690
|
+
}
|
|
1691
|
+
toggleDialogMemberRole(roleKeyArg, checkedArg) {
|
|
1692
|
+
const nextRoles = new Set(this.dialogMemberRoles);
|
|
1693
|
+
if (checkedArg) {
|
|
1694
|
+
nextRoles.add(roleKeyArg);
|
|
1695
|
+
}
|
|
1696
|
+
else {
|
|
1697
|
+
nextRoles.delete(roleKeyArg);
|
|
1698
|
+
}
|
|
1699
|
+
this.dialogMemberRoles = [...nextRoles];
|
|
1700
|
+
this.dialogError = '';
|
|
1701
|
+
}
|
|
1702
|
+
setDialogMappingField(roleKeyArg, fieldArg, eventArg) {
|
|
1703
|
+
const value = eventArg.target.value;
|
|
1704
|
+
this.dialogAppMappings = this.dialogAppMappings.map((mappingArg) => mappingArg.orgRoleKey === roleKeyArg
|
|
1705
|
+
? { ...mappingArg, [fieldArg]: this.parseCsv(value) }
|
|
1706
|
+
: mappingArg);
|
|
1707
|
+
this.dialogError = '';
|
|
1708
|
+
}
|
|
1709
|
+
submitRoleUpsertDialog() {
|
|
1710
|
+
const key = this.normalizeRoleKey(this.dialogRoleKey);
|
|
1711
|
+
const name = this.dialogRoleName.trim();
|
|
1712
|
+
if (!key || !name) {
|
|
1713
|
+
this.dialogError = 'Role key and name are required.';
|
|
1714
|
+
return;
|
|
1715
|
+
}
|
|
1716
|
+
this.dispatchShellEvent('idp-admin-org-role-upsert', {
|
|
1717
|
+
organizationId: this.currentOrg.id,
|
|
1718
|
+
roleDefinition: {
|
|
1719
|
+
key,
|
|
1720
|
+
name,
|
|
1721
|
+
description: this.dialogRoleDescription.trim(),
|
|
1722
|
+
},
|
|
1723
|
+
});
|
|
1724
|
+
this.closeDialog();
|
|
1725
|
+
}
|
|
1726
|
+
submitRoleDeleteDialog() {
|
|
1727
|
+
const expectedText = `delete role ${this.dialogRoleKey}`;
|
|
1728
|
+
if (this.dialogRoleDeleteConfirmation.trim() !== expectedText) {
|
|
1729
|
+
this.dialogError = `Type ${expectedText} to confirm role deletion.`;
|
|
1730
|
+
return;
|
|
1731
|
+
}
|
|
1732
|
+
this.dispatchShellEvent('idp-admin-org-role-delete', {
|
|
1733
|
+
organizationId: this.currentOrg.id,
|
|
1734
|
+
roleKey: this.dialogRoleKey,
|
|
1735
|
+
confirmationText: this.dialogRoleDeleteConfirmation.trim(),
|
|
1736
|
+
});
|
|
1737
|
+
this.closeDialog();
|
|
1738
|
+
}
|
|
1739
|
+
submitMemberRolesDialog() {
|
|
1740
|
+
if (!this.dialogMember)
|
|
1741
|
+
return;
|
|
1742
|
+
if (!this.dialogMemberRoles.length) {
|
|
1743
|
+
this.dialogError = 'At least one role is required.';
|
|
1744
|
+
return;
|
|
1745
|
+
}
|
|
1746
|
+
this.dispatchShellEvent('idp-admin-member-roles-update', {
|
|
1747
|
+
userId: this.dialogMember.userId,
|
|
1748
|
+
roles: this.dialogMemberRoles,
|
|
1749
|
+
});
|
|
1750
|
+
this.closeDialog();
|
|
1751
|
+
}
|
|
1752
|
+
submitAppRoleMappingsDialog() {
|
|
1753
|
+
if (!this.dialogApp)
|
|
1754
|
+
return;
|
|
1755
|
+
const roleMappings = this.dialogAppMappings
|
|
1756
|
+
.map((mappingArg) => ({
|
|
1757
|
+
orgRoleKey: mappingArg.orgRoleKey,
|
|
1758
|
+
appRoles: [...mappingArg.appRoles],
|
|
1759
|
+
permissions: [...mappingArg.permissions],
|
|
1760
|
+
scopes: [...mappingArg.scopes],
|
|
1761
|
+
}))
|
|
1762
|
+
.filter((mappingArg) => mappingArg.appRoles.length || mappingArg.permissions.length || mappingArg.scopes.length);
|
|
1763
|
+
const allowedScopes = this.dialogApp.scopes || [];
|
|
1764
|
+
const invalidScopes = roleMappings.flatMap((mappingArg) => mappingArg.scopes).filter((scopeArg) => !allowedScopes.includes(scopeArg));
|
|
1765
|
+
if (invalidScopes.length) {
|
|
1766
|
+
this.dialogError = `Unsupported app scopes: ${[...new Set(invalidScopes)].join(', ')}.`;
|
|
1767
|
+
return;
|
|
1768
|
+
}
|
|
1769
|
+
this.dispatchShellEvent('idp-admin-app-role-mappings-update', {
|
|
1770
|
+
organizationId: this.currentOrg.id,
|
|
1771
|
+
appId: this.dialogApp.id,
|
|
1772
|
+
roleMappings,
|
|
1773
|
+
});
|
|
1774
|
+
this.closeDialog();
|
|
1775
|
+
}
|
|
1776
|
+
renderDialogError() {
|
|
1777
|
+
return this.dialogError
|
|
1778
|
+
? html `<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">Action blocked</div><div class="muted">${this.dialogError}</div></div></div>`
|
|
1779
|
+
: html ``;
|
|
1780
|
+
}
|
|
1781
|
+
renderRoleUpsertDialog() {
|
|
1782
|
+
const isEdit = this.orgRoleDefinitions.some((roleArg) => roleArg.key === this.dialogRoleKey);
|
|
1783
|
+
return html `
|
|
1784
|
+
<div class="dialog-card" @click=${(eventArg) => eventArg.stopPropagation()}>
|
|
1785
|
+
<div class="dialog-head">
|
|
1786
|
+
<div><div class="dialog-title">${isEdit ? 'Edit custom role' : 'Add custom role'}</div><div class="muted">Custom roles model organisation-specific business access.</div></div>
|
|
1787
|
+
<button class="plain-button ghost" @click=${() => this.closeDialog()}>Close</button>
|
|
1788
|
+
</div>
|
|
1789
|
+
<div class="dialog-body">
|
|
1790
|
+
${this.renderDialogError()}
|
|
1791
|
+
${this.renderFormRow('Role name', 'Readable label shown to admins.', html `<input class="input" .value=${this.dialogRoleName} @input=${(eventArg) => this.setDialogRoleField('name', eventArg)} />`, true)}
|
|
1792
|
+
${this.renderFormRow('Role key', 'Lowercase stable identifier used in assignments and app mappings.', html `<input class="input" .value=${this.dialogRoleKey} @input=${(eventArg) => this.setDialogRoleField('key', eventArg)} ?disabled=${isEdit} />`, true)}
|
|
1793
|
+
${this.renderFormRow('Description', 'Optional admin note describing when this role should be used.', html `<textarea class="textarea" .value=${this.dialogRoleDescription} @input=${(eventArg) => this.setDialogRoleField('description', eventArg)}></textarea>`)}
|
|
1794
|
+
</div>
|
|
1795
|
+
<div class="dialog-actions">
|
|
1796
|
+
<button class="plain-button outline" @click=${() => this.closeDialog()}>Cancel</button>
|
|
1797
|
+
<button class="plain-button primary" @click=${() => this.submitRoleUpsertDialog()}>Save role</button>
|
|
1798
|
+
</div>
|
|
1799
|
+
</div>
|
|
1800
|
+
`;
|
|
1801
|
+
}
|
|
1802
|
+
renderRoleDeleteDialog() {
|
|
1803
|
+
const expectedText = `delete role ${this.dialogRoleKey}`;
|
|
1804
|
+
return html `
|
|
1805
|
+
<div class="dialog-card" @click=${(eventArg) => eventArg.stopPropagation()}>
|
|
1806
|
+
<div class="dialog-head">
|
|
1807
|
+
<div><div class="dialog-title">Delete custom role</div><div class="muted">This removes the role from member assignments and app mappings after backend confirmation.</div></div>
|
|
1808
|
+
<button class="plain-button ghost" @click=${() => this.closeDialog()}>Close</button>
|
|
1809
|
+
</div>
|
|
1810
|
+
<div class="dialog-body">
|
|
1811
|
+
${this.renderDialogError()}
|
|
1812
|
+
<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">${this.dialogRoleName}</div><div class="muted">Type <span class="mono">${expectedText}</span> to confirm deletion.</div></div></div>
|
|
1813
|
+
${this.renderFormRow('Confirmation', `Type ${expectedText}`, html `<input class="input" .value=${this.dialogRoleDeleteConfirmation} @input=${(eventArg) => this.setDialogRoleField('deleteConfirmation', eventArg)} />`, true)}
|
|
1814
|
+
</div>
|
|
1815
|
+
<div class="dialog-actions">
|
|
1816
|
+
<button class="plain-button outline" @click=${() => this.closeDialog()}>Cancel</button>
|
|
1817
|
+
<button class="plain-button destructive" @click=${() => this.submitRoleDeleteDialog()}>Delete role</button>
|
|
1818
|
+
</div>
|
|
1819
|
+
</div>
|
|
1820
|
+
`;
|
|
1821
|
+
}
|
|
1822
|
+
renderMemberRolesDialog() {
|
|
1823
|
+
const member = this.dialogMember;
|
|
1824
|
+
return html `
|
|
1825
|
+
<div class="dialog-card" @click=${(eventArg) => eventArg.stopPropagation()}>
|
|
1826
|
+
<div class="dialog-head">
|
|
1827
|
+
<div><div class="dialog-title">Edit member roles</div><div class="muted">${member?.name || member?.email || 'Member'} receives the selected organisation roles.</div></div>
|
|
1828
|
+
<button class="plain-button ghost" @click=${() => this.closeDialog()}>Close</button>
|
|
1829
|
+
</div>
|
|
1830
|
+
<div class="dialog-body">
|
|
1831
|
+
${this.renderDialogError()}
|
|
1832
|
+
<div class="role-grid">
|
|
1833
|
+
${this.availableOrgRoles.map((roleArg) => {
|
|
1834
|
+
const checked = this.dialogMemberRoles.includes(roleArg.key);
|
|
1835
|
+
return html `
|
|
1836
|
+
<label class="role-option">
|
|
1837
|
+
<input type="checkbox" .checked=${checked} @change=${(eventArg) => this.toggleDialogMemberRole(roleArg.key, eventArg.target.checked)} />
|
|
1838
|
+
<span><span class="section-title">${roleArg.name}</span><span class="muted" style="display:block">${roleArg.description || roleArg.key}</span></span>
|
|
1839
|
+
</label>
|
|
1840
|
+
`;
|
|
1841
|
+
})}
|
|
1842
|
+
</div>
|
|
1843
|
+
</div>
|
|
1844
|
+
<div class="dialog-actions">
|
|
1845
|
+
<button class="plain-button outline" @click=${() => this.closeDialog()}>Cancel</button>
|
|
1846
|
+
<button class="plain-button primary" @click=${() => this.submitMemberRolesDialog()}>Save roles</button>
|
|
1847
|
+
</div>
|
|
1848
|
+
</div>
|
|
1849
|
+
`;
|
|
1850
|
+
}
|
|
1851
|
+
renderAppRoleMappingsDialog() {
|
|
1852
|
+
const app = this.dialogApp;
|
|
1853
|
+
return html `
|
|
1854
|
+
<div class="dialog-card wide" @click=${(eventArg) => eventArg.stopPropagation()}>
|
|
1855
|
+
<div class="dialog-head">
|
|
1856
|
+
<div><div class="dialog-title">Map organisation roles</div><div class="muted">Map ${this.currentOrg.name} roles to app-specific roles, permissions, and OAuth scopes for ${app?.name || 'this app'}.</div></div>
|
|
1857
|
+
<button class="plain-button ghost" @click=${() => this.closeDialog()}>Close</button>
|
|
1858
|
+
</div>
|
|
1859
|
+
<div class="dialog-body">
|
|
1860
|
+
${this.renderDialogError()}
|
|
1861
|
+
${app?.scopes?.length ? html `<div class="muted">Available OAuth scopes: <span class="mono">${app.scopes.join(', ')}</span></div>` : html `<div class="muted">This app has no declared OAuth scopes. Role and permission mappings are still supported.</div>`}
|
|
1862
|
+
${this.dialogAppMappings.map((mappingArg) => {
|
|
1863
|
+
const role = this.availableOrgRoles.find((roleArg) => roleArg.key === mappingArg.orgRoleKey);
|
|
1864
|
+
return html `
|
|
1865
|
+
<div class="mapping-row">
|
|
1866
|
+
<div class="mapping-role">${role?.name || mappingArg.orgRoleKey}<span class="muted">${mappingArg.orgRoleKey}</span></div>
|
|
1867
|
+
<div>${this.renderFormRow('App roles', '', html `<input class="input" .value=${mappingArg.appRoles.join(', ')} @input=${(eventArg) => this.setDialogMappingField(mappingArg.orgRoleKey, 'appRoles', eventArg)} />`)}</div>
|
|
1868
|
+
<div>${this.renderFormRow('Permissions', '', html `<input class="input" .value=${mappingArg.permissions.join(', ')} @input=${(eventArg) => this.setDialogMappingField(mappingArg.orgRoleKey, 'permissions', eventArg)} />`)}</div>
|
|
1869
|
+
<div>${this.renderFormRow('Scopes', '', html `<input class="input" .value=${mappingArg.scopes.join(', ')} @input=${(eventArg) => this.setDialogMappingField(mappingArg.orgRoleKey, 'scopes', eventArg)} />`)}</div>
|
|
1870
|
+
</div>
|
|
1871
|
+
`;
|
|
1872
|
+
})}
|
|
1873
|
+
</div>
|
|
1874
|
+
<div class="dialog-actions">
|
|
1875
|
+
<button class="plain-button outline" @click=${() => this.closeDialog()}>Cancel</button>
|
|
1876
|
+
<button class="plain-button primary" @click=${() => this.submitAppRoleMappingsDialog()}>Save mappings</button>
|
|
1877
|
+
</div>
|
|
1878
|
+
</div>
|
|
1879
|
+
`;
|
|
1880
|
+
}
|
|
1881
|
+
renderDialog() {
|
|
1882
|
+
if (this.dialogMode === 'none') {
|
|
1883
|
+
return html ``;
|
|
1884
|
+
}
|
|
1885
|
+
const dialog = this.dialogMode === 'role-upsert'
|
|
1886
|
+
? this.renderRoleUpsertDialog()
|
|
1887
|
+
: this.dialogMode === 'role-delete'
|
|
1888
|
+
? this.renderRoleDeleteDialog()
|
|
1889
|
+
: this.dialogMode === 'member-roles'
|
|
1890
|
+
? this.renderMemberRolesDialog()
|
|
1891
|
+
: this.renderAppRoleMappingsDialog();
|
|
1892
|
+
return html `<div class="dialog-backdrop" @click=${() => this.closeDialog()}>${dialog}</div>`;
|
|
1893
|
+
}
|
|
1894
|
+
renderNavGroup(items, active = '') {
|
|
1895
|
+
return html `
|
|
1896
|
+
<div class="nav-list">
|
|
1897
|
+
${items.map((item) => html `
|
|
1898
|
+
<button class="nav-item ${item.id === active ? 'active' : ''}" @click=${() => this.setPage(item.id)}>
|
|
1899
|
+
<idp-icon name=${item.icon} size="14"></idp-icon>
|
|
1900
|
+
${item.label}
|
|
1901
|
+
${item.badge ? html `<idp-badge variant="accent" style="margin-left:auto">${item.badge}</idp-badge>` : html ``}
|
|
1902
|
+
</button>
|
|
1903
|
+
`)}
|
|
1904
|
+
</div>
|
|
1905
|
+
`;
|
|
1906
|
+
}
|
|
1907
|
+
renderSidebar() {
|
|
1908
|
+
const currentOrg = this.currentOrg;
|
|
1909
|
+
return html `
|
|
1910
|
+
<aside class="sidebar">
|
|
1911
|
+
<div class="logo-block">
|
|
1912
|
+
<div class="logo">
|
|
1913
|
+
<div class="logo-icon" aria-hidden="true">
|
|
1914
|
+
<svg width="13" height="13" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
|
|
1915
|
+
<path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"></path>
|
|
1916
|
+
</svg>
|
|
1917
|
+
</div>
|
|
1918
|
+
<span class="logo-text">idp.global</span>
|
|
1919
|
+
</div>
|
|
1920
|
+
</div>
|
|
1921
|
+
<div class="nav-wrap">
|
|
1922
|
+
<div class="nav-section"><div class="nav-title">Workspace</div>${this.renderNavGroup(this.workspaceNav, this.page)}</div>
|
|
1923
|
+
<div class="nav-section"><div class="nav-title">My Account</div>${this.renderNavGroup(this.accountNav, this.page)}</div>
|
|
1924
|
+
<div class="nav-section">
|
|
1925
|
+
<div class="nav-title">Organisation</div>
|
|
1926
|
+
<div class="org-switch-wrap">
|
|
1927
|
+
<button class="org-switch ${this.orgMenuOpen ? 'open' : ''}" @click=${() => { this.orgMenuOpen = !this.orgMenuOpen; }}>
|
|
1928
|
+
<span class="org-avatar">${currentOrg.name.slice(0, 2).toUpperCase()}</span>
|
|
1929
|
+
<span class="org-name">${currentOrg.name}</span>
|
|
1930
|
+
<idp-icon name="chevron-down" size="10"></idp-icon>
|
|
1931
|
+
</button>
|
|
1932
|
+
${this.orgMenuOpen ? html `
|
|
1933
|
+
<div class="org-menu">
|
|
1934
|
+
<div class="org-menu-title">Switch organisation</div>
|
|
1935
|
+
${this.safeOrgs.map((orgArg) => html `
|
|
1936
|
+
<button class="org-menu-item ${orgArg.id === this.selectedOrgId ? 'selected' : ''}" @click=${() => this.selectOrg(orgArg.id)}>
|
|
1937
|
+
<span class="org-avatar">${orgArg.name.slice(0, 2).toUpperCase()}</span>
|
|
1938
|
+
<span style="flex:1;min-width:0"><span class="org-menu-name">${orgArg.name}</span><span class="org-menu-role">${orgArg.myRole || 'member'}</span></span>
|
|
1939
|
+
${orgArg.id === this.selectedOrgId ? html `<idp-icon name="check" size="11"></idp-icon>` : html ``}
|
|
1940
|
+
</button>
|
|
1941
|
+
`)}
|
|
1942
|
+
<div class="org-menu-divider"></div>
|
|
1943
|
+
<button class="org-create" @click=${() => this.requestOrgCreate()}><span class="org-create-icon"><idp-icon name="plus" size="9"></idp-icon></span>Create organisation</button>
|
|
1944
|
+
</div>
|
|
1945
|
+
` : html ``}
|
|
1946
|
+
</div>
|
|
1947
|
+
${this.renderNavGroup(this.orgNav, this.page)}
|
|
1948
|
+
</div>
|
|
1949
|
+
<div class="nav-section"><div class="nav-title">Support</div>${this.renderNavGroup(this.supportNav, this.page)}</div>
|
|
1950
|
+
${this.globalAdmin ? html `<div class="nav-section"><div class="nav-title">Global Admin</div>${this.renderNavGroup(this.adminNav, this.page)}</div>` : html ``}
|
|
1951
|
+
</div>
|
|
1952
|
+
<div class="user-footer">
|
|
1953
|
+
<span class="user-avatar">${this.userInitials}</span>
|
|
1954
|
+
<div class="user-meta"><div class="user-name">${this.user?.name || 'Unknown User'}</div><div class="user-email">${this.user?.email || 'No email'}</div></div>
|
|
1955
|
+
</div>
|
|
1956
|
+
</aside>
|
|
1957
|
+
`;
|
|
1958
|
+
}
|
|
1959
|
+
renderSparkline(data, color) {
|
|
1960
|
+
const max = Math.max(...data);
|
|
1961
|
+
const min = Math.min(...data);
|
|
1962
|
+
const range = max - min || 1;
|
|
1963
|
+
const width = 100;
|
|
1964
|
+
const height = 22;
|
|
1965
|
+
const points = data.map((valueArg, indexArg) => {
|
|
1966
|
+
const x = (indexArg / (data.length - 1)) * width;
|
|
1967
|
+
const y = height - ((valueArg - min) / range) * (height - 4) - 2;
|
|
1968
|
+
return `${x},${y}`;
|
|
1969
|
+
}).join(' ');
|
|
1970
|
+
const area = `0,${height} ${points} ${width},${height}`;
|
|
1971
|
+
return html `
|
|
1972
|
+
<svg viewBox="0 0 ${width} ${height}" preserveAspectRatio="none">
|
|
1973
|
+
<polygon points=${area} fill=${color} opacity="0.12"></polygon>
|
|
1974
|
+
<polyline points=${points} fill="none" stroke=${color} stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"></polyline>
|
|
1975
|
+
</svg>
|
|
1976
|
+
`;
|
|
1977
|
+
}
|
|
1978
|
+
renderKpi(kpi) {
|
|
1979
|
+
return html `
|
|
1980
|
+
<div class="kpi" style="--kpi-accent:${kpi.accent}">
|
|
1981
|
+
<div class="kpi-label">${kpi.label}</div>
|
|
1982
|
+
<div class="kpi-value">${kpi.value}${kpi.unit ? html `<span>${kpi.unit}</span>` : html ``}</div>
|
|
1983
|
+
<div class="kpi-sub">${kpi.sub}</div>
|
|
1984
|
+
<div class="kpi-foot">
|
|
1985
|
+
<span class="delta">${kpi.deltaKind === 'live' ? html `<span class="live-dot"></span>` : html ``}${kpi.delta}</span>
|
|
1986
|
+
<div class="sparkline">${this.renderSparkline(kpi.spark, kpi.sparkColor)}</div>
|
|
1987
|
+
</div>
|
|
1988
|
+
</div>
|
|
1989
|
+
`;
|
|
1990
|
+
}
|
|
1991
|
+
renderPageHeader(titleArg, descriptionArg, actionArg) {
|
|
1992
|
+
return html `
|
|
1993
|
+
<header class="page-head">
|
|
1994
|
+
<div><h1>${titleArg}</h1><div class="lead">${descriptionArg}</div></div>
|
|
1995
|
+
${actionArg ? html `<div class="page-actions">${actionArg}</div>` : html ``}
|
|
1996
|
+
</header>
|
|
1997
|
+
`;
|
|
1998
|
+
}
|
|
1999
|
+
renderSectionCard(titleArg, descriptionArg, contentArg, actionArg) {
|
|
2000
|
+
return html `
|
|
2001
|
+
<section class="section-card">
|
|
2002
|
+
${titleArg || actionArg ? html `
|
|
2003
|
+
<div class="section-headline">
|
|
2004
|
+
<div><div class="section-title">${titleArg}</div>${descriptionArg ? html `<div class="section-description">${descriptionArg}</div>` : html ``}</div>
|
|
2005
|
+
${actionArg}
|
|
2006
|
+
</div>
|
|
2007
|
+
` : html ``}
|
|
2008
|
+
${contentArg}
|
|
2009
|
+
</section>
|
|
2010
|
+
`;
|
|
2011
|
+
}
|
|
2012
|
+
renderFormRow(labelArg, hintArg, contentArg, requiredArg = false) {
|
|
2013
|
+
return html `
|
|
2014
|
+
<div class="form-row">
|
|
2015
|
+
<div><div class="form-label">${labelArg}${requiredArg ? html `<span style="color:var(--idp-error)">*</span>` : html ``}</div>${hintArg ? html `<div class="form-hint">${hintArg}</div>` : html ``}</div>
|
|
2016
|
+
<div>${contentArg}</div>
|
|
2017
|
+
</div>
|
|
2018
|
+
`;
|
|
2019
|
+
}
|
|
2020
|
+
renderCodeBlock(valueArg) {
|
|
2021
|
+
return html `<div class="code-block"><code>${valueArg}</code><idp-icon name="copy" size="13"></idp-icon></div>`;
|
|
2022
|
+
}
|
|
2023
|
+
renderOverview() {
|
|
2024
|
+
const firstName = this.user?.name?.split(' ')[0] || 'there';
|
|
2025
|
+
const activeSessionCount = this.sessions.filter((sessionArg) => sessionArg.isCurrent).length || this.sessions.length;
|
|
2026
|
+
const activePassportCount = this.passportDevices.filter((deviceArg) => deviceArg.status === 'active').length;
|
|
2027
|
+
const kpis = [
|
|
2028
|
+
{
|
|
2029
|
+
label: 'Organisations',
|
|
2030
|
+
value: String(this.orgs.length),
|
|
2031
|
+
delta: 'live',
|
|
2032
|
+
deltaKind: 'live',
|
|
2033
|
+
spark: [1, 1, 1, 1, 1, 1, 1, Math.max(this.orgs.length, 1)],
|
|
2034
|
+
sparkColor: 'var(--idp-spark-info)',
|
|
2035
|
+
accent: 'var(--idp-chart-1)',
|
|
2036
|
+
sub: 'Memberships visible to this account',
|
|
2037
|
+
},
|
|
2038
|
+
{
|
|
2039
|
+
label: 'Sessions',
|
|
2040
|
+
value: String(this.sessions.length),
|
|
2041
|
+
delta: `${activeSessionCount} active`,
|
|
2042
|
+
deltaKind: 'up',
|
|
2043
|
+
spark: [1, 2, 1, 2, 3, 2, Math.max(this.sessions.length, 1)],
|
|
2044
|
+
sparkColor: 'var(--idp-spark-up)',
|
|
2045
|
+
accent: 'var(--idp-chart-2)',
|
|
2046
|
+
sub: this.sessions.length ? `Latest ${this.formatTimeAgo(Math.max(...this.sessions.map((sessionArg) => sessionArg.lastActive)))}` : 'No active sessions loaded',
|
|
2047
|
+
},
|
|
2048
|
+
{
|
|
2049
|
+
label: 'Passport devices',
|
|
2050
|
+
value: String(this.passportDevices.length),
|
|
2051
|
+
delta: `${activePassportCount} active`,
|
|
2052
|
+
deltaKind: 'live',
|
|
2053
|
+
spark: [1, 1, 1, Math.max(this.passportDevices.length, 1)],
|
|
2054
|
+
sparkColor: 'var(--idp-spark-info)',
|
|
2055
|
+
accent: 'var(--idp-chart-5)',
|
|
2056
|
+
sub: 'Cryptographic credentials',
|
|
2057
|
+
},
|
|
2058
|
+
{
|
|
2059
|
+
label: 'Activity',
|
|
2060
|
+
value: String(this.activities.length),
|
|
2061
|
+
delta: 'live',
|
|
2062
|
+
deltaKind: 'live',
|
|
2063
|
+
spark: [1, 2, 2, 3, Math.max(this.activities.length, 1)],
|
|
2064
|
+
sparkColor: 'var(--idp-spark-info)',
|
|
2065
|
+
accent: 'var(--idp-info)',
|
|
2066
|
+
sub: 'Recent account events',
|
|
2067
|
+
},
|
|
2068
|
+
];
|
|
2069
|
+
return html `
|
|
2070
|
+
<header class="page-head">
|
|
2071
|
+
<div>
|
|
2072
|
+
<div class="eyebrow-row"><span class="eyebrow">Account - Overview</span><span class="live-pill"><span class="live-dot"></span>live</span></div>
|
|
2073
|
+
<h1>Good morning, ${firstName}.</h1>
|
|
2074
|
+
<div class="lead">Account-wide operational snapshot using live identity data.</div>
|
|
2075
|
+
</div>
|
|
2076
|
+
<div class="page-actions"><button class="plain-button outline" @click=${() => this.setPage('sessions')}>Review sessions</button><button class="plain-button primary" @click=${() => this.setPage('security')}>Manage security</button></div>
|
|
2077
|
+
</header>
|
|
2078
|
+
<div class="body">
|
|
2079
|
+
<div class="kpis">${kpis.map((kpiArg) => this.renderKpi(kpiArg))}</div>
|
|
2080
|
+
${this.dataLoading || this.dataError ? this.renderDataState('No overview data', 'The console has not received live account data yet.', 'activity') : html ``}
|
|
2081
|
+
<div class="primary-grid">
|
|
2082
|
+
<div class="card">
|
|
2083
|
+
<div class="card-head"><span class="card-title">Recent activity</span><idp-badge>${this.activities.length} events</idp-badge></div>
|
|
2084
|
+
${this.activities.length ? this.activities.slice(0, 8).map((activityArg) => html `
|
|
2085
|
+
<div class="feed-item"><span class="feed-dot" style="--dot-color:var(--idp-info)"></span><div class="feed-text"><strong>${activityArg.action.replace(/_/g, ' ')}</strong> - ${activityArg.description}</div><span class="feed-meta">${this.formatTimeAgo(activityArg.timestamp)}</span></div>
|
|
2086
|
+
`) : this.renderStateCard('No activity yet', 'Activity events will appear here after logins, app changes, and organisation updates.', 'activity')}
|
|
2087
|
+
</div>
|
|
2088
|
+
<div class="card">
|
|
2089
|
+
<div class="card-head"><span class="card-title">Current sessions</span><idp-badge>${this.sessions.length} total</idp-badge></div>
|
|
2090
|
+
${this.sessions.length ? this.sessions.slice(0, 5).map((sessionArg) => html `
|
|
2091
|
+
<div class="feed-item"><span class="feed-dot" style="--dot-color:${sessionArg.isCurrent ? 'var(--idp-ok)' : 'var(--idp-muted-fg)'}"></span><div class="feed-text"><strong>${sessionArg.deviceName || 'Unknown device'}</strong> - <span class="mono">${sessionArg.browser} ${sessionArg.os}</span></div><span class="feed-meta">${this.formatTimeAgo(sessionArg.lastActive)}</span></div>
|
|
2092
|
+
`) : this.renderStateCard('No sessions loaded', 'Active session telemetry is unavailable or there are no sessions.', 'monitor')}
|
|
2093
|
+
</div>
|
|
2094
|
+
</div>
|
|
2095
|
+
</div>
|
|
2096
|
+
`;
|
|
2097
|
+
}
|
|
2098
|
+
renderProfile() {
|
|
2099
|
+
const username = this.user?.username || this.user?.email?.split('@')[0] || '';
|
|
2100
|
+
const status = this.user?.status || 'active';
|
|
2101
|
+
return html `
|
|
2102
|
+
${this.renderPageHeader('Profile', 'Your personal identity details visible to connected apps.')}
|
|
2103
|
+
<div class="body narrow-body">
|
|
2104
|
+
${this.renderSectionCard('Avatar', 'Shown to apps that request your profile.', html `<div class="split-row" style="justify-content:flex-start"><span class="avatar" style="width:56px;height:56px;font-size:20px">${this.userInitials}</span><div><div class="section-title">${this.user?.name || 'Unknown User'}</div><div class="muted" style="margin-top:5px">Profile update endpoints are not exposed in this console yet.</div></div></div>`)}
|
|
2105
|
+
${this.renderSectionCard('Personal information', '', html `
|
|
2106
|
+
${this.renderFormRow('Full name', '', html `<input class="input" .value=${this.user?.name || ''} disabled />`, true)}
|
|
2107
|
+
${this.renderFormRow('Username', 'Used in your public profile URL', html `<div class="input-group"><span class="input-prefix">idp.global/user/</span><input class="input" .value=${username} disabled /></div>`)}
|
|
2108
|
+
${this.renderFormRow('Email', 'Primary address for login and notifications', html `<input class="input" .value=${this.user?.email || ''} disabled />`)}
|
|
2109
|
+
${this.renderFormRow('Mobile number', 'Used for SMS verification', html `<input class="input" .value=${this.user?.mobileNumber || ''} disabled />`)}
|
|
2110
|
+
`)}
|
|
2111
|
+
${this.renderSectionCard('Account status', '', html `<div class="split-row"><div><div class="section-title">Status</div><div class="muted">Your account is currently ${status}.</div></div><idp-badge variant=${status === 'active' ? 'ok' : status === 'suspended' ? 'error' : 'warn'}>${status}</idp-badge></div>${this.globalAdmin ? html `<div class="divider"></div><div class="split-row"><div><div class="section-title">Global admin</div><div class="muted">You have platform-wide administrative access.</div></div><idp-badge variant="accent">Admin</idp-badge></div>` : html ``}`)}
|
|
2112
|
+
</div>
|
|
2113
|
+
`;
|
|
2114
|
+
}
|
|
2115
|
+
renderSecurity() {
|
|
2116
|
+
const passportRows = this.passportDevices.map((deviceArg) => ({
|
|
2117
|
+
cells: [
|
|
2118
|
+
html `
|
|
2119
|
+
<div class="identity-cell">
|
|
2120
|
+
<span class="identity-avatar">${this.getInitials(deviceArg.label)}</span>
|
|
2121
|
+
<div>
|
|
2122
|
+
<div class="identity-primary">${deviceArg.label}</div>
|
|
2123
|
+
<div class="identity-secondary">${deviceArg.platform}${deviceArg.appVersion ? ` - ${deviceArg.appVersion}` : ''}</div>
|
|
2124
|
+
</div>
|
|
2125
|
+
</div>
|
|
2126
|
+
`,
|
|
2127
|
+
html `<idp-badge variant=${deviceArg.status === 'active' ? 'ok' : 'error'}>${deviceArg.status}</idp-badge>`,
|
|
2128
|
+
[
|
|
2129
|
+
deviceArg.capabilities?.push ? 'push' : '',
|
|
2130
|
+
deviceArg.capabilities?.nfc ? 'nfc' : '',
|
|
2131
|
+
deviceArg.capabilities?.gps ? 'gps' : '',
|
|
2132
|
+
].filter(Boolean).join(', ') || '-',
|
|
2133
|
+
deviceArg.lastSeenAt ? this.formatTimeAgo(deviceArg.lastSeenAt) : 'never',
|
|
2134
|
+
html `<div class="cell-actions"><button class="table-action destructive" @click=${() => this.dispatchShellEvent('idp-admin-passport-revoke', { deviceId: deviceArg.id })}>Revoke</button></div>`,
|
|
2135
|
+
],
|
|
2136
|
+
}));
|
|
2137
|
+
return html `
|
|
2138
|
+
${this.renderPageHeader('Security', 'Manage how you authenticate and protect your account.')}
|
|
2139
|
+
<div class="body wide-body">
|
|
2140
|
+
${this.credentialMessage ? html `<div class="notice-card"><idp-icon name="shield" size="16"></idp-icon><div><div class="section-title">Credential update</div><div class="muted">${this.credentialMessage}</div></div></div>` : html ``}
|
|
2141
|
+
${this.credentialError ? html `<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">Credential error</div><div class="muted">${this.credentialError}</div></div></div>` : html ``}
|
|
2142
|
+
${this.renderSectionCard('Session security', 'Live session data is available and sessions can be revoked from the device list.', html `
|
|
2143
|
+
<div class="split-row"><div><div class="section-title">Active sessions</div><div class="muted">Review and revoke sessions from the Sessions & Devices page.</div></div><idp-badge variant="accent">${this.sessions.length}</idp-badge></div>
|
|
2144
|
+
<div class="divider"></div>
|
|
2145
|
+
<button class="plain-button outline" @click=${() => this.setPage('sessions')}>Open sessions</button>
|
|
2146
|
+
`)}
|
|
2147
|
+
${this.renderSectionCard('Password', 'Change your password using the existing production password endpoint. All fields are required.', html `
|
|
2148
|
+
${this.renderFormRow('Current password', '', html `<input class="input" type="password" autocomplete="current-password" .value=${this.currentPassword} @input=${(eventArg) => this.setPasswordField('current', eventArg)} />`, true)}
|
|
2149
|
+
${this.renderFormRow('New password', 'Minimum 12 characters.', html `<input class="input" type="password" autocomplete="new-password" .value=${this.newPassword} @input=${(eventArg) => this.setPasswordField('new', eventArg)} />`, true)}
|
|
2150
|
+
${this.renderFormRow('Confirm password', '', html `<input class="input" type="password" autocomplete="new-password" .value=${this.confirmPassword} @input=${(eventArg) => this.setPasswordField('confirm', eventArg)} />`, true)}
|
|
2151
|
+
<div class="divider"></div>
|
|
2152
|
+
<button class="plain-button primary" @click=${() => this.submitPasswordChange()}>Update password</button>
|
|
2153
|
+
`)}
|
|
2154
|
+
<idp-data-table
|
|
2155
|
+
title="Passport devices"
|
|
2156
|
+
subtitle="Cryptographic IDP Passport devices registered for this account."
|
|
2157
|
+
badge=${`${this.passportDevices.length} total`}
|
|
2158
|
+
empty-title="No passport devices"
|
|
2159
|
+
empty-description="Passport devices will appear here after enrollment from the mobile passport app."
|
|
2160
|
+
.columns=${[
|
|
2161
|
+
{ label: 'Device' },
|
|
2162
|
+
{ label: 'Status' },
|
|
2163
|
+
{ label: 'Capabilities', hideBelow: 'mobile' },
|
|
2164
|
+
{ label: 'Last seen', mono: true, hideBelow: 'mobile' },
|
|
2165
|
+
{ label: 'Action', align: 'right' },
|
|
2166
|
+
]}
|
|
2167
|
+
.rows=${passportRows}
|
|
2168
|
+
></idp-data-table>
|
|
2169
|
+
<div class="section-card">
|
|
2170
|
+
<div class="section-headline">
|
|
2171
|
+
<div><div class="section-title">Enroll passport device</div><div class="section-description">Creates a signed enrollment challenge for the IDP Passport device flow.</div></div>
|
|
2172
|
+
<button class="plain-button outline" @click=${() => this.requestPassportEnrollment()}>Create challenge</button>
|
|
2173
|
+
</div>
|
|
2174
|
+
${this.passportEnrollment ? html `
|
|
2175
|
+
<div class="notice-card" style="margin-bottom:14px"><idp-icon name="key" size="16"></idp-icon><div><div class="section-title">Enrollment challenge ready</div><div class="muted">Expires ${new Date(this.passportEnrollment.expiresAt).toLocaleString()}. Use the pairing token or payload in a passport client to complete enrollment.</div></div></div>
|
|
2176
|
+
${this.renderFormRow('Pairing token', '', this.renderCodeBlock(this.passportEnrollment.pairingToken))}
|
|
2177
|
+
${this.renderFormRow('Pairing payload', '', this.renderCodeBlock(this.passportEnrollment.pairingPayload))}
|
|
2178
|
+
${this.renderFormRow('Signing payload', '', this.renderCodeBlock(this.passportEnrollment.signingPayload))}
|
|
2179
|
+
` : html `<div class="muted">No active enrollment challenge.</div>`}
|
|
2180
|
+
</div>
|
|
2181
|
+
<div class="primary-grid">
|
|
2182
|
+
${this.renderStateCard('TOTP controls not connected', 'No TOTP secret, enrollment, or verification endpoints exist in this backend yet, so no fake TOTP toggle is shown.', 'lock')}
|
|
2183
|
+
${this.renderStateCard('WebAuthn passkeys not connected', 'No WebAuthn passkey credential model or assertion endpoints exist yet. Passport devices are the available cryptographic credential path.', 'key')}
|
|
2184
|
+
</div>
|
|
2185
|
+
</div>
|
|
2186
|
+
`;
|
|
2187
|
+
}
|
|
2188
|
+
renderSessions() {
|
|
2189
|
+
return html `
|
|
2190
|
+
${this.renderPageHeader('Sessions & Devices', 'Active login sessions across all your devices.')}
|
|
2191
|
+
<div class="body narrow-body"><div class="list-stack">
|
|
2192
|
+
${this.sessions.length ? this.sessions.map((sessionArg) => html `
|
|
2193
|
+
<div class="row-card">
|
|
2194
|
+
<span class="icon-tile"><idp-icon name="monitor" size="17"></idp-icon></span>
|
|
2195
|
+
<div style="flex:1">
|
|
2196
|
+
<div style="display:flex;gap:8px;align-items:center"><span class="section-title">${sessionArg.deviceName || 'Unknown device'}</span>${sessionArg.isCurrent ? html `<idp-badge variant="ok">Current session</idp-badge>` : html ``}</div>
|
|
2197
|
+
<div class="muted">${sessionArg.browser || 'Unknown browser'} - ${sessionArg.os || 'Unknown OS'} - IP: <span class="mono">${sessionArg.ip || 'unknown'}</span></div>
|
|
2198
|
+
<div class="muted">Started ${this.formatTimeAgo(sessionArg.createdAt)} - Active ${this.formatTimeAgo(sessionArg.lastActive)}</div>
|
|
2199
|
+
</div>
|
|
2200
|
+
${sessionArg.isCurrent ? html `` : html `<button class="plain-button ghost" style="color:var(--idp-error)" @click=${() => this.dispatchShellEvent('idp-admin-session-revoke', { sessionId: sessionArg.id })}>Revoke</button>`}
|
|
2201
|
+
</div>
|
|
2202
|
+
`) : this.renderDataState('No sessions', 'There are no active sessions for this account or session telemetry is unavailable.', 'monitor')}
|
|
2203
|
+
</div></div>
|
|
2204
|
+
`;
|
|
2205
|
+
}
|
|
2206
|
+
renderAccountApps() {
|
|
2207
|
+
const apps = this.accountApps;
|
|
2208
|
+
return html `
|
|
2209
|
+
${this.renderPageHeader('Connected Apps', 'Third-party apps and services that have OAuth access to your account.')}
|
|
2210
|
+
<div class="body narrow-body"><div class="list-stack">
|
|
2211
|
+
${apps.length ? apps.map((appArg) => html `<div class="row-card"><span class="app-avatar">${appArg.name.slice(0, 2).toUpperCase()}</span><div style="flex:1"><div class="section-title" style="margin-bottom:4px">${appArg.name}</div><div class="chip-row">${(appArg.scopes || []).map((scopeArg) => html `<idp-badge variant="outline">${scopeArg}</idp-badge>`)}</div><div class="muted" style="margin-top:6px">${appArg.description || appArg.appUrl || 'Connected application'}</div></div><button class="plain-button ghost" style="color:var(--idp-error)" @click=${() => this.dispatchShellEvent('idp-admin-app-toggle', { appId: appArg.id, connected: false })}>Revoke</button></div>`) : this.renderDataState('Account app grants not connected', 'No account-level OAuth grant endpoint is wired into this app yet. Organisation app connections are managed under Organisation > OAuth Apps.', 'grid')}
|
|
2212
|
+
</div></div>
|
|
2213
|
+
`;
|
|
2214
|
+
}
|
|
2215
|
+
renderOrgGeneral() {
|
|
2216
|
+
const org = this.currentOrg;
|
|
2217
|
+
const connectedAppCount = this.orgApps.filter((appArg) => appArg.isConnected).length;
|
|
2218
|
+
const orgActivities = this.activities
|
|
2219
|
+
.filter((activityArg) => {
|
|
2220
|
+
const searchableText = `${activityArg.targetType || ''} ${activityArg.description || ''}`.toLowerCase();
|
|
2221
|
+
return Boolean(org.slug && searchableText.includes(org.slug.toLowerCase()))
|
|
2222
|
+
|| Boolean(org.name && searchableText.includes(org.name.toLowerCase()))
|
|
2223
|
+
|| searchableText.includes('org')
|
|
2224
|
+
|| searchableText.includes('organization')
|
|
2225
|
+
|| searchableText.includes('organisation');
|
|
2226
|
+
})
|
|
2227
|
+
.slice(0, 5);
|
|
2228
|
+
const kpis = [
|
|
2229
|
+
{
|
|
2230
|
+
label: 'Members',
|
|
2231
|
+
value: String(this.orgMembers.length),
|
|
2232
|
+
delta: `${this.orgInvitations.length} pending`,
|
|
2233
|
+
deltaKind: 'up',
|
|
2234
|
+
spark: [1, 1, 2, Math.max(this.orgMembers.length, 1)],
|
|
2235
|
+
sparkColor: 'var(--idp-spark-up)',
|
|
2236
|
+
accent: 'var(--idp-chart-5)',
|
|
2237
|
+
sub: org.name,
|
|
2238
|
+
},
|
|
2239
|
+
{
|
|
2240
|
+
label: 'Connected apps',
|
|
2241
|
+
value: String(connectedAppCount),
|
|
2242
|
+
delta: `${this.orgApps.length} available`,
|
|
2243
|
+
deltaKind: 'live',
|
|
2244
|
+
spark: [1, 2, 2, Math.max(connectedAppCount, 1)],
|
|
2245
|
+
sparkColor: 'var(--idp-spark-info)',
|
|
2246
|
+
accent: 'var(--idp-info)',
|
|
2247
|
+
sub: 'Organisation OAuth catalogue',
|
|
2248
|
+
},
|
|
2249
|
+
{
|
|
2250
|
+
label: 'Role',
|
|
2251
|
+
value: org.myRole || 'member',
|
|
2252
|
+
delta: 'live',
|
|
2253
|
+
deltaKind: 'live',
|
|
2254
|
+
spark: [1, 1, 1, 1],
|
|
2255
|
+
sparkColor: 'var(--idp-spark-info)',
|
|
2256
|
+
accent: 'var(--idp-chart-1)',
|
|
2257
|
+
sub: 'Your access level',
|
|
2258
|
+
},
|
|
2259
|
+
{
|
|
2260
|
+
label: 'Activity',
|
|
2261
|
+
value: String(orgActivities.length),
|
|
2262
|
+
delta: `${this.activities.length} account events`,
|
|
2263
|
+
deltaKind: 'up',
|
|
2264
|
+
spark: [1, 1, Math.max(orgActivities.length, 1)],
|
|
2265
|
+
sparkColor: 'var(--idp-spark-up)',
|
|
2266
|
+
accent: 'var(--idp-chart-2)',
|
|
2267
|
+
sub: 'Recent org-related events',
|
|
2268
|
+
},
|
|
2269
|
+
];
|
|
2270
|
+
return html `
|
|
2271
|
+
<header class="page-head">
|
|
2272
|
+
<div>
|
|
2273
|
+
<div class="eyebrow-row"><span class="eyebrow">Organisation - General</span><span class="live-pill"><span class="live-dot"></span>live</span></div>
|
|
2274
|
+
<h1>${org.name}</h1>
|
|
2275
|
+
<div class="lead">Selected organisation dashboard for <code>${org.slug ? `@${org.slug}` : org.id || 'no organisation selected'}</code>.</div>
|
|
2276
|
+
</div>
|
|
2277
|
+
<div class="page-actions"><button class="plain-button outline" @click=${() => this.setPage('org-members')}>Manage members</button><button class="plain-button primary" @click=${() => this.setPage('org-apps')}>Manage apps</button></div>
|
|
2278
|
+
</header>
|
|
2279
|
+
<div class="body">
|
|
2280
|
+
<div class="kpis">${kpis.map((kpiArg) => this.renderKpi(kpiArg))}</div>
|
|
2281
|
+
${this.dataLoading || this.dataError ? this.renderDataState('No organisation data', 'The console has not received live organisation data yet.', 'building') : html ``}
|
|
2282
|
+
<div class="primary-grid">
|
|
2283
|
+
<div class="card">
|
|
2284
|
+
<div class="card-head"><span class="card-title">Organisation profile</span><idp-badge>${org.myRole || 'member'}</idp-badge></div>
|
|
2285
|
+
<div style="padding:16px">
|
|
2286
|
+
<div style="display:flex;align-items:center;gap:14px;margin-bottom:16px"><span class="org-avatar" style="width:48px;height:48px;font-size:17px">${org.name.slice(0, 2).toUpperCase()}</span><div><div style="font-size:16px;font-weight:600;color:var(--idp-fg)">${org.name}</div><div class="mono">idp.global/org/${org.slug || 'unassigned'}</div></div></div>
|
|
2287
|
+
${this.renderCodeBlock(org.id || 'No organisation selected')}
|
|
2288
|
+
<div class="muted" style="margin-top:10px">Rename, slug updates, ownership transfer, and deletion are available from Settings with server-side audited confirmation.</div>
|
|
2289
|
+
</div>
|
|
2290
|
+
</div>
|
|
2291
|
+
<div class="card">
|
|
2292
|
+
<div class="card-head"><span class="card-title">Recent organisation activity</span><idp-badge>${orgActivities.length} events</idp-badge></div>
|
|
2293
|
+
${orgActivities.length ? orgActivities.map((activityArg) => html `
|
|
2294
|
+
<div class="feed-item"><span class="feed-dot" style="--dot-color:var(--idp-info)"></span><div class="feed-text"><strong>${activityArg.action.replace(/_/g, ' ')}</strong> - ${activityArg.description}</div><span class="feed-meta">${this.formatTimeAgo(activityArg.timestamp)}</span></div>
|
|
2295
|
+
`) : this.renderStateCard('No org activity yet', 'Organisation-related activity will appear here when the backend reports matching activity events.', 'activity')}
|
|
2296
|
+
</div>
|
|
2297
|
+
</div>
|
|
2298
|
+
</div>
|
|
2299
|
+
`;
|
|
2300
|
+
}
|
|
2301
|
+
renderOrgSettings() {
|
|
2302
|
+
const org = this.currentOrg;
|
|
2303
|
+
this.syncOrgSettingsState();
|
|
2304
|
+
const transferCandidates = this.orgMembers.filter((memberArg) => !memberArg.isCurrentUser);
|
|
2305
|
+
const transferConfirmText = `transfer ${org.slug}`;
|
|
2306
|
+
const deleteConfirmText = `delete ${org.slug}`;
|
|
2307
|
+
const identityChanged = this.orgNameDraft.trim() !== org.name || this.orgSlugDraft.trim().toLowerCase() !== org.slug;
|
|
2308
|
+
return html `
|
|
2309
|
+
${this.renderPageHeader('Organisation Settings', 'Audited configuration and owner-controlled destructive operations.')}
|
|
2310
|
+
<div class="body narrow-body">
|
|
2311
|
+
${this.orgSettingsError ? html `<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">Settings action blocked</div><div class="muted">${this.orgSettingsError}</div></div></div>` : html ``}
|
|
2312
|
+
${this.renderSectionCard('Organisation identity', `Type ${org.slug} to confirm name or slug changes. The backend verifies this confirmation before saving.`, html `
|
|
2313
|
+
<div style="display:flex;align-items:center;gap:14px;margin-bottom:20px"><span class="org-avatar" style="width:48px;height:48px;font-size:17px">${org.name.slice(0, 2).toUpperCase()}</span><div><div style="font-size:16px;font-weight:600;color:var(--idp-fg)">${org.name}</div><div class="mono">idp.global/org/${org.slug}</div></div></div>
|
|
2314
|
+
${this.renderFormRow('Organisation name', '', html `<input class="input" .value=${this.orgNameDraft} @input=${(eventArg) => this.setOrgSettingsField('name', eventArg)} />`, true)}
|
|
2315
|
+
${this.renderFormRow('URL slug', "Used in your org's public URLs.", html `<div class="input-group"><span class="input-prefix">idp.global/org/</span><input class="input" .value=${this.orgSlugDraft} @input=${(eventArg) => this.setOrgSettingsField('slug', eventArg)} /></div>`)}
|
|
2316
|
+
${this.renderFormRow('Confirmation', `Type ${org.slug}`, html `<input class="input" .value=${this.orgSettingsConfirmation} @input=${(eventArg) => this.setOrgSettingsField('settingsConfirmation', eventArg)} />`)}
|
|
2317
|
+
<div class="divider"></div>
|
|
2318
|
+
<button class="plain-button primary" ?disabled=${!identityChanged} @click=${() => this.submitOrgSettingsUpdate()}>Apply identity changes</button>
|
|
2319
|
+
`)}
|
|
2320
|
+
${this.renderSectionCard('Organisation ID', 'Use this identifier when making API calls.', this.renderCodeBlock(org.id))}
|
|
2321
|
+
${this.renderSectionCard('Transfer ownership', `Owner-only operation. Type ${transferConfirmText} to confirm.`, html `
|
|
2322
|
+
${transferCandidates.length ? html `
|
|
2323
|
+
${this.renderFormRow('New owner', 'The target user must already be an organisation member.', html `
|
|
2324
|
+
<select class="select" .value=${this.transferOwnerId} @change=${(eventArg) => this.setOrgSettingsField('transferOwnerId', eventArg)}>
|
|
2325
|
+
<option value="">Select a member</option>
|
|
2326
|
+
${transferCandidates.map((memberArg) => html `<option value=${memberArg.userId}>${memberArg.name || memberArg.email} (${memberArg.email})</option>`)}
|
|
2327
|
+
</select>
|
|
2328
|
+
`, true)}
|
|
2329
|
+
${this.renderFormRow('Confirmation', `Type ${transferConfirmText}`, html `<input class="input" .value=${this.transferConfirmation} @input=${(eventArg) => this.setOrgSettingsField('transferConfirmation', eventArg)} />`)}
|
|
2330
|
+
<div class="divider"></div>
|
|
2331
|
+
<button class="plain-button outline" @click=${() => this.submitOrgTransfer()}>Transfer ownership</button>
|
|
2332
|
+
` : this.renderStateCard('No transfer candidates loaded', 'Load organisation members before transferring ownership.', 'users')}
|
|
2333
|
+
`)}
|
|
2334
|
+
${this.renderSectionCard('Delete organisation', `Owner-only destructive operation. Type ${deleteConfirmText} to permanently remove this organisation, its memberships, pending invitations, billing records, and app connections.`, html `
|
|
2335
|
+
${this.renderFormRow('Confirmation', `Type ${deleteConfirmText}`, html `<input class="input" .value=${this.deleteConfirmation} @input=${(eventArg) => this.setOrgSettingsField('deleteConfirmation', eventArg)} />`)}
|
|
2336
|
+
<div class="divider"></div>
|
|
2337
|
+
<button class="plain-button destructive" @click=${() => this.submitOrgDelete()}>Delete organisation</button>
|
|
2338
|
+
`)}
|
|
2339
|
+
</div>
|
|
2340
|
+
`;
|
|
2341
|
+
}
|
|
2342
|
+
renderOrgMembers() {
|
|
2343
|
+
const customRoleRows = this.orgRoleDefinitions.map((roleArg) => ({
|
|
2344
|
+
cells: [
|
|
2345
|
+
html `
|
|
2346
|
+
<div class="identity-cell">
|
|
2347
|
+
<span class="identity-avatar">${this.getInitials(roleArg.name)}</span>
|
|
2348
|
+
<div>
|
|
2349
|
+
<div class="identity-primary">${roleArg.name}</div>
|
|
2350
|
+
<div class="identity-secondary">${roleArg.description || 'Custom organisation role'}</div>
|
|
2351
|
+
</div>
|
|
2352
|
+
</div>
|
|
2353
|
+
`,
|
|
2354
|
+
roleArg.key,
|
|
2355
|
+
html `
|
|
2356
|
+
<div class="cell-actions">
|
|
2357
|
+
<button class="table-action" @click=${() => this.openRoleUpsertDialog(roleArg)}>Edit</button>
|
|
2358
|
+
<button class="table-action destructive" @click=${() => this.openRoleDeleteDialog(roleArg)}>Delete</button>
|
|
2359
|
+
</div>
|
|
2360
|
+
`,
|
|
2361
|
+
],
|
|
2362
|
+
}));
|
|
2363
|
+
const memberRows = this.orgMembers.map((memberArg) => ({
|
|
2364
|
+
cells: [
|
|
2365
|
+
html `
|
|
2366
|
+
<div class="identity-cell">
|
|
2367
|
+
<span class="identity-avatar">${this.getInitials(memberArg.name || memberArg.email)}</span>
|
|
2368
|
+
<div>
|
|
2369
|
+
<div class="identity-primary">${memberArg.name || memberArg.email}</div>
|
|
2370
|
+
<div class="identity-secondary">${memberArg.email}</div>
|
|
2371
|
+
</div>
|
|
2372
|
+
</div>
|
|
2373
|
+
`,
|
|
2374
|
+
html `<div class="chip-row">${memberArg.roles.map((roleArg) => html `<idp-badge variant=${this.roleVariant(roleArg)}>${roleArg}</idp-badge>`)}</div>`,
|
|
2375
|
+
memberArg.isCurrentUser ? html `<idp-badge variant="accent">You</idp-badge>` : html `<idp-badge variant="outline">Member</idp-badge>`,
|
|
2376
|
+
memberArg.roles.includes('owner') || memberArg.isCurrentUser
|
|
2377
|
+
? html `<div class="cell-actions"><button class="table-action" @click=${() => this.openMemberRolesDialog(memberArg)}>Edit roles</button></div>`
|
|
2378
|
+
: html `<div class="cell-actions"><button class="table-action" @click=${() => this.openMemberRolesDialog(memberArg)}>Edit roles</button><button class="table-action destructive" @click=${() => this.dispatchShellEvent('idp-admin-member-remove', { userId: memberArg.userId })}>Remove</button></div>`,
|
|
2379
|
+
],
|
|
2380
|
+
}));
|
|
2381
|
+
const invitationRows = this.orgInvitations.map((inviteArg) => ({
|
|
2382
|
+
cells: [
|
|
2383
|
+
html `
|
|
2384
|
+
<div class="identity-cell">
|
|
2385
|
+
<span class="identity-avatar">${this.getInitials(inviteArg.email)}</span>
|
|
2386
|
+
<div>
|
|
2387
|
+
<div class="identity-primary">${inviteArg.email}</div>
|
|
2388
|
+
<div class="identity-secondary">Invited ${this.formatTimeAgo(inviteArg.invitedAt)}</div>
|
|
2389
|
+
</div>
|
|
2390
|
+
</div>
|
|
2391
|
+
`,
|
|
2392
|
+
html `<div class="chip-row">${inviteArg.roles.map((roleArg) => html `<idp-badge variant=${this.roleVariant(roleArg)}>${roleArg}</idp-badge>`)}</div>`,
|
|
2393
|
+
new Date(inviteArg.expiresAt).toLocaleDateString(),
|
|
2394
|
+
html `
|
|
2395
|
+
<div class="cell-actions">
|
|
2396
|
+
<button class="table-action" @click=${() => this.dispatchShellEvent('idp-admin-invitation-resend', { invitationId: inviteArg.id })}>Resend</button>
|
|
2397
|
+
<button class="table-action destructive" @click=${() => this.dispatchShellEvent('idp-admin-invitation-cancel', { invitationId: inviteArg.id })}>Cancel</button>
|
|
2398
|
+
</div>
|
|
2399
|
+
`,
|
|
2400
|
+
],
|
|
2401
|
+
}));
|
|
2402
|
+
return html `
|
|
2403
|
+
${this.renderPageHeader('Members', `${this.orgMembers.length} members - ${this.orgInvitations.length} pending invitations`, html `<button class="plain-button primary" @click=${() => this.dispatchShellEvent('idp-admin-member-invite', { orgId: this.currentOrg.id })}><idp-icon name="plus" size="12"></idp-icon>Invite member</button>`)}
|
|
2404
|
+
<div class="body wide-body">
|
|
2405
|
+
${this.orgSettingsError ? html `<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">Role action blocked</div><div class="muted">${this.orgSettingsError}</div></div></div>` : html ``}
|
|
2406
|
+
<idp-data-table
|
|
2407
|
+
title="Custom organisation roles"
|
|
2408
|
+
subtitle="Business roles defined by this organisation. Platform roles like owner/admin remain protected."
|
|
2409
|
+
badge=${`${this.orgRoleDefinitions.length} custom`}
|
|
2410
|
+
empty-title="No custom roles"
|
|
2411
|
+
empty-description="Create custom roles such as Finance, Support Lead, or Contractor, then assign them to members."
|
|
2412
|
+
.columns=${[
|
|
2413
|
+
{ label: 'Role' },
|
|
2414
|
+
{ label: 'Key', mono: true },
|
|
2415
|
+
{ label: 'Action', align: 'right' },
|
|
2416
|
+
]}
|
|
2417
|
+
.rows=${customRoleRows}
|
|
2418
|
+
></idp-data-table>
|
|
2419
|
+
<div><button class="plain-button outline" @click=${() => this.openRoleUpsertDialog()}><idp-icon name="plus" size="12"></idp-icon>Add custom role</button></div>
|
|
2420
|
+
<idp-data-table
|
|
2421
|
+
title="Members"
|
|
2422
|
+
badge=${`${this.orgMembers.length} total`}
|
|
2423
|
+
empty-title="No members loaded"
|
|
2424
|
+
empty-description="Members will appear here after organisation membership data is loaded."
|
|
2425
|
+
.columns=${[
|
|
2426
|
+
{ label: 'User' },
|
|
2427
|
+
{ label: 'Roles', hideBelow: 'mobile' },
|
|
2428
|
+
{ label: 'Status' },
|
|
2429
|
+
{ label: 'Action', align: 'right' },
|
|
2430
|
+
]}
|
|
2431
|
+
.rows=${memberRows}
|
|
2432
|
+
></idp-data-table>
|
|
2433
|
+
${this.orgInvitations.length ? html `
|
|
2434
|
+
<idp-data-table
|
|
2435
|
+
title="Pending invitations"
|
|
2436
|
+
badge=${`${this.orgInvitations.length} total`}
|
|
2437
|
+
.columns=${[
|
|
2438
|
+
{ label: 'Invitee' },
|
|
2439
|
+
{ label: 'Roles', hideBelow: 'mobile' },
|
|
2440
|
+
{ label: 'Expires', mono: true },
|
|
2441
|
+
{ label: 'Action', align: 'right' },
|
|
2442
|
+
]}
|
|
2443
|
+
.rows=${invitationRows}
|
|
2444
|
+
></idp-data-table>
|
|
2445
|
+
` : html ``}
|
|
2446
|
+
</div>
|
|
2447
|
+
`;
|
|
2448
|
+
}
|
|
2449
|
+
renderOrgApps() {
|
|
2450
|
+
const appRows = this.orgApps.map((appArg) => ({
|
|
2451
|
+
cells: [
|
|
2452
|
+
html `
|
|
2453
|
+
<div class="identity-cell">
|
|
2454
|
+
<span class="identity-avatar">${this.getInitials(appArg.name)}</span>
|
|
2455
|
+
<div>
|
|
2456
|
+
<div class="identity-primary">${appArg.name}</div>
|
|
2457
|
+
<div class="identity-secondary">${appArg.description || appArg.appUrl || 'Global app'}</div>
|
|
2458
|
+
</div>
|
|
2459
|
+
</div>
|
|
2460
|
+
`,
|
|
2461
|
+
appArg.clientId || '-',
|
|
2462
|
+
html `<div class="chip-row">${(appArg.scopes || []).slice(0, 4).map((scopeArg) => html `<idp-badge variant="outline">${scopeArg}</idp-badge>`)}</div>`,
|
|
2463
|
+
html `<idp-badge variant=${appArg.isConnected ? 'ok' : 'outline'}>${appArg.isConnected ? 'connected' : 'available'}</idp-badge>`,
|
|
2464
|
+
html `<idp-badge variant=${appArg.roleMappings?.length ? 'accent' : 'outline'}>${appArg.roleMappings?.length || 0} mappings</idp-badge>`,
|
|
2465
|
+
html `<div class="cell-actions">${appArg.isConnected ? html `<button class="table-action" @click=${() => this.openAppRoleMappingsDialog(appArg)}>Map roles</button>` : html ``}<button class="table-action ${appArg.isConnected ? '' : 'primary'}" @click=${() => this.dispatchShellEvent('idp-admin-app-toggle', { appId: appArg.id, connected: !appArg.isConnected })}>${appArg.isConnected ? 'Disconnect' : 'Connect'}</button></div>`,
|
|
2466
|
+
],
|
|
2467
|
+
}));
|
|
2468
|
+
return html `
|
|
2469
|
+
${this.renderPageHeader('Apps', "Global apps connected to this organisation.")}
|
|
2470
|
+
<div class="body wide-body">
|
|
2471
|
+
${this.orgSettingsError ? html `<div class="notice-card" style="border-color:var(--idp-error-border);background:var(--idp-error-bg)"><idp-icon name="alert" size="16" style="color:var(--idp-error)"></idp-icon><div><div class="section-title" style="color:var(--idp-error)">App mapping blocked</div><div class="muted">${this.orgSettingsError}</div></div></div>` : html ``}
|
|
2472
|
+
<idp-data-table
|
|
2473
|
+
title="OAuth apps"
|
|
2474
|
+
badge=${`${this.orgApps.length} total`}
|
|
2475
|
+
empty-title="No apps available"
|
|
2476
|
+
empty-description="Global apps will appear here after app catalogue data is loaded."
|
|
2477
|
+
.columns=${[
|
|
2478
|
+
{ label: 'App' },
|
|
2479
|
+
{ label: 'Client ID', mono: true, hideBelow: 'tablet' },
|
|
2480
|
+
{ label: 'Scopes', hideBelow: 'mobile' },
|
|
2481
|
+
{ label: 'Status' },
|
|
2482
|
+
{ label: 'Role mappings' },
|
|
2483
|
+
{ label: 'Action', align: 'right' },
|
|
2484
|
+
]}
|
|
2485
|
+
.rows=${appRows}
|
|
2486
|
+
></idp-data-table>
|
|
2487
|
+
</div>
|
|
2488
|
+
`;
|
|
2489
|
+
}
|
|
2490
|
+
renderSupport() {
|
|
2491
|
+
const services = [
|
|
2492
|
+
['Account Recovery', 'Lost access to your account or locked out of your organisation? Our team will verify your identity and restore access securely.', 'EUR149', 'per incident', 'key', '1-2 business days'],
|
|
2493
|
+
['Organisation Recovery', 'All owners have lost access to your organisation. We can verify ownership and restore admin access.', 'EUR249', 'per incident', 'building', '2-3 business days'],
|
|
2494
|
+
['Data Export & Migration', 'Full export of your org data - users, sessions, app connections - for migration or compliance.', 'EUR199', 'per request', 'box', '3-5 business days'],
|
|
2495
|
+
['Identity & SSO Consulting', 'Architecture review, OIDC guidance, and custom SSO setup for your organisation stack.', 'EUR190', 'per hour', 'globe', 'Scheduled session'],
|
|
2496
|
+
['Security Review', 'Audit of connected apps, active sessions, passkey policies, and role assignments.', 'EUR390', 'per review', 'shield', '5-7 business days'],
|
|
2497
|
+
];
|
|
2498
|
+
return html `
|
|
2499
|
+
${this.renderPageHeader('Support', 'idp.global is free for everyone. Paid options cover hands-on recovery and consulting work.')}
|
|
2500
|
+
<div class="body narrow-body"><div class="row-card" style="background:var(--idp-accent-soft);border-color:var(--idp-info-border)"><idp-icon name="shield" size="16" style="color:var(--idp-accent)"></idp-icon><div><div class="section-title" style="color:var(--idp-accent)">idp.global is free, forever</div><div class="muted">All platform features - authentication, passkeys, OIDC apps, team management - are included at no cost.</div></div></div><div class="list-stack">${services.map((serviceArg) => html `<div class="row-card"><span class="icon-tile"><idp-icon name=${serviceArg[4]} size="16"></idp-icon></span><div style="flex:1"><div style="display:flex;gap:8px;align-items:baseline"><span class="section-title">${serviceArg[0]}</span><span class="muted">- ${serviceArg[5]}</span></div><div class="muted">${serviceArg[1]}</div><div style="display:flex;align-items:center;justify-content:space-between;margin-top:10px"><div><span style="font-size:16px;font-weight:700;color:var(--idp-fg)">${serviceArg[2]}</span> <span class="muted">${serviceArg[3]}</span></div><button class="plain-button outline" disabled>Request flow pending</button></div></div></div>`)}</div></div>
|
|
2501
|
+
`;
|
|
2502
|
+
}
|
|
2503
|
+
renderGAUsers() {
|
|
2504
|
+
return html `${this.renderPageHeader('All Users', 'Platform-wide user administration.')}<div class="body wide-body">${this.renderDataState('User directory not connected', 'The shell is ready for global user data, but no platform user-list endpoint is wired into this app yet. No demo users are shown in production mode.', 'users')}</div>`;
|
|
2505
|
+
}
|
|
2506
|
+
renderGAOrgs() {
|
|
2507
|
+
const orgRows = this.orgs.map((orgArg) => ({
|
|
2508
|
+
cells: [
|
|
2509
|
+
html `
|
|
2510
|
+
<div class="identity-cell">
|
|
2511
|
+
<span class="identity-avatar">${this.getInitials(orgArg.name)}</span>
|
|
2512
|
+
<div>
|
|
2513
|
+
<div class="identity-primary">${orgArg.name}</div>
|
|
2514
|
+
<div class="identity-secondary">${orgArg.slug ? `idp.global/org/${orgArg.slug}` : 'No slug'}</div>
|
|
2515
|
+
</div>
|
|
2516
|
+
</div>
|
|
2517
|
+
`,
|
|
2518
|
+
orgArg.slug || '-',
|
|
2519
|
+
html `<idp-badge variant=${this.roleVariant(orgArg.myRole || 'member')}>${orgArg.myRole || 'member'}</idp-badge>`,
|
|
2520
|
+
orgArg.id,
|
|
2521
|
+
],
|
|
2522
|
+
}));
|
|
2523
|
+
return html `
|
|
2524
|
+
${this.renderPageHeader('All Organisations', `${this.orgs.length} organisations visible to this admin session`)}
|
|
2525
|
+
<div class="body wide-body">
|
|
2526
|
+
<idp-data-table
|
|
2527
|
+
title="Organisations"
|
|
2528
|
+
badge=${`${this.orgs.length} total`}
|
|
2529
|
+
empty-title="No organisations"
|
|
2530
|
+
empty-description="No organisations are visible to this admin session."
|
|
2531
|
+
.columns=${[
|
|
2532
|
+
{ label: 'Organisation' },
|
|
2533
|
+
{ label: 'Slug', mono: true, hideBelow: 'mobile' },
|
|
2534
|
+
{ label: 'Role' },
|
|
2535
|
+
{ label: 'Identifier', mono: true, hideBelow: 'tablet' },
|
|
2536
|
+
]}
|
|
2537
|
+
.rows=${orgRows}
|
|
2538
|
+
></idp-data-table>
|
|
2539
|
+
</div>
|
|
2540
|
+
`;
|
|
2541
|
+
}
|
|
2542
|
+
renderGAApps() {
|
|
2543
|
+
const apps = this.adminApps.length ? this.adminApps : this.orgApps;
|
|
2544
|
+
const appRows = apps.map((appArg) => ({
|
|
2545
|
+
cells: [
|
|
2546
|
+
html `
|
|
2547
|
+
<div class="identity-cell">
|
|
2548
|
+
<span class="identity-avatar">${this.getInitials(appArg.name)}</span>
|
|
2549
|
+
<div>
|
|
2550
|
+
<div class="identity-primary">${appArg.name}</div>
|
|
2551
|
+
<div class="identity-secondary">${appArg.description || appArg.appUrl || 'Platform app'}</div>
|
|
2552
|
+
</div>
|
|
2553
|
+
</div>
|
|
2554
|
+
`,
|
|
2555
|
+
html `<idp-badge variant=${appArg.type === 'global' ? 'accent' : 'outline'}>${appArg.type || 'global'}</idp-badge>`,
|
|
2556
|
+
appArg.category || '-',
|
|
2557
|
+
appArg.connectionCount ?? '-',
|
|
2558
|
+
html `<idp-badge variant=${appArg.status === 'suspended' ? 'error' : appArg.status === 'pending_review' ? 'warn' : 'ok'}>${appArg.status || 'active'}</idp-badge>`,
|
|
2559
|
+
],
|
|
2560
|
+
}));
|
|
2561
|
+
return html `
|
|
2562
|
+
${this.renderPageHeader('Platform Apps', 'Global and partner apps across the platform.')}
|
|
2563
|
+
<div class="body wide-body">
|
|
2564
|
+
<idp-data-table
|
|
2565
|
+
title="Platform apps"
|
|
2566
|
+
badge=${`${apps.length} total`}
|
|
2567
|
+
empty-title="No platform apps"
|
|
2568
|
+
empty-description="Global app administration data is not available for this session."
|
|
2569
|
+
.columns=${[
|
|
2570
|
+
{ label: 'App' },
|
|
2571
|
+
{ label: 'Type' },
|
|
2572
|
+
{ label: 'Category', hideBelow: 'mobile' },
|
|
2573
|
+
{ label: 'Connections', align: 'right', mono: true, hideBelow: 'mobile' },
|
|
2574
|
+
{ label: 'Status' },
|
|
2575
|
+
]}
|
|
2576
|
+
.rows=${appRows}
|
|
2577
|
+
></idp-data-table>
|
|
2578
|
+
</div>
|
|
2579
|
+
`;
|
|
2580
|
+
}
|
|
2581
|
+
renderMainContent() {
|
|
2582
|
+
const renderers = {
|
|
2583
|
+
overview: () => this.renderOverview(),
|
|
2584
|
+
profile: () => this.renderProfile(),
|
|
2585
|
+
security: () => this.renderSecurity(),
|
|
2586
|
+
sessions: () => this.renderSessions(),
|
|
2587
|
+
apps: () => this.renderAccountApps(),
|
|
2588
|
+
'org-general': () => this.renderOrgGeneral(),
|
|
2589
|
+
'org-settings': () => this.renderOrgSettings(),
|
|
2590
|
+
'org-members': () => this.renderOrgMembers(),
|
|
2591
|
+
'org-apps': () => this.renderOrgApps(),
|
|
2592
|
+
support: () => this.renderSupport(),
|
|
2593
|
+
'ga-users': () => this.renderGAUsers(),
|
|
2594
|
+
'ga-orgs': () => this.renderGAOrgs(),
|
|
2595
|
+
'ga-apps': () => this.renderGAApps(),
|
|
2596
|
+
};
|
|
2597
|
+
return (renderers[this.page] || renderers.overview)();
|
|
2598
|
+
}
|
|
2599
|
+
render() {
|
|
2600
|
+
return html `
|
|
2601
|
+
<div class="shell">
|
|
2602
|
+
${this.renderSidebar()}
|
|
2603
|
+
<main>${this.renderMainContent()}</main>
|
|
2604
|
+
</div>
|
|
2605
|
+
${this.renderDialog()}
|
|
2606
|
+
`;
|
|
2607
|
+
}
|
|
2608
|
+
static {
|
|
2609
|
+
__runInitializers(_classThis, _classExtraInitializers);
|
|
2610
|
+
}
|
|
2611
|
+
};
|
|
2612
|
+
return IdpAdminShell = _classThis;
|
|
2613
|
+
})();
|
|
2614
|
+
export { IdpAdminShell };
|
|
2615
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaWRwLWFkbWluLXNoZWxsLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vdHNfd2ViL2VsZW1lbnRzL2lkcC1hZG1pbi1zaGVsbC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsT0FBTyxFQUFFLFdBQVcsRUFBRSxJQUFJLEVBQUUsUUFBUSxFQUFFLEtBQUssRUFBRSxhQUFhLEVBQUUsR0FBRyxFQUF1QixNQUFNLDZCQUE2QixDQUFDO0FBQzFILE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLGFBQWEsQ0FBQztBQUMvQyxPQUFPLGdCQUFnQixDQUFDO0FBQ3hCLE9BQU8sZUFBZSxDQUFDO0FBQ3ZCLE9BQU8scUJBQXFCLENBQUM7SUE0T2hCLGFBQWE7NEJBRHpCLGFBQWEsQ0FBQyxpQkFBaUIsQ0FBQzs7OztzQkFDRSxXQUFXOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OzZCQUFuQixTQUFRLFdBQVc7Ozs7Z0NBbTdCM0MsUUFBUSxDQUFDLEVBQUUsSUFBSSxFQUFFLE1BQU0sRUFBRSxDQUFDO2dDQUcxQixRQUFRLENBQUMsRUFBRSxJQUFJLEVBQUUsTUFBTSxFQUFFLENBQUM7Z0NBTTFCLFFBQVEsQ0FBQyxFQUFFLElBQUksRUFBRSxLQUFLLEVBQUUsQ0FBQzt5Q0FHekIsUUFBUSxDQUFDLEVBQUUsSUFBSSxFQUFFLE1BQU0sRUFBRSxTQUFTLEVBQUUsaUJBQWlCLEVBQUUsQ0FBQzt1Q0FHeEQsUUFBUSxDQUFDLEVBQUUsSUFBSSxFQUFFLE9BQU8sRUFBRSxTQUFTLEVBQUUsY0FBYyxFQUFFLE9BQU8sRUFBRSxJQUFJLEVBQUUsQ0FBQzt1Q0FHckUsUUFBUSxDQUFDLEVBQUUsSUFBSSxFQUFF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WUFDckIsR0FBRyxnQkFBZ0I7WUFDbkIsR0FBRyxDQUFBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7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
|