@memberjunction/ng-dashboards 2.128.0 → 2.129.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/AI/components/agents/agent-configuration.component.d.ts +34 -1
- package/dist/AI/components/agents/agent-configuration.component.d.ts.map +1 -1
- package/dist/AI/components/agents/agent-configuration.component.js +419 -109
- package/dist/AI/components/agents/agent-configuration.component.js.map +1 -1
- package/dist/AI/components/agents/agent-editor.component.d.ts +1 -1
- package/dist/AI/components/agents/agent-editor.component.d.ts.map +1 -1
- package/dist/AI/components/agents/agent-filter-panel.component.d.ts +1 -1
- package/dist/AI/components/agents/agent-filter-panel.component.d.ts.map +1 -1
- package/dist/AI/components/agents/agent-filter-panel.component.js +3 -3
- package/dist/AI/components/agents/agent-filter-panel.component.js.map +1 -1
- package/dist/AI/components/execution-monitoring.component.d.ts +1 -1
- package/dist/AI/components/execution-monitoring.component.d.ts.map +1 -1
- package/dist/AI/components/execution-monitoring.component.js +3 -3
- package/dist/AI/components/execution-monitoring.component.js.map +1 -1
- package/dist/AI/components/models/{model-management-v2.component.d.ts → model-management.component.d.ts} +21 -5
- package/dist/AI/components/models/model-management.component.d.ts.map +1 -0
- package/dist/AI/components/models/model-management.component.js +1283 -0
- package/dist/AI/components/models/model-management.component.js.map +1 -0
- package/dist/AI/components/prompts/model-prompt-priority-matrix.component.d.ts +2 -1
- package/dist/AI/components/prompts/model-prompt-priority-matrix.component.d.ts.map +1 -1
- package/dist/AI/components/prompts/prompt-filter-panel.component.js +2 -2
- package/dist/AI/components/prompts/{prompt-management-v2.component.d.ts → prompt-management.component.d.ts} +30 -5
- package/dist/AI/components/prompts/prompt-management.component.d.ts.map +1 -0
- package/dist/AI/components/prompts/prompt-management.component.js +1079 -0
- package/dist/AI/components/prompts/prompt-management.component.js.map +1 -0
- package/dist/AI/components/prompts/prompt-version-control.component.d.ts +2 -1
- package/dist/AI/components/prompts/prompt-version-control.component.d.ts.map +1 -1
- package/dist/AI/components/prompts/prompt-version-control.component.js +1 -1
- package/dist/AI/components/prompts/prompt-version-control.component.js.map +1 -1
- package/dist/AI/components/system/system-config-filter-panel.component.js +2 -2
- package/dist/AI/components/system/system-configuration.component.d.ts +55 -11
- package/dist/AI/components/system/system-configuration.component.d.ts.map +1 -1
- package/dist/AI/components/system/system-configuration.component.js +790 -131
- package/dist/AI/components/system/system-configuration.component.js.map +1 -1
- package/dist/AI/components/widgets/kpi-card.component.d.ts.map +1 -1
- package/dist/AI/components/widgets/kpi-card.component.js +3 -3
- package/dist/AI/components/widgets/kpi-card.component.js.map +1 -1
- package/dist/AI/index.d.ts +2 -2
- package/dist/AI/index.d.ts.map +1 -1
- package/dist/AI/index.js +2 -2
- package/dist/AI/index.js.map +1 -1
- package/dist/AI/services/ai-instrumentation.service.d.ts +5 -6
- package/dist/AI/services/ai-instrumentation.service.d.ts.map +1 -1
- package/dist/AI/services/ai-instrumentation.service.js.map +1 -1
- package/dist/Communication/communication-dashboard.component.d.ts +2 -0
- package/dist/Communication/communication-dashboard.component.d.ts.map +1 -1
- package/dist/Communication/communication-dashboard.component.js +5 -2
- package/dist/Communication/communication-dashboard.component.js.map +1 -1
- package/dist/ComponentStudio/component-studio-dashboard.component.d.ts +3 -2
- package/dist/ComponentStudio/component-studio-dashboard.component.d.ts.map +1 -1
- package/dist/ComponentStudio/component-studio-dashboard.component.js +7 -3
- package/dist/ComponentStudio/component-studio-dashboard.component.js.map +1 -1
- package/dist/Credentials/components/credential-category-edit-panel.component.d.ts +44 -0
- package/dist/Credentials/components/credential-category-edit-panel.component.d.ts.map +1 -0
- package/dist/Credentials/components/credential-category-edit-panel.component.js +456 -0
- package/dist/Credentials/components/credential-category-edit-panel.component.js.map +1 -0
- package/dist/Credentials/components/credential-edit-panel.component.d.ts +70 -0
- package/dist/Credentials/components/credential-edit-panel.component.d.ts.map +1 -0
- package/dist/Credentials/components/credential-edit-panel.component.js +694 -0
- package/dist/Credentials/components/credential-edit-panel.component.js.map +1 -0
- package/dist/Credentials/components/credential-type-edit-panel.component.d.ts +56 -0
- package/dist/Credentials/components/credential-type-edit-panel.component.d.ts.map +1 -0
- package/dist/Credentials/components/credential-type-edit-panel.component.js +563 -0
- package/dist/Credentials/components/credential-type-edit-panel.component.js.map +1 -0
- package/dist/Credentials/components/credentials-audit-resource.component.d.ts +81 -0
- package/dist/Credentials/components/credentials-audit-resource.component.d.ts.map +1 -0
- package/dist/Credentials/components/credentials-audit-resource.component.js +864 -0
- package/dist/Credentials/components/credentials-audit-resource.component.js.map +1 -0
- package/dist/Credentials/components/credentials-categories-resource.component.d.ts +61 -0
- package/dist/Credentials/components/credentials-categories-resource.component.d.ts.map +1 -0
- package/dist/Credentials/components/credentials-categories-resource.component.js +816 -0
- package/dist/Credentials/components/credentials-categories-resource.component.js.map +1 -0
- package/dist/Credentials/components/credentials-list-resource.component.d.ts +83 -0
- package/dist/Credentials/components/credentials-list-resource.component.d.ts.map +1 -0
- package/dist/Credentials/components/credentials-list-resource.component.js +1253 -0
- package/dist/Credentials/components/credentials-list-resource.component.js.map +1 -0
- package/dist/Credentials/components/credentials-overview-resource.component.d.ts +99 -0
- package/dist/Credentials/components/credentials-overview-resource.component.d.ts.map +1 -0
- package/dist/Credentials/components/credentials-overview-resource.component.js +936 -0
- package/dist/Credentials/components/credentials-overview-resource.component.js.map +1 -0
- package/dist/Credentials/components/credentials-types-resource.component.d.ts +70 -0
- package/dist/Credentials/components/credentials-types-resource.component.d.ts.map +1 -0
- package/dist/Credentials/components/credentials-types-resource.component.js +868 -0
- package/dist/Credentials/components/credentials-types-resource.component.js.map +1 -0
- package/dist/Credentials/credentials-dashboard.component.d.ts +37 -0
- package/dist/Credentials/credentials-dashboard.component.d.ts.map +1 -0
- package/dist/Credentials/credentials-dashboard.component.js +290 -0
- package/dist/Credentials/credentials-dashboard.component.js.map +1 -0
- package/dist/Credentials/index.d.ts +7 -0
- package/dist/Credentials/index.d.ts.map +1 -0
- package/dist/Credentials/index.js +9 -0
- package/dist/Credentials/index.js.map +1 -0
- package/dist/Credentials/pipes/group-by.pipe.d.ts +13 -0
- package/dist/Credentials/pipes/group-by.pipe.d.ts.map +1 -0
- package/dist/Credentials/pipes/group-by.pipe.js +29 -0
- package/dist/Credentials/pipes/group-by.pipe.js.map +1 -0
- package/dist/DataExplorer/components/navigation-panel/navigation-panel.component.d.ts +2 -2
- package/dist/DataExplorer/data-explorer-dashboard.component.d.ts +2 -0
- package/dist/DataExplorer/data-explorer-dashboard.component.d.ts.map +1 -1
- package/dist/DataExplorer/data-explorer-dashboard.component.js +5 -0
- package/dist/DataExplorer/data-explorer-dashboard.component.js.map +1 -1
- package/dist/DataExplorer/services/explorer-state.service.d.ts +5 -5
- package/dist/DataExplorer/services/explorer-state.service.d.ts.map +1 -1
- package/dist/DataExplorer/services/explorer-state.service.js +125 -151
- package/dist/DataExplorer/services/explorer-state.service.js.map +1 -1
- package/dist/EntityAdmin/entity-admin-dashboard.component.d.ts +15 -19
- package/dist/EntityAdmin/entity-admin-dashboard.component.d.ts.map +1 -1
- package/dist/EntityAdmin/entity-admin-dashboard.component.js +70 -26
- package/dist/EntityAdmin/entity-admin-dashboard.component.js.map +1 -1
- package/dist/Home/home-dashboard.component.d.ts +6 -5
- package/dist/Home/home-dashboard.component.d.ts.map +1 -1
- package/dist/Home/home-dashboard.component.js +174 -166
- package/dist/Home/home-dashboard.component.js.map +1 -1
- package/dist/Scheduling/scheduling-dashboard.component.d.ts +2 -0
- package/dist/Scheduling/scheduling-dashboard.component.d.ts.map +1 -1
- package/dist/Scheduling/scheduling-dashboard.component.js +5 -2
- package/dist/Scheduling/scheduling-dashboard.component.js.map +1 -1
- package/dist/Scheduling/services/scheduling-instrumentation.service.d.ts.map +1 -1
- package/dist/Scheduling/services/scheduling-instrumentation.service.js +4 -2
- package/dist/Scheduling/services/scheduling-instrumentation.service.js.map +1 -1
- package/dist/SystemDiagnostics/index.d.ts +2 -0
- package/dist/SystemDiagnostics/index.d.ts.map +1 -0
- package/dist/SystemDiagnostics/index.js +3 -0
- package/dist/SystemDiagnostics/index.js.map +1 -0
- package/dist/SystemDiagnostics/system-diagnostics.component.d.ts +497 -0
- package/dist/SystemDiagnostics/system-diagnostics.component.d.ts.map +1 -0
- package/dist/SystemDiagnostics/system-diagnostics.component.js +6063 -0
- package/dist/SystemDiagnostics/system-diagnostics.component.js.map +1 -0
- package/dist/Testing/testing-dashboard.component.d.ts +2 -0
- package/dist/Testing/testing-dashboard.component.d.ts.map +1 -1
- package/dist/Testing/testing-dashboard.component.js +5 -2
- package/dist/Testing/testing-dashboard.component.js.map +1 -1
- package/dist/module.d.ts +103 -95
- package/dist/module.d.ts.map +1 -1
- package/dist/module.js +90 -29
- package/dist/module.js.map +1 -1
- package/dist/public-api.d.ts +3 -1
- package/dist/public-api.d.ts.map +1 -1
- package/dist/public-api.js +21 -1
- package/dist/public-api.js.map +1 -1
- package/package.json +28 -25
- package/dist/AI/components/models/model-management-v2.component.d.ts.map +0 -1
- package/dist/AI/components/models/model-management-v2.component.js +0 -981
- package/dist/AI/components/models/model-management-v2.component.js.map +0 -1
- package/dist/AI/components/prompts/prompt-management-v2.component.d.ts.map +0 -1
- package/dist/AI/components/prompts/prompt-management-v2.component.js +0 -811
- package/dist/AI/components/prompts/prompt-management-v2.component.js.map +0 -1
- package/dist/EntityAdmin/components/entity-details.component.d.ts +0 -50
- package/dist/EntityAdmin/components/entity-details.component.d.ts.map +0 -1
- package/dist/EntityAdmin/components/entity-details.component.js +0 -680
- package/dist/EntityAdmin/components/entity-details.component.js.map +0 -1
- package/dist/EntityAdmin/components/entity-filter-panel.component.d.ts +0 -31
- package/dist/EntityAdmin/components/entity-filter-panel.component.d.ts.map +0 -1
- package/dist/EntityAdmin/components/entity-filter-panel.component.js +0 -160
- package/dist/EntityAdmin/components/entity-filter-panel.component.js.map +0 -1
- package/dist/EntityAdmin/components/erd-composite.component.d.ts +0 -73
- package/dist/EntityAdmin/components/erd-composite.component.d.ts.map +0 -1
- package/dist/EntityAdmin/components/erd-composite.component.js +0 -271
- package/dist/EntityAdmin/components/erd-composite.component.js.map +0 -1
- package/dist/EntityAdmin/components/erd-diagram.component.d.ts +0 -47
- package/dist/EntityAdmin/components/erd-diagram.component.d.ts.map +0 -1
- package/dist/EntityAdmin/components/erd-diagram.component.js +0 -618
- package/dist/EntityAdmin/components/erd-diagram.component.js.map +0 -1
|
@@ -0,0 +1,936 @@
|
|
|
1
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
2
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
3
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
4
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
|
+
};
|
|
7
|
+
import { Component, ChangeDetectionStrategy } from '@angular/core';
|
|
8
|
+
import { Subject } from 'rxjs';
|
|
9
|
+
import { RegisterClass } from '@memberjunction/global';
|
|
10
|
+
import { BaseResourceComponent } from '@memberjunction/ng-shared';
|
|
11
|
+
import { RunView, Metadata, CompositeKey } from '@memberjunction/core';
|
|
12
|
+
import * as i0 from "@angular/core";
|
|
13
|
+
import * as i1 from "@memberjunction/ng-shared";
|
|
14
|
+
import * as i2 from "@angular/common";
|
|
15
|
+
import * as i3 from "@memberjunction/ng-shared-generic";
|
|
16
|
+
function CredentialsOverviewResourceComponent_mj_loading_1_Template(rf, ctx) { if (rf & 1) {
|
|
17
|
+
i0.ɵɵelement(0, "mj-loading", 3);
|
|
18
|
+
} }
|
|
19
|
+
function CredentialsOverviewResourceComponent_ng_container_2_button_10_Template(rf, ctx) { if (rf & 1) {
|
|
20
|
+
const _r3 = i0.ɵɵgetCurrentView();
|
|
21
|
+
i0.ɵɵelementStart(0, "button", 62);
|
|
22
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_button_10_Template_button_click_0_listener() { i0.ɵɵrestoreView(_r3); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.createNewCredential()); });
|
|
23
|
+
i0.ɵɵelement(1, "i", 63);
|
|
24
|
+
i0.ɵɵelementStart(2, "span");
|
|
25
|
+
i0.ɵɵtext(3, "New Credential");
|
|
26
|
+
i0.ɵɵelementEnd()();
|
|
27
|
+
} }
|
|
28
|
+
function CredentialsOverviewResourceComponent_ng_container_2_span_23_Template(rf, ctx) { if (rf & 1) {
|
|
29
|
+
i0.ɵɵelementStart(0, "span", 64);
|
|
30
|
+
i0.ɵɵelement(1, "i", 65);
|
|
31
|
+
i0.ɵɵtext(2);
|
|
32
|
+
i0.ɵɵelementEnd();
|
|
33
|
+
} if (rf & 2) {
|
|
34
|
+
const ctx_r1 = i0.ɵɵnextContext(2);
|
|
35
|
+
i0.ɵɵadvance(2);
|
|
36
|
+
i0.ɵɵtextInterpolate1(" ", ctx_r1.expiredCredentials, " expired ");
|
|
37
|
+
} }
|
|
38
|
+
function CredentialsOverviewResourceComponent_ng_container_2_span_24_Template(rf, ctx) { if (rf & 1) {
|
|
39
|
+
const _r4 = i0.ɵɵgetCurrentView();
|
|
40
|
+
i0.ɵɵelementStart(0, "span", 66);
|
|
41
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_span_24_Template_span_click_0_listener() { i0.ɵɵrestoreView(_r4); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.viewExpiringCredentials()); });
|
|
42
|
+
i0.ɵɵelement(1, "i", 40);
|
|
43
|
+
i0.ɵɵtext(2);
|
|
44
|
+
i0.ɵɵelementEnd();
|
|
45
|
+
} if (rf & 2) {
|
|
46
|
+
const ctx_r1 = i0.ɵɵnextContext(2);
|
|
47
|
+
i0.ɵɵadvance(2);
|
|
48
|
+
i0.ɵɵtextInterpolate1(" ", ctx_r1.expiringSoonCount, " expiring soon ");
|
|
49
|
+
} }
|
|
50
|
+
function CredentialsOverviewResourceComponent_ng_container_2_span_25_Template(rf, ctx) { if (rf & 1) {
|
|
51
|
+
i0.ɵɵelementStart(0, "span", 67);
|
|
52
|
+
i0.ɵɵelement(1, "i", 35);
|
|
53
|
+
i0.ɵɵtext(2, " All credentials healthy ");
|
|
54
|
+
i0.ɵɵelementEnd();
|
|
55
|
+
} }
|
|
56
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_64_Template(rf, ctx) { if (rf & 1) {
|
|
57
|
+
i0.ɵɵelementStart(0, "div", 68);
|
|
58
|
+
i0.ɵɵelement(1, "i", 33);
|
|
59
|
+
i0.ɵɵelementEnd();
|
|
60
|
+
} }
|
|
61
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_83__svg_ng_container_4_Template(rf, ctx) { if (rf & 1) {
|
|
62
|
+
const _r5 = i0.ɵɵgetCurrentView();
|
|
63
|
+
i0.ɵɵnamespaceSVG();
|
|
64
|
+
i0.ɵɵelementContainerStart(0);
|
|
65
|
+
i0.ɵɵelementStart(1, "circle", 79);
|
|
66
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_83__svg_ng_container_4_Template_circle_click_1_listener() { const stat_r6 = i0.ɵɵrestoreView(_r5).$implicit; const ctx_r1 = i0.ɵɵnextContext(3); return i0.ɵɵresetView(ctx_r1.onCategoryClick(stat_r6)); });
|
|
67
|
+
i0.ɵɵelementEnd();
|
|
68
|
+
i0.ɵɵelementContainerEnd();
|
|
69
|
+
} if (rf & 2) {
|
|
70
|
+
const stat_r6 = ctx.$implicit;
|
|
71
|
+
const i_r7 = ctx.index;
|
|
72
|
+
const ctx_r1 = i0.ɵɵnextContext(3);
|
|
73
|
+
i0.ɵɵadvance();
|
|
74
|
+
i0.ɵɵattribute("stroke", stat_r6.color)("stroke-dasharray", stat_r6.percentage * 2.51 + " " + (251 - stat_r6.percentage * 2.51))("stroke-dashoffset", ctx_r1.getDonutOffset(i_r7));
|
|
75
|
+
} }
|
|
76
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_83_div_11_Template(rf, ctx) { if (rf & 1) {
|
|
77
|
+
const _r8 = i0.ɵɵgetCurrentView();
|
|
78
|
+
i0.ɵɵelementStart(0, "div", 80);
|
|
79
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_83_div_11_Template_div_click_0_listener() { const stat_r9 = i0.ɵɵrestoreView(_r8).$implicit; const ctx_r1 = i0.ɵɵnextContext(3); return i0.ɵɵresetView(ctx_r1.onCategoryClick(stat_r9)); });
|
|
80
|
+
i0.ɵɵelement(1, "div", 81);
|
|
81
|
+
i0.ɵɵelementStart(2, "div", 82)(3, "div", 83);
|
|
82
|
+
i0.ɵɵelement(4, "i");
|
|
83
|
+
i0.ɵɵtext(5);
|
|
84
|
+
i0.ɵɵelementEnd();
|
|
85
|
+
i0.ɵɵelementStart(6, "div", 84);
|
|
86
|
+
i0.ɵɵtext(7);
|
|
87
|
+
i0.ɵɵelementEnd()();
|
|
88
|
+
i0.ɵɵelement(8, "i", 85);
|
|
89
|
+
i0.ɵɵelementEnd();
|
|
90
|
+
} if (rf & 2) {
|
|
91
|
+
const stat_r9 = ctx.$implicit;
|
|
92
|
+
i0.ɵɵadvance();
|
|
93
|
+
i0.ɵɵstyleProp("background-color", stat_r9.color);
|
|
94
|
+
i0.ɵɵadvance(3);
|
|
95
|
+
i0.ɵɵclassMap(stat_r9.iconClass);
|
|
96
|
+
i0.ɵɵadvance();
|
|
97
|
+
i0.ɵɵtextInterpolate1(" ", stat_r9.category, " ");
|
|
98
|
+
i0.ɵɵadvance(2);
|
|
99
|
+
i0.ɵɵtextInterpolate2("", stat_r9.count, " (", stat_r9.percentage, "%)");
|
|
100
|
+
} }
|
|
101
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_83_Template(rf, ctx) { if (rf & 1) {
|
|
102
|
+
i0.ɵɵelementStart(0, "div", 69)(1, "div", 70);
|
|
103
|
+
i0.ɵɵnamespaceSVG();
|
|
104
|
+
i0.ɵɵelementStart(2, "svg", 71);
|
|
105
|
+
i0.ɵɵelement(3, "circle", 72);
|
|
106
|
+
i0.ɵɵtemplate(4, CredentialsOverviewResourceComponent_ng_container_2_div_83__svg_ng_container_4_Template, 2, 3, "ng-container", 73);
|
|
107
|
+
i0.ɵɵelementEnd();
|
|
108
|
+
i0.ɵɵnamespaceHTML();
|
|
109
|
+
i0.ɵɵelementStart(5, "div", 74)(6, "div", 75);
|
|
110
|
+
i0.ɵɵtext(7);
|
|
111
|
+
i0.ɵɵelementEnd();
|
|
112
|
+
i0.ɵɵelementStart(8, "div", 76);
|
|
113
|
+
i0.ɵɵtext(9, "Total");
|
|
114
|
+
i0.ɵɵelementEnd()()();
|
|
115
|
+
i0.ɵɵelementStart(10, "div", 77);
|
|
116
|
+
i0.ɵɵtemplate(11, CredentialsOverviewResourceComponent_ng_container_2_div_83_div_11_Template, 9, 7, "div", 78);
|
|
117
|
+
i0.ɵɵelementEnd()();
|
|
118
|
+
} if (rf & 2) {
|
|
119
|
+
const ctx_r1 = i0.ɵɵnextContext(2);
|
|
120
|
+
i0.ɵɵadvance(4);
|
|
121
|
+
i0.ɵɵproperty("ngForOf", ctx_r1.categoryStats);
|
|
122
|
+
i0.ɵɵadvance(3);
|
|
123
|
+
i0.ɵɵtextInterpolate(ctx_r1.totalCredentials);
|
|
124
|
+
i0.ɵɵadvance(4);
|
|
125
|
+
i0.ɵɵproperty("ngForOf", ctx_r1.categoryStats);
|
|
126
|
+
} }
|
|
127
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_84_Template(rf, ctx) { if (rf & 1) {
|
|
128
|
+
i0.ɵɵelementStart(0, "div", 86);
|
|
129
|
+
i0.ɵɵelement(1, "i", 87);
|
|
130
|
+
i0.ɵɵelementStart(2, "span");
|
|
131
|
+
i0.ɵɵtext(3, "No credentials configured");
|
|
132
|
+
i0.ɵɵelementEnd()();
|
|
133
|
+
} }
|
|
134
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_span_15_Template(rf, ctx) { if (rf & 1) {
|
|
135
|
+
i0.ɵɵelementStart(0, "span", 103);
|
|
136
|
+
i0.ɵɵelement(1, "i", 104);
|
|
137
|
+
i0.ɵɵtext(2);
|
|
138
|
+
i0.ɵɵelementEnd();
|
|
139
|
+
} if (rf & 2) {
|
|
140
|
+
const type_r11 = i0.ɵɵnextContext().$implicit;
|
|
141
|
+
i0.ɵɵadvance(2);
|
|
142
|
+
i0.ɵɵtextInterpolate1(" ", type_r11.activeCount, " ");
|
|
143
|
+
} }
|
|
144
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_span_16_Template(rf, ctx) { if (rf & 1) {
|
|
145
|
+
i0.ɵɵelementStart(0, "span", 105);
|
|
146
|
+
i0.ɵɵelement(1, "i", 40);
|
|
147
|
+
i0.ɵɵtext(2);
|
|
148
|
+
i0.ɵɵelementEnd();
|
|
149
|
+
} if (rf & 2) {
|
|
150
|
+
const type_r11 = i0.ɵɵnextContext().$implicit;
|
|
151
|
+
i0.ɵɵadvance(2);
|
|
152
|
+
i0.ɵɵtextInterpolate1(" ", type_r11.expiringCount, " ");
|
|
153
|
+
} }
|
|
154
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_Template(rf, ctx) { if (rf & 1) {
|
|
155
|
+
const _r10 = i0.ɵɵgetCurrentView();
|
|
156
|
+
i0.ɵɵelementStart(0, "div", 90);
|
|
157
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_Template_div_click_0_listener() { const type_r11 = i0.ɵɵrestoreView(_r10).$implicit; const ctx_r1 = i0.ɵɵnextContext(3); return i0.ɵɵresetView(ctx_r1.onTypeClick(type_r11)); });
|
|
158
|
+
i0.ɵɵelementStart(1, "div", 91)(2, "div", 92);
|
|
159
|
+
i0.ɵɵtext(3);
|
|
160
|
+
i0.ɵɵelementEnd();
|
|
161
|
+
i0.ɵɵelementStart(4, "div", 93);
|
|
162
|
+
i0.ɵɵtext(5);
|
|
163
|
+
i0.ɵɵelementEnd()();
|
|
164
|
+
i0.ɵɵelementStart(6, "div", 94)(7, "div", 95)(8, "span", 96);
|
|
165
|
+
i0.ɵɵtext(9);
|
|
166
|
+
i0.ɵɵelementEnd();
|
|
167
|
+
i0.ɵɵelementStart(10, "span", 97);
|
|
168
|
+
i0.ɵɵtext(11, "credentials");
|
|
169
|
+
i0.ɵɵelementEnd()();
|
|
170
|
+
i0.ɵɵelementStart(12, "div", 98);
|
|
171
|
+
i0.ɵɵelement(13, "div", 99);
|
|
172
|
+
i0.ɵɵelementEnd();
|
|
173
|
+
i0.ɵɵelementStart(14, "div", 100);
|
|
174
|
+
i0.ɵɵtemplate(15, CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_span_15_Template, 3, 1, "span", 101)(16, CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_span_16_Template, 3, 1, "span", 102);
|
|
175
|
+
i0.ɵɵelementEnd()()();
|
|
176
|
+
} if (rf & 2) {
|
|
177
|
+
const type_r11 = ctx.$implicit;
|
|
178
|
+
const ctx_r1 = i0.ɵɵnextContext(3);
|
|
179
|
+
i0.ɵɵadvance(3);
|
|
180
|
+
i0.ɵɵtextInterpolate(type_r11.typeName);
|
|
181
|
+
i0.ɵɵadvance(2);
|
|
182
|
+
i0.ɵɵtextInterpolate(type_r11.category);
|
|
183
|
+
i0.ɵɵadvance(4);
|
|
184
|
+
i0.ɵɵtextInterpolate(type_r11.credentialCount);
|
|
185
|
+
i0.ɵɵadvance(4);
|
|
186
|
+
i0.ɵɵstyleProp("width", ctx_r1.totalCredentials > 0 ? type_r11.credentialCount / ctx_r1.totalCredentials * 100 : 0, "%");
|
|
187
|
+
i0.ɵɵadvance(2);
|
|
188
|
+
i0.ɵɵproperty("ngIf", type_r11.activeCount > 0);
|
|
189
|
+
i0.ɵɵadvance();
|
|
190
|
+
i0.ɵɵproperty("ngIf", type_r11.expiringCount > 0);
|
|
191
|
+
} }
|
|
192
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_95_Template(rf, ctx) { if (rf & 1) {
|
|
193
|
+
i0.ɵɵelementStart(0, "div", 88);
|
|
194
|
+
i0.ɵɵtemplate(1, CredentialsOverviewResourceComponent_ng_container_2_div_95_div_1_Template, 17, 7, "div", 89);
|
|
195
|
+
i0.ɵɵelementEnd();
|
|
196
|
+
} if (rf & 2) {
|
|
197
|
+
const ctx_r1 = i0.ɵɵnextContext(2);
|
|
198
|
+
i0.ɵɵadvance();
|
|
199
|
+
i0.ɵɵproperty("ngForOf", ctx_r1.typeStats.slice(0, 6));
|
|
200
|
+
} }
|
|
201
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_96_Template(rf, ctx) { if (rf & 1) {
|
|
202
|
+
i0.ɵɵelementStart(0, "div", 86);
|
|
203
|
+
i0.ɵɵelement(1, "i", 106);
|
|
204
|
+
i0.ɵɵelementStart(2, "span");
|
|
205
|
+
i0.ɵɵtext(3, "No credential types configured");
|
|
206
|
+
i0.ɵɵelementEnd()();
|
|
207
|
+
} }
|
|
208
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_107_div_1_span_11_Template(rf, ctx) { if (rf & 1) {
|
|
209
|
+
i0.ɵɵelementStart(0, "span", 118);
|
|
210
|
+
i0.ɵɵtext(1);
|
|
211
|
+
i0.ɵɵelementEnd();
|
|
212
|
+
} if (rf & 2) {
|
|
213
|
+
const activity_r13 = i0.ɵɵnextContext().$implicit;
|
|
214
|
+
i0.ɵɵadvance();
|
|
215
|
+
i0.ɵɵtextInterpolate1("by ", activity_r13.user, "");
|
|
216
|
+
} }
|
|
217
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_107_div_1_Template(rf, ctx) { if (rf & 1) {
|
|
218
|
+
const _r12 = i0.ɵɵgetCurrentView();
|
|
219
|
+
i0.ɵɵelementStart(0, "div", 109);
|
|
220
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_107_div_1_Template_div_click_0_listener() { const activity_r13 = i0.ɵɵrestoreView(_r12).$implicit; const ctx_r1 = i0.ɵɵnextContext(3); return i0.ɵɵresetView(ctx_r1.onActivityClick(activity_r13)); });
|
|
221
|
+
i0.ɵɵelementStart(1, "div", 110);
|
|
222
|
+
i0.ɵɵelement(2, "i");
|
|
223
|
+
i0.ɵɵelementEnd();
|
|
224
|
+
i0.ɵɵelementStart(3, "div", 111)(4, "div", 112);
|
|
225
|
+
i0.ɵɵtext(5);
|
|
226
|
+
i0.ɵɵelementEnd();
|
|
227
|
+
i0.ɵɵelementStart(6, "div", 113)(7, "span", 114);
|
|
228
|
+
i0.ɵɵtext(8);
|
|
229
|
+
i0.ɵɵelementEnd();
|
|
230
|
+
i0.ɵɵelementStart(9, "span", 115);
|
|
231
|
+
i0.ɵɵtext(10);
|
|
232
|
+
i0.ɵɵelementEnd();
|
|
233
|
+
i0.ɵɵtemplate(11, CredentialsOverviewResourceComponent_ng_container_2_div_107_div_1_span_11_Template, 2, 1, "span", 116);
|
|
234
|
+
i0.ɵɵelementEnd()();
|
|
235
|
+
i0.ɵɵelementStart(12, "div", 117);
|
|
236
|
+
i0.ɵɵtext(13);
|
|
237
|
+
i0.ɵɵelementEnd()();
|
|
238
|
+
} if (rf & 2) {
|
|
239
|
+
const activity_r13 = ctx.$implicit;
|
|
240
|
+
const ctx_r1 = i0.ɵɵnextContext(3);
|
|
241
|
+
i0.ɵɵadvance();
|
|
242
|
+
i0.ɵɵproperty("ngClass", ctx_r1.getActionClass(activity_r13.action));
|
|
243
|
+
i0.ɵɵadvance();
|
|
244
|
+
i0.ɵɵclassMap(ctx_r1.getActionIcon(activity_r13.action));
|
|
245
|
+
i0.ɵɵadvance(3);
|
|
246
|
+
i0.ɵɵtextInterpolate(activity_r13.credentialName);
|
|
247
|
+
i0.ɵɵadvance(3);
|
|
248
|
+
i0.ɵɵtextInterpolate(activity_r13.typeName);
|
|
249
|
+
i0.ɵɵadvance(2);
|
|
250
|
+
i0.ɵɵtextInterpolate(activity_r13.action);
|
|
251
|
+
i0.ɵɵadvance();
|
|
252
|
+
i0.ɵɵproperty("ngIf", activity_r13.user);
|
|
253
|
+
i0.ɵɵadvance(2);
|
|
254
|
+
i0.ɵɵtextInterpolate1(" ", ctx_r1.formatDate(activity_r13.date), " ");
|
|
255
|
+
} }
|
|
256
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_107_Template(rf, ctx) { if (rf & 1) {
|
|
257
|
+
i0.ɵɵelementStart(0, "div", 107);
|
|
258
|
+
i0.ɵɵtemplate(1, CredentialsOverviewResourceComponent_ng_container_2_div_107_div_1_Template, 14, 8, "div", 108);
|
|
259
|
+
i0.ɵɵelementEnd();
|
|
260
|
+
} if (rf & 2) {
|
|
261
|
+
const ctx_r1 = i0.ɵɵnextContext(2);
|
|
262
|
+
i0.ɵɵadvance();
|
|
263
|
+
i0.ɵɵproperty("ngForOf", ctx_r1.recentActivity);
|
|
264
|
+
} }
|
|
265
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_108_Template(rf, ctx) { if (rf & 1) {
|
|
266
|
+
i0.ɵɵelementStart(0, "div", 86);
|
|
267
|
+
i0.ɵɵelement(1, "i", 119);
|
|
268
|
+
i0.ɵɵelementStart(2, "span");
|
|
269
|
+
i0.ɵɵtext(3, "No recent activity");
|
|
270
|
+
i0.ɵɵelementEnd()();
|
|
271
|
+
} }
|
|
272
|
+
function CredentialsOverviewResourceComponent_ng_container_2_div_109_Template(rf, ctx) { if (rf & 1) {
|
|
273
|
+
const _r14 = i0.ɵɵgetCurrentView();
|
|
274
|
+
i0.ɵɵelementStart(0, "div", 120)(1, "div", 121);
|
|
275
|
+
i0.ɵɵtext(2, "Quick Actions");
|
|
276
|
+
i0.ɵɵelementEnd();
|
|
277
|
+
i0.ɵɵelementStart(3, "div", 122)(4, "button", 123);
|
|
278
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_109_Template_button_click_4_listener() { i0.ɵɵrestoreView(_r14); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.createNewCredential()); });
|
|
279
|
+
i0.ɵɵelement(5, "i", 63);
|
|
280
|
+
i0.ɵɵelementStart(6, "span");
|
|
281
|
+
i0.ɵɵtext(7, "Add Credential");
|
|
282
|
+
i0.ɵɵelementEnd()();
|
|
283
|
+
i0.ɵɵelementStart(8, "button", 123);
|
|
284
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_109_Template_button_click_8_listener() { i0.ɵɵrestoreView(_r14); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.viewAllTypes()); });
|
|
285
|
+
i0.ɵɵelement(9, "i", 106);
|
|
286
|
+
i0.ɵɵelementStart(10, "span");
|
|
287
|
+
i0.ɵɵtext(11, "Manage Types");
|
|
288
|
+
i0.ɵɵelementEnd()();
|
|
289
|
+
i0.ɵɵelementStart(12, "button", 123);
|
|
290
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_109_Template_button_click_12_listener() { i0.ɵɵrestoreView(_r14); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.viewAllCategories()); });
|
|
291
|
+
i0.ɵɵelement(13, "i", 124);
|
|
292
|
+
i0.ɵɵelementStart(14, "span");
|
|
293
|
+
i0.ɵɵtext(15, "Categories");
|
|
294
|
+
i0.ɵɵelementEnd()();
|
|
295
|
+
i0.ɵɵelementStart(16, "button", 123);
|
|
296
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_div_109_Template_button_click_16_listener() { i0.ɵɵrestoreView(_r14); const ctx_r1 = i0.ɵɵnextContext(2); return i0.ɵɵresetView(ctx_r1.viewAuditLog()); });
|
|
297
|
+
i0.ɵɵelement(17, "i", 125);
|
|
298
|
+
i0.ɵɵelementStart(18, "span");
|
|
299
|
+
i0.ɵɵtext(19, "Audit Log");
|
|
300
|
+
i0.ɵɵelementEnd()()()();
|
|
301
|
+
} }
|
|
302
|
+
function CredentialsOverviewResourceComponent_ng_container_2_Template(rf, ctx) { if (rf & 1) {
|
|
303
|
+
const _r1 = i0.ɵɵgetCurrentView();
|
|
304
|
+
i0.ɵɵelementContainerStart(0);
|
|
305
|
+
i0.ɵɵelementStart(1, "div", 4)(2, "div", 5)(3, "h2", 6);
|
|
306
|
+
i0.ɵɵtext(4, "Credential Overview");
|
|
307
|
+
i0.ɵɵelementEnd();
|
|
308
|
+
i0.ɵɵelementStart(5, "p", 7);
|
|
309
|
+
i0.ɵɵtext(6, "Monitor and manage your organization's credentials");
|
|
310
|
+
i0.ɵɵelementEnd()();
|
|
311
|
+
i0.ɵɵelementStart(7, "div", 8)(8, "button", 9);
|
|
312
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_button_click_8_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.refresh()); });
|
|
313
|
+
i0.ɵɵelement(9, "i", 10);
|
|
314
|
+
i0.ɵɵelementEnd();
|
|
315
|
+
i0.ɵɵtemplate(10, CredentialsOverviewResourceComponent_ng_container_2_button_10_Template, 4, 0, "button", 11);
|
|
316
|
+
i0.ɵɵelementEnd()();
|
|
317
|
+
i0.ɵɵelementStart(11, "div", 12)(12, "div", 13)(13, "div", 14);
|
|
318
|
+
i0.ɵɵnamespaceSVG();
|
|
319
|
+
i0.ɵɵelementStart(14, "svg", 15);
|
|
320
|
+
i0.ɵɵelement(15, "path", 16)(16, "path", 17);
|
|
321
|
+
i0.ɵɵelementEnd();
|
|
322
|
+
i0.ɵɵnamespaceHTML();
|
|
323
|
+
i0.ɵɵelementStart(17, "div", 18);
|
|
324
|
+
i0.ɵɵtext(18);
|
|
325
|
+
i0.ɵɵelementEnd()()();
|
|
326
|
+
i0.ɵɵelementStart(19, "div", 19)(20, "div", 20);
|
|
327
|
+
i0.ɵɵtext(21);
|
|
328
|
+
i0.ɵɵelementEnd();
|
|
329
|
+
i0.ɵɵelementStart(22, "div", 21);
|
|
330
|
+
i0.ɵɵtemplate(23, CredentialsOverviewResourceComponent_ng_container_2_span_23_Template, 3, 1, "span", 22)(24, CredentialsOverviewResourceComponent_ng_container_2_span_24_Template, 3, 1, "span", 23)(25, CredentialsOverviewResourceComponent_ng_container_2_span_25_Template, 3, 0, "span", 24);
|
|
331
|
+
i0.ɵɵelementEnd()()();
|
|
332
|
+
i0.ɵɵelementStart(26, "div", 25)(27, "div", 26);
|
|
333
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_div_click_27_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.viewAllCredentials()); });
|
|
334
|
+
i0.ɵɵelementStart(28, "div", 27);
|
|
335
|
+
i0.ɵɵelement(29, "i", 28);
|
|
336
|
+
i0.ɵɵelementEnd();
|
|
337
|
+
i0.ɵɵelementStart(30, "div", 29)(31, "div", 30);
|
|
338
|
+
i0.ɵɵtext(32);
|
|
339
|
+
i0.ɵɵelementEnd();
|
|
340
|
+
i0.ɵɵelementStart(33, "div", 31);
|
|
341
|
+
i0.ɵɵtext(34, "Total Credentials");
|
|
342
|
+
i0.ɵɵelementEnd()();
|
|
343
|
+
i0.ɵɵelementStart(35, "div", 32);
|
|
344
|
+
i0.ɵɵelement(36, "i", 33);
|
|
345
|
+
i0.ɵɵelementEnd()();
|
|
346
|
+
i0.ɵɵelementStart(37, "div", 34);
|
|
347
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_div_click_37_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.viewAllCredentials()); });
|
|
348
|
+
i0.ɵɵelementStart(38, "div", 27);
|
|
349
|
+
i0.ɵɵelement(39, "i", 35);
|
|
350
|
+
i0.ɵɵelementEnd();
|
|
351
|
+
i0.ɵɵelementStart(40, "div", 29)(41, "div", 30);
|
|
352
|
+
i0.ɵɵtext(42);
|
|
353
|
+
i0.ɵɵelementEnd();
|
|
354
|
+
i0.ɵɵelementStart(43, "div", 31);
|
|
355
|
+
i0.ɵɵtext(44, "Active");
|
|
356
|
+
i0.ɵɵelementEnd()();
|
|
357
|
+
i0.ɵɵelementStart(45, "div", 36)(46, "span", 37);
|
|
358
|
+
i0.ɵɵtext(47);
|
|
359
|
+
i0.ɵɵelementEnd()()();
|
|
360
|
+
i0.ɵɵelementStart(48, "div", 38)(49, "div", 27);
|
|
361
|
+
i0.ɵɵelement(50, "i", 39);
|
|
362
|
+
i0.ɵɵelementEnd();
|
|
363
|
+
i0.ɵɵelementStart(51, "div", 29)(52, "div", 30);
|
|
364
|
+
i0.ɵɵtext(53);
|
|
365
|
+
i0.ɵɵelementEnd();
|
|
366
|
+
i0.ɵɵelementStart(54, "div", 31);
|
|
367
|
+
i0.ɵɵtext(55, "Types");
|
|
368
|
+
i0.ɵɵelementEnd()()();
|
|
369
|
+
i0.ɵɵelementStart(56, "div", 26);
|
|
370
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_div_click_56_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.viewExpiringCredentials()); });
|
|
371
|
+
i0.ɵɵelementStart(57, "div", 27);
|
|
372
|
+
i0.ɵɵelement(58, "i", 40);
|
|
373
|
+
i0.ɵɵelementEnd();
|
|
374
|
+
i0.ɵɵelementStart(59, "div", 29)(60, "div", 30);
|
|
375
|
+
i0.ɵɵtext(61);
|
|
376
|
+
i0.ɵɵelementEnd();
|
|
377
|
+
i0.ɵɵelementStart(62, "div", 31);
|
|
378
|
+
i0.ɵɵtext(63, "Expiring Soon");
|
|
379
|
+
i0.ɵɵelementEnd()();
|
|
380
|
+
i0.ɵɵtemplate(64, CredentialsOverviewResourceComponent_ng_container_2_div_64_Template, 2, 0, "div", 41);
|
|
381
|
+
i0.ɵɵelementEnd();
|
|
382
|
+
i0.ɵɵelementStart(65, "div", 38)(66, "div", 27);
|
|
383
|
+
i0.ɵɵelement(67, "i", 42);
|
|
384
|
+
i0.ɵɵelementEnd();
|
|
385
|
+
i0.ɵɵelementStart(68, "div", 29)(69, "div", 30);
|
|
386
|
+
i0.ɵɵtext(70);
|
|
387
|
+
i0.ɵɵelementEnd();
|
|
388
|
+
i0.ɵɵelementStart(71, "div", 31);
|
|
389
|
+
i0.ɵɵtext(72, "Expired");
|
|
390
|
+
i0.ɵɵelementEnd()()()();
|
|
391
|
+
i0.ɵɵelementStart(73, "div", 43)(74, "div", 44)(75, "div", 45)(76, "div", 46);
|
|
392
|
+
i0.ɵɵelement(77, "i", 47);
|
|
393
|
+
i0.ɵɵelementStart(78, "span");
|
|
394
|
+
i0.ɵɵtext(79, "Credentials by Category");
|
|
395
|
+
i0.ɵɵelementEnd()();
|
|
396
|
+
i0.ɵɵelementStart(80, "span", 48);
|
|
397
|
+
i0.ɵɵtext(81, "Click to filter by category");
|
|
398
|
+
i0.ɵɵelementEnd()();
|
|
399
|
+
i0.ɵɵelementStart(82, "div", 49);
|
|
400
|
+
i0.ɵɵtemplate(83, CredentialsOverviewResourceComponent_ng_container_2_div_83_Template, 12, 3, "div", 50)(84, CredentialsOverviewResourceComponent_ng_container_2_div_84_Template, 4, 0, "div", 51);
|
|
401
|
+
i0.ɵɵelementEnd()();
|
|
402
|
+
i0.ɵɵelementStart(85, "div", 52)(86, "div", 45)(87, "div", 46);
|
|
403
|
+
i0.ɵɵelement(88, "i", 39);
|
|
404
|
+
i0.ɵɵelementStart(89, "span");
|
|
405
|
+
i0.ɵɵtext(90, "Top Credential Types");
|
|
406
|
+
i0.ɵɵelementEnd()();
|
|
407
|
+
i0.ɵɵelementStart(91, "button", 53);
|
|
408
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_button_click_91_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.viewAllTypes()); });
|
|
409
|
+
i0.ɵɵtext(92, " View All ");
|
|
410
|
+
i0.ɵɵelement(93, "i", 33);
|
|
411
|
+
i0.ɵɵelementEnd()();
|
|
412
|
+
i0.ɵɵelementStart(94, "div", 49);
|
|
413
|
+
i0.ɵɵtemplate(95, CredentialsOverviewResourceComponent_ng_container_2_div_95_Template, 2, 1, "div", 54)(96, CredentialsOverviewResourceComponent_ng_container_2_div_96_Template, 4, 0, "div", 51);
|
|
414
|
+
i0.ɵɵelementEnd()();
|
|
415
|
+
i0.ɵɵelementStart(97, "div", 55)(98, "div", 45)(99, "div", 46);
|
|
416
|
+
i0.ɵɵelement(100, "i", 56);
|
|
417
|
+
i0.ɵɵelementStart(101, "span");
|
|
418
|
+
i0.ɵɵtext(102, "Recent Activity");
|
|
419
|
+
i0.ɵɵelementEnd()();
|
|
420
|
+
i0.ɵɵelementStart(103, "button", 53);
|
|
421
|
+
i0.ɵɵlistener("click", function CredentialsOverviewResourceComponent_ng_container_2_Template_button_click_103_listener() { i0.ɵɵrestoreView(_r1); const ctx_r1 = i0.ɵɵnextContext(); return i0.ɵɵresetView(ctx_r1.viewAuditLog()); });
|
|
422
|
+
i0.ɵɵtext(104, " View All ");
|
|
423
|
+
i0.ɵɵelement(105, "i", 33);
|
|
424
|
+
i0.ɵɵelementEnd()();
|
|
425
|
+
i0.ɵɵelementStart(106, "div", 49);
|
|
426
|
+
i0.ɵɵtemplate(107, CredentialsOverviewResourceComponent_ng_container_2_div_107_Template, 2, 1, "div", 57)(108, CredentialsOverviewResourceComponent_ng_container_2_div_108_Template, 4, 0, "div", 51);
|
|
427
|
+
i0.ɵɵelementEnd()()();
|
|
428
|
+
i0.ɵɵtemplate(109, CredentialsOverviewResourceComponent_ng_container_2_div_109_Template, 20, 0, "div", 58);
|
|
429
|
+
i0.ɵɵelementStart(110, "div", 59);
|
|
430
|
+
i0.ɵɵelement(111, "i", 60);
|
|
431
|
+
i0.ɵɵelementStart(112, "div", 61)(113, "strong");
|
|
432
|
+
i0.ɵɵtext(114, "Security Note:");
|
|
433
|
+
i0.ɵɵelementEnd();
|
|
434
|
+
i0.ɵɵtext(115, " All credential values are encrypted. Access to credentials is logged in the audit trail for compliance and security monitoring. ");
|
|
435
|
+
i0.ɵɵelementEnd()();
|
|
436
|
+
i0.ɵɵelementContainerEnd();
|
|
437
|
+
} if (rf & 2) {
|
|
438
|
+
const ctx_r1 = i0.ɵɵnextContext();
|
|
439
|
+
i0.ɵɵadvance(10);
|
|
440
|
+
i0.ɵɵproperty("ngIf", ctx_r1.UserCanCreateCredentials);
|
|
441
|
+
i0.ɵɵadvance();
|
|
442
|
+
i0.ɵɵproperty("ngClass", ctx_r1.getHealthClass());
|
|
443
|
+
i0.ɵɵadvance(5);
|
|
444
|
+
i0.ɵɵattribute("stroke-dasharray", ctx_r1.getHealthScore() + ", 100");
|
|
445
|
+
i0.ɵɵadvance(2);
|
|
446
|
+
i0.ɵɵtextInterpolate(ctx_r1.getHealthScore());
|
|
447
|
+
i0.ɵɵadvance(3);
|
|
448
|
+
i0.ɵɵtextInterpolate(ctx_r1.getHealthLabel());
|
|
449
|
+
i0.ɵɵadvance(2);
|
|
450
|
+
i0.ɵɵproperty("ngIf", ctx_r1.expiredCredentials > 0);
|
|
451
|
+
i0.ɵɵadvance();
|
|
452
|
+
i0.ɵɵproperty("ngIf", ctx_r1.expiringSoonCount > 0);
|
|
453
|
+
i0.ɵɵadvance();
|
|
454
|
+
i0.ɵɵproperty("ngIf", ctx_r1.expiredCredentials === 0 && ctx_r1.expiringSoonCount === 0);
|
|
455
|
+
i0.ɵɵadvance(7);
|
|
456
|
+
i0.ɵɵtextInterpolate(ctx_r1.totalCredentials);
|
|
457
|
+
i0.ɵɵadvance(10);
|
|
458
|
+
i0.ɵɵtextInterpolate(ctx_r1.activeCredentials);
|
|
459
|
+
i0.ɵɵadvance(5);
|
|
460
|
+
i0.ɵɵtextInterpolate1("", ctx_r1.totalCredentials > 0 ? (ctx_r1.activeCredentials / ctx_r1.totalCredentials * 100).toFixed(0) : 0, "%");
|
|
461
|
+
i0.ɵɵadvance(6);
|
|
462
|
+
i0.ɵɵtextInterpolate(ctx_r1.credentialTypes);
|
|
463
|
+
i0.ɵɵadvance(3);
|
|
464
|
+
i0.ɵɵclassProp("warning", ctx_r1.expiringSoonCount > 0);
|
|
465
|
+
i0.ɵɵadvance(5);
|
|
466
|
+
i0.ɵɵtextInterpolate(ctx_r1.expiringSoonCount);
|
|
467
|
+
i0.ɵɵadvance(3);
|
|
468
|
+
i0.ɵɵproperty("ngIf", ctx_r1.expiringSoonCount > 0);
|
|
469
|
+
i0.ɵɵadvance();
|
|
470
|
+
i0.ɵɵclassProp("danger", ctx_r1.expiredCredentials > 0);
|
|
471
|
+
i0.ɵɵadvance(5);
|
|
472
|
+
i0.ɵɵtextInterpolate(ctx_r1.expiredCredentials);
|
|
473
|
+
i0.ɵɵadvance(13);
|
|
474
|
+
i0.ɵɵproperty("ngIf", ctx_r1.categoryStats.length > 0);
|
|
475
|
+
i0.ɵɵadvance();
|
|
476
|
+
i0.ɵɵproperty("ngIf", ctx_r1.categoryStats.length === 0);
|
|
477
|
+
i0.ɵɵadvance(11);
|
|
478
|
+
i0.ɵɵproperty("ngIf", ctx_r1.typeStats.length > 0);
|
|
479
|
+
i0.ɵɵadvance();
|
|
480
|
+
i0.ɵɵproperty("ngIf", ctx_r1.typeStats.length === 0);
|
|
481
|
+
i0.ɵɵadvance(11);
|
|
482
|
+
i0.ɵɵproperty("ngIf", ctx_r1.recentActivity.length > 0);
|
|
483
|
+
i0.ɵɵadvance();
|
|
484
|
+
i0.ɵɵproperty("ngIf", ctx_r1.recentActivity.length === 0);
|
|
485
|
+
i0.ɵɵadvance();
|
|
486
|
+
i0.ɵɵproperty("ngIf", ctx_r1.UserCanCreateCredentials);
|
|
487
|
+
} }
|
|
488
|
+
export function LoadCredentialsOverviewResource() {
|
|
489
|
+
// Prevents tree-shaking
|
|
490
|
+
}
|
|
491
|
+
let CredentialsOverviewResourceComponent = class CredentialsOverviewResourceComponent extends BaseResourceComponent {
|
|
492
|
+
cdr;
|
|
493
|
+
navigationService;
|
|
494
|
+
isLoading = true;
|
|
495
|
+
// Summary stats
|
|
496
|
+
totalCredentials = 0;
|
|
497
|
+
activeCredentials = 0;
|
|
498
|
+
expiredCredentials = 0;
|
|
499
|
+
expiringSoonCount = 0;
|
|
500
|
+
credentialTypes = 0;
|
|
501
|
+
categories = 0;
|
|
502
|
+
// Grouped data
|
|
503
|
+
categoryStats = [];
|
|
504
|
+
typeStats = [];
|
|
505
|
+
recentActivity = [];
|
|
506
|
+
usageTrend = [];
|
|
507
|
+
// Raw data
|
|
508
|
+
credentials = [];
|
|
509
|
+
types = [];
|
|
510
|
+
categoryList = [];
|
|
511
|
+
auditLogs = [];
|
|
512
|
+
// Permissions
|
|
513
|
+
_metadata = new Metadata();
|
|
514
|
+
_permissionCache = new Map();
|
|
515
|
+
// Category colors for charts
|
|
516
|
+
categoryColors = {
|
|
517
|
+
'AI': '#8b5cf6',
|
|
518
|
+
'Communication': '#3b82f6',
|
|
519
|
+
'Storage': '#10b981',
|
|
520
|
+
'Database': '#f59e0b',
|
|
521
|
+
'Authentication': '#ef4444',
|
|
522
|
+
'Integration': '#6366f1'
|
|
523
|
+
};
|
|
524
|
+
destroy$ = new Subject();
|
|
525
|
+
constructor(cdr, navigationService) {
|
|
526
|
+
super();
|
|
527
|
+
this.cdr = cdr;
|
|
528
|
+
this.navigationService = navigationService;
|
|
529
|
+
}
|
|
530
|
+
ngOnInit() {
|
|
531
|
+
this.loadData();
|
|
532
|
+
}
|
|
533
|
+
ngOnDestroy() {
|
|
534
|
+
this.destroy$.next();
|
|
535
|
+
this.destroy$.complete();
|
|
536
|
+
}
|
|
537
|
+
async GetResourceDisplayName(data) {
|
|
538
|
+
return 'Overview';
|
|
539
|
+
}
|
|
540
|
+
async GetResourceIconClass(data) {
|
|
541
|
+
return 'fa-solid fa-chart-pie';
|
|
542
|
+
}
|
|
543
|
+
// === Permission Checks ===
|
|
544
|
+
get UserCanCreateCredentials() {
|
|
545
|
+
return this.checkEntityPermission('MJ: Credentials', 'Create');
|
|
546
|
+
}
|
|
547
|
+
get UserCanUpdateCredentials() {
|
|
548
|
+
return this.checkEntityPermission('MJ: Credentials', 'Update');
|
|
549
|
+
}
|
|
550
|
+
checkEntityPermission(entityName, permissionType) {
|
|
551
|
+
const cacheKey = `${entityName}_${permissionType}`;
|
|
552
|
+
if (this._permissionCache.has(cacheKey)) {
|
|
553
|
+
return this._permissionCache.get(cacheKey);
|
|
554
|
+
}
|
|
555
|
+
try {
|
|
556
|
+
const entityInfo = this._metadata.Entities.find(e => e.Name === entityName);
|
|
557
|
+
if (!entityInfo) {
|
|
558
|
+
this._permissionCache.set(cacheKey, false);
|
|
559
|
+
return false;
|
|
560
|
+
}
|
|
561
|
+
const userPermissions = entityInfo.GetUserPermisions(this._metadata.CurrentUser);
|
|
562
|
+
let hasPermission = false;
|
|
563
|
+
switch (permissionType) {
|
|
564
|
+
case 'Create':
|
|
565
|
+
hasPermission = userPermissions.CanCreate;
|
|
566
|
+
break;
|
|
567
|
+
case 'Read':
|
|
568
|
+
hasPermission = userPermissions.CanRead;
|
|
569
|
+
break;
|
|
570
|
+
case 'Update':
|
|
571
|
+
hasPermission = userPermissions.CanUpdate;
|
|
572
|
+
break;
|
|
573
|
+
case 'Delete':
|
|
574
|
+
hasPermission = userPermissions.CanDelete;
|
|
575
|
+
break;
|
|
576
|
+
}
|
|
577
|
+
this._permissionCache.set(cacheKey, hasPermission);
|
|
578
|
+
return hasPermission;
|
|
579
|
+
}
|
|
580
|
+
catch (error) {
|
|
581
|
+
this._permissionCache.set(cacheKey, false);
|
|
582
|
+
return false;
|
|
583
|
+
}
|
|
584
|
+
}
|
|
585
|
+
async loadData() {
|
|
586
|
+
try {
|
|
587
|
+
this.isLoading = true;
|
|
588
|
+
this.cdr.markForCheck();
|
|
589
|
+
const rv = new RunView();
|
|
590
|
+
// Calculate date range for audit logs (last 30 days)
|
|
591
|
+
const thirtyDaysAgo = new Date();
|
|
592
|
+
thirtyDaysAgo.setDate(thirtyDaysAgo.getDate() - 30);
|
|
593
|
+
const dateFilter = `__mj_CreatedAt >= '${thirtyDaysAgo.toISOString()}'`;
|
|
594
|
+
// Load all data in parallel using RunViews
|
|
595
|
+
const [credResult, typeResult, categoryResult, auditResult] = await rv.RunViews([
|
|
596
|
+
{
|
|
597
|
+
EntityName: 'MJ: Credentials',
|
|
598
|
+
ResultType: 'entity_object'
|
|
599
|
+
},
|
|
600
|
+
{
|
|
601
|
+
EntityName: 'MJ: Credential Types',
|
|
602
|
+
ResultType: 'entity_object'
|
|
603
|
+
},
|
|
604
|
+
{
|
|
605
|
+
EntityName: 'MJ: Credential Categories',
|
|
606
|
+
ResultType: 'entity_object'
|
|
607
|
+
},
|
|
608
|
+
{
|
|
609
|
+
EntityName: 'Audit Logs',
|
|
610
|
+
ExtraFilter: `AuditLogType LIKE '%Credential%' AND ${dateFilter}`,
|
|
611
|
+
OrderBy: '__mj_CreatedAt DESC',
|
|
612
|
+
MaxRows: 100,
|
|
613
|
+
ResultType: 'entity_object'
|
|
614
|
+
}
|
|
615
|
+
]);
|
|
616
|
+
if (credResult.Success) {
|
|
617
|
+
this.credentials = credResult.Results;
|
|
618
|
+
this.processCredentialStats();
|
|
619
|
+
}
|
|
620
|
+
if (typeResult.Success) {
|
|
621
|
+
this.types = typeResult.Results;
|
|
622
|
+
this.credentialTypes = this.types.length;
|
|
623
|
+
this.processTypeStats();
|
|
624
|
+
}
|
|
625
|
+
if (categoryResult.Success) {
|
|
626
|
+
this.categoryList = categoryResult.Results;
|
|
627
|
+
this.categories = this.categoryList.length;
|
|
628
|
+
this.processCategoryStats();
|
|
629
|
+
}
|
|
630
|
+
if (auditResult.Success) {
|
|
631
|
+
this.auditLogs = auditResult.Results;
|
|
632
|
+
this.processActivityAndTrends();
|
|
633
|
+
}
|
|
634
|
+
// Build recent activity from credentials if no audit logs
|
|
635
|
+
if (this.recentActivity.length === 0) {
|
|
636
|
+
this.buildActivityFromCredentials();
|
|
637
|
+
}
|
|
638
|
+
}
|
|
639
|
+
catch (error) {
|
|
640
|
+
console.error('Error loading credentials overview:', error);
|
|
641
|
+
}
|
|
642
|
+
finally {
|
|
643
|
+
this.isLoading = false;
|
|
644
|
+
this.NotifyLoadComplete();
|
|
645
|
+
this.cdr.markForCheck();
|
|
646
|
+
}
|
|
647
|
+
}
|
|
648
|
+
processCredentialStats() {
|
|
649
|
+
this.totalCredentials = this.credentials.length;
|
|
650
|
+
this.activeCredentials = this.credentials.filter(c => c.IsActive).length;
|
|
651
|
+
const now = new Date();
|
|
652
|
+
const thirtyDaysFromNow = new Date();
|
|
653
|
+
thirtyDaysFromNow.setDate(thirtyDaysFromNow.getDate() + 30);
|
|
654
|
+
this.expiredCredentials = this.credentials.filter(c => c.ExpiresAt && new Date(c.ExpiresAt) < now).length;
|
|
655
|
+
this.expiringSoonCount = this.credentials.filter(c => c.ExpiresAt &&
|
|
656
|
+
new Date(c.ExpiresAt) >= now &&
|
|
657
|
+
new Date(c.ExpiresAt) <= thirtyDaysFromNow &&
|
|
658
|
+
c.IsActive).length;
|
|
659
|
+
}
|
|
660
|
+
processTypeStats() {
|
|
661
|
+
const now = new Date();
|
|
662
|
+
const thirtyDaysFromNow = new Date();
|
|
663
|
+
thirtyDaysFromNow.setDate(thirtyDaysFromNow.getDate() + 30);
|
|
664
|
+
this.typeStats = this.types.map(type => {
|
|
665
|
+
const typeCredentials = this.credentials.filter(c => c.CredentialTypeID === type.ID);
|
|
666
|
+
return {
|
|
667
|
+
typeId: type.ID,
|
|
668
|
+
typeName: type.Name,
|
|
669
|
+
category: type.Category,
|
|
670
|
+
credentialCount: typeCredentials.length,
|
|
671
|
+
activeCount: typeCredentials.filter(c => c.IsActive).length,
|
|
672
|
+
expiringCount: typeCredentials.filter(c => c.ExpiresAt &&
|
|
673
|
+
new Date(c.ExpiresAt) >= now &&
|
|
674
|
+
new Date(c.ExpiresAt) <= thirtyDaysFromNow).length
|
|
675
|
+
};
|
|
676
|
+
}).sort((a, b) => b.credentialCount - a.credentialCount);
|
|
677
|
+
}
|
|
678
|
+
processCategoryStats() {
|
|
679
|
+
const categoryMap = new Map();
|
|
680
|
+
// Initialize from credential types
|
|
681
|
+
for (const type of this.types) {
|
|
682
|
+
const category = type.Category;
|
|
683
|
+
const existing = categoryMap.get(category);
|
|
684
|
+
const categoryCredentials = this.credentials.filter(c => c.CredentialTypeID === type.ID);
|
|
685
|
+
if (existing) {
|
|
686
|
+
existing.count += categoryCredentials.length;
|
|
687
|
+
}
|
|
688
|
+
else {
|
|
689
|
+
categoryMap.set(category, {
|
|
690
|
+
category: category,
|
|
691
|
+
categoryId: category, // Use category name as ID for filtering
|
|
692
|
+
count: categoryCredentials.length,
|
|
693
|
+
iconClass: this.getCategoryIcon(category),
|
|
694
|
+
color: this.categoryColors[category] || '#64748b',
|
|
695
|
+
percentage: 0
|
|
696
|
+
});
|
|
697
|
+
}
|
|
698
|
+
}
|
|
699
|
+
// Calculate percentages
|
|
700
|
+
const total = this.totalCredentials || 1;
|
|
701
|
+
categoryMap.forEach(stat => {
|
|
702
|
+
stat.percentage = Math.round((stat.count / total) * 100);
|
|
703
|
+
});
|
|
704
|
+
this.categoryStats = Array.from(categoryMap.values())
|
|
705
|
+
.sort((a, b) => b.count - a.count);
|
|
706
|
+
}
|
|
707
|
+
processActivityAndTrends() {
|
|
708
|
+
// Process recent activity from audit logs
|
|
709
|
+
this.recentActivity = this.auditLogs
|
|
710
|
+
.slice(0, 10)
|
|
711
|
+
.map(log => ({
|
|
712
|
+
id: log.ID,
|
|
713
|
+
credentialName: this.extractCredentialName(log.Description || ''),
|
|
714
|
+
credentialId: '', // Would need to parse from log
|
|
715
|
+
typeName: 'Credential',
|
|
716
|
+
action: this.extractAction(log.Description || ''),
|
|
717
|
+
date: new Date(log.__mj_CreatedAt),
|
|
718
|
+
user: log.User
|
|
719
|
+
}));
|
|
720
|
+
// Build usage trend data (group by day)
|
|
721
|
+
const trendMap = new Map();
|
|
722
|
+
const uniqueCredentialsPerDay = new Map();
|
|
723
|
+
for (const log of this.auditLogs) {
|
|
724
|
+
const dateKey = new Date(log.__mj_CreatedAt).toISOString().split('T')[0];
|
|
725
|
+
if (!trendMap.has(dateKey)) {
|
|
726
|
+
trendMap.set(dateKey, {
|
|
727
|
+
timestamp: new Date(dateKey),
|
|
728
|
+
accessCount: 0,
|
|
729
|
+
uniqueCredentials: 0,
|
|
730
|
+
successRate: 100
|
|
731
|
+
});
|
|
732
|
+
uniqueCredentialsPerDay.set(dateKey, new Set());
|
|
733
|
+
}
|
|
734
|
+
const point = trendMap.get(dateKey);
|
|
735
|
+
point.accessCount++;
|
|
736
|
+
// Track unique credentials (would need proper parsing)
|
|
737
|
+
const credId = this.extractCredentialId(log.Description || '');
|
|
738
|
+
if (credId) {
|
|
739
|
+
uniqueCredentialsPerDay.get(dateKey).add(credId);
|
|
740
|
+
}
|
|
741
|
+
}
|
|
742
|
+
// Finalize unique counts
|
|
743
|
+
trendMap.forEach((point, dateKey) => {
|
|
744
|
+
point.uniqueCredentials = uniqueCredentialsPerDay.get(dateKey)?.size || 0;
|
|
745
|
+
});
|
|
746
|
+
this.usageTrend = Array.from(trendMap.values())
|
|
747
|
+
.sort((a, b) => a.timestamp.getTime() - b.timestamp.getTime());
|
|
748
|
+
}
|
|
749
|
+
buildActivityFromCredentials() {
|
|
750
|
+
this.recentActivity = this.credentials
|
|
751
|
+
.filter(c => c.__mj_UpdatedAt)
|
|
752
|
+
.sort((a, b) => new Date(b.__mj_UpdatedAt).getTime() - new Date(a.__mj_UpdatedAt).getTime())
|
|
753
|
+
.slice(0, 10)
|
|
754
|
+
.map(c => ({
|
|
755
|
+
id: c.ID,
|
|
756
|
+
credentialName: c.Name,
|
|
757
|
+
credentialId: c.ID,
|
|
758
|
+
typeName: c.CredentialType || 'Unknown',
|
|
759
|
+
action: 'Updated',
|
|
760
|
+
date: new Date(c.__mj_UpdatedAt),
|
|
761
|
+
user: undefined
|
|
762
|
+
}));
|
|
763
|
+
}
|
|
764
|
+
extractCredentialName(description) {
|
|
765
|
+
// Try to extract credential name from audit log description
|
|
766
|
+
const match = description.match(/credential[:\s]+['"]?([^'"]+)['"]?/i);
|
|
767
|
+
return match ? match[1] : 'Unknown Credential';
|
|
768
|
+
}
|
|
769
|
+
extractAction(description) {
|
|
770
|
+
if (description.toLowerCase().includes('creat'))
|
|
771
|
+
return 'Created';
|
|
772
|
+
if (description.toLowerCase().includes('rotat'))
|
|
773
|
+
return 'Rotated';
|
|
774
|
+
if (description.toLowerCase().includes('access'))
|
|
775
|
+
return 'Accessed';
|
|
776
|
+
return 'Updated';
|
|
777
|
+
}
|
|
778
|
+
extractCredentialId(description) {
|
|
779
|
+
const match = description.match(/[a-f0-9-]{36}/i);
|
|
780
|
+
return match ? match[0] : '';
|
|
781
|
+
}
|
|
782
|
+
getCategoryIcon(category) {
|
|
783
|
+
const iconMap = {
|
|
784
|
+
'AI': 'fa-solid fa-brain',
|
|
785
|
+
'Communication': 'fa-solid fa-envelope',
|
|
786
|
+
'Storage': 'fa-solid fa-cloud',
|
|
787
|
+
'Database': 'fa-solid fa-database',
|
|
788
|
+
'Authentication': 'fa-solid fa-shield-halved',
|
|
789
|
+
'Integration': 'fa-solid fa-plug'
|
|
790
|
+
};
|
|
791
|
+
return iconMap[category] || 'fa-solid fa-key';
|
|
792
|
+
}
|
|
793
|
+
// === Navigation Actions ===
|
|
794
|
+
createNewCredential() {
|
|
795
|
+
// Navigate to Credentials tab with openCreatePanel flag to show the slide-in editor
|
|
796
|
+
this.navigationService.OpenNavItemByName('Credentials', {
|
|
797
|
+
openCreatePanel: true
|
|
798
|
+
});
|
|
799
|
+
}
|
|
800
|
+
openCredential(credentialId) {
|
|
801
|
+
const key = new CompositeKey([{ FieldName: 'ID', Value: credentialId }]);
|
|
802
|
+
this.navigationService.OpenEntityRecord('MJ: Credentials', key);
|
|
803
|
+
}
|
|
804
|
+
onCategoryClick(category) {
|
|
805
|
+
// Navigate to types nav item with category filter
|
|
806
|
+
this.navigationService.OpenNavItemByName('Types', {
|
|
807
|
+
categoryFilter: category.category
|
|
808
|
+
});
|
|
809
|
+
}
|
|
810
|
+
onTypeClick(typeStat) {
|
|
811
|
+
// Navigate to credentials nav item with type filter
|
|
812
|
+
this.navigationService.OpenNavItemByName('Credentials', {
|
|
813
|
+
typeId: typeStat.typeId
|
|
814
|
+
});
|
|
815
|
+
}
|
|
816
|
+
onActivityClick(activity) {
|
|
817
|
+
if (activity.credentialId) {
|
|
818
|
+
this.openCredential(activity.credentialId);
|
|
819
|
+
}
|
|
820
|
+
}
|
|
821
|
+
viewAllCredentials() {
|
|
822
|
+
this.navigationService.OpenNavItemByName('Credentials');
|
|
823
|
+
}
|
|
824
|
+
viewAuditLog() {
|
|
825
|
+
this.navigationService.OpenNavItemByName('Audit Log');
|
|
826
|
+
}
|
|
827
|
+
viewAllTypes() {
|
|
828
|
+
this.navigationService.OpenNavItemByName('Types');
|
|
829
|
+
}
|
|
830
|
+
viewAllCategories() {
|
|
831
|
+
this.navigationService.OpenNavItemByName('Categories');
|
|
832
|
+
}
|
|
833
|
+
viewExpiringCredentials() {
|
|
834
|
+
this.navigationService.OpenNavItemByName('Credentials', {
|
|
835
|
+
filter: 'expiring'
|
|
836
|
+
});
|
|
837
|
+
}
|
|
838
|
+
// === Formatting Helpers ===
|
|
839
|
+
formatDate(date) {
|
|
840
|
+
const now = new Date();
|
|
841
|
+
const diffMs = now.getTime() - date.getTime();
|
|
842
|
+
const diffMins = Math.floor(diffMs / 60000);
|
|
843
|
+
const diffHours = Math.floor(diffMs / 3600000);
|
|
844
|
+
const diffDays = Math.floor(diffMs / 86400000);
|
|
845
|
+
if (diffMins < 1)
|
|
846
|
+
return 'Just now';
|
|
847
|
+
if (diffMins < 60)
|
|
848
|
+
return `${diffMins}m ago`;
|
|
849
|
+
if (diffHours < 24)
|
|
850
|
+
return `${diffHours}h ago`;
|
|
851
|
+
if (diffDays < 7)
|
|
852
|
+
return `${diffDays}d ago`;
|
|
853
|
+
return date.toLocaleDateString('en-US', {
|
|
854
|
+
month: 'short',
|
|
855
|
+
day: 'numeric',
|
|
856
|
+
hour: '2-digit',
|
|
857
|
+
minute: '2-digit'
|
|
858
|
+
});
|
|
859
|
+
}
|
|
860
|
+
getActionIcon(action) {
|
|
861
|
+
const iconMap = {
|
|
862
|
+
'Created': 'fa-solid fa-plus',
|
|
863
|
+
'Updated': 'fa-solid fa-pen',
|
|
864
|
+
'Accessed': 'fa-solid fa-eye',
|
|
865
|
+
'Rotated': 'fa-solid fa-rotate'
|
|
866
|
+
};
|
|
867
|
+
return iconMap[action] || 'fa-solid fa-circle';
|
|
868
|
+
}
|
|
869
|
+
getActionClass(action) {
|
|
870
|
+
const classMap = {
|
|
871
|
+
'Created': 'action-created',
|
|
872
|
+
'Updated': 'action-updated',
|
|
873
|
+
'Accessed': 'action-accessed',
|
|
874
|
+
'Rotated': 'action-rotated'
|
|
875
|
+
};
|
|
876
|
+
return classMap[action] || '';
|
|
877
|
+
}
|
|
878
|
+
refresh() {
|
|
879
|
+
this.loadData();
|
|
880
|
+
}
|
|
881
|
+
getHealthScore() {
|
|
882
|
+
if (this.totalCredentials === 0)
|
|
883
|
+
return 100;
|
|
884
|
+
const activeRatio = this.activeCredentials / this.totalCredentials;
|
|
885
|
+
const expiredPenalty = (this.expiredCredentials / this.totalCredentials) * 30;
|
|
886
|
+
const expiringPenalty = (this.expiringSoonCount / this.totalCredentials) * 15;
|
|
887
|
+
return Math.max(0, Math.min(100, Math.round((activeRatio * 100) - expiredPenalty - expiringPenalty)));
|
|
888
|
+
}
|
|
889
|
+
getHealthClass() {
|
|
890
|
+
const score = this.getHealthScore();
|
|
891
|
+
if (score >= 80)
|
|
892
|
+
return 'health-good';
|
|
893
|
+
if (score >= 60)
|
|
894
|
+
return 'health-warning';
|
|
895
|
+
return 'health-critical';
|
|
896
|
+
}
|
|
897
|
+
getHealthLabel() {
|
|
898
|
+
const score = this.getHealthScore();
|
|
899
|
+
if (score >= 80)
|
|
900
|
+
return 'Healthy';
|
|
901
|
+
if (score >= 60)
|
|
902
|
+
return 'Needs Attention';
|
|
903
|
+
return 'Critical';
|
|
904
|
+
}
|
|
905
|
+
getDonutOffset(index) {
|
|
906
|
+
// Calculate cumulative offset for donut chart segments
|
|
907
|
+
// Each segment starts where the previous one ended
|
|
908
|
+
// The circumference is 251 (2 * PI * 40)
|
|
909
|
+
let offset = 63; // Start at top (25% of circumference = 90 degrees rotation)
|
|
910
|
+
for (let i = 0; i < index; i++) {
|
|
911
|
+
offset -= this.categoryStats[i].percentage * 2.51;
|
|
912
|
+
}
|
|
913
|
+
return offset;
|
|
914
|
+
}
|
|
915
|
+
static ɵfac = function CredentialsOverviewResourceComponent_Factory(t) { return new (t || CredentialsOverviewResourceComponent)(i0.ɵɵdirectiveInject(i0.ChangeDetectorRef), i0.ɵɵdirectiveInject(i1.NavigationService)); };
|
|
916
|
+
static ɵcmp = /*@__PURE__*/ i0.ɵɵdefineComponent({ type: CredentialsOverviewResourceComponent, selectors: [["mj-credentials-overview-resource"]], features: [i0.ɵɵInheritDefinitionFeature], decls: 3, vars: 2, consts: [[1, "overview-container"], ["text", "Loading overview...", 4, "ngIf"], [4, "ngIf"], ["text", "Loading overview..."], [1, "overview-header"], [1, "header-left"], [1, "overview-title"], [1, "overview-subtitle"], [1, "header-actions"], ["title", "Refresh", 1, "btn-refresh", 3, "click"], [1, "fa-solid", "fa-refresh"], ["class", "btn-primary", 3, "click", 4, "ngIf"], [1, "health-banner", 3, "ngClass"], [1, "health-score-container"], [1, "health-score-ring"], ["viewBox", "0 0 36 36", 1, "circular-chart"], ["d", "M18 2.0845\n a 15.9155 15.9155 0 0 1 0 31.831\n a 15.9155 15.9155 0 0 1 0 -31.831", 1, "circle-bg"], ["d", "M18 2.0845\n a 15.9155 15.9155 0 0 1 0 31.831\n a 15.9155 15.9155 0 0 1 0 -31.831", 1, "circle"], [1, "health-score-value"], [1, "health-info"], [1, "health-label"], [1, "health-details"], ["class", "health-alert", 4, "ngIf"], ["class", "health-warning-text", 3, "click", 4, "ngIf"], ["class", "health-ok", 4, "ngIf"], [1, "kpi-row"], [1, "kpi-card", "clickable", 3, "click"], [1, "kpi-icon"], [1, "fa-solid", "fa-key"], [1, "kpi-content"], [1, "kpi-value"], [1, "kpi-label"], [1, "kpi-trend"], [1, "fa-solid", "fa-arrow-right"], [1, "kpi-card", "active", "clickable", 3, "click"], [1, "fa-solid", "fa-check-circle"], [1, "kpi-trend", "success"], [1, "percentage"], [1, "kpi-card"], [1, "fa-solid", "fa-cubes"], [1, "fa-solid", "fa-clock"], ["class", "kpi-trend warning", 4, "ngIf"], [1, "fa-solid", "fa-circle-xmark"], [1, "content-grid"], [1, "panel", "category-panel"], [1, "panel-header"], [1, "panel-title"], [1, "fa-solid", "fa-chart-pie"], [1, "panel-subtitle"], [1, "panel-body"], ["class", "category-chart", 4, "ngIf"], ["class", "empty-state", 4, "ngIf"], [1, "panel", "types-panel"], [1, "panel-action", 3, "click"], ["class", "type-list", 4, "ngIf"], [1, "panel", "activity-panel"], [1, "fa-solid", "fa-clock-rotate-left"], ["class", "activity-list", 4, "ngIf"], ["class", "quick-actions", 4, "ngIf"], [1, "security-notice"], [1, "fa-solid", "fa-shield-check"], [1, "notice-content"], [1, "btn-primary", 3, "click"], [1, "fa-solid", "fa-plus"], [1, "health-alert"], [1, "fa-solid", "fa-circle-exclamation"], [1, "health-warning-text", 3, "click"], [1, "health-ok"], [1, "kpi-trend", "warning"], [1, "category-chart"], [1, "donut-chart-container"], ["viewBox", "0 0 100 100", 1, "donut-chart"], ["cx", "50", "cy", "50", "r", "40", "fill", "none", "stroke", "#e5e7eb", "stroke-width", "12"], [4, "ngFor", "ngForOf"], [1, "donut-center"], [1, "donut-total"], [1, "donut-label"], [1, "category-legend"], ["class", "legend-item", 3, "click", 4, "ngFor", "ngForOf"], ["cx", "50", "cy", "50", "r", "40", "fill", "none", "stroke-width", "12", 1, "donut-segment", 3, "click"], [1, "legend-item", 3, "click"], [1, "legend-color"], [1, "legend-info"], [1, "legend-name"], [1, "legend-value"], [1, "fa-solid", "fa-chevron-right", "legend-arrow"], [1, "empty-state"], [1, "fa-solid", "fa-folder-open"], [1, "type-list"], ["class", "type-item", 3, "click", 4, "ngFor", "ngForOf"], [1, "type-item", 3, "click"], [1, "type-info"], [1, "type-name"], [1, "type-category"], [1, "type-stats"], [1, "type-count"], [1, "count-value"], [1, "count-label"], [1, "type-bar"], [1, "type-bar-fill"], [1, "type-indicators"], ["class", "indicator active", "title", "Active", 4, "ngIf"], ["class", "indicator warning", "title", "Expiring Soon", 4, "ngIf"], ["title", "Active", 1, "indicator", "active"], [1, "fa-solid", "fa-circle"], ["title", "Expiring Soon", 1, "indicator", "warning"], [1, "fa-solid", "fa-shapes"], [1, "activity-list"], ["class", "activity-item", 3, "click", 4, "ngFor", "ngForOf"], [1, "activity-item", 3, "click"], [1, "activity-icon", 3, "ngClass"], [1, "activity-info"], [1, "activity-name"], [1, "activity-meta"], [1, "activity-type"], [1, "activity-action"], ["class", "activity-user", 4, "ngIf"], [1, "activity-time"], [1, "activity-user"], [1, "fa-solid", "fa-inbox"], [1, "quick-actions"], [1, "quick-actions-title"], [1, "quick-actions-grid"], [1, "quick-action", 3, "click"], [1, "fa-solid", "fa-folder-tree"], [1, "fa-solid", "fa-clipboard-list"]], template: function CredentialsOverviewResourceComponent_Template(rf, ctx) { if (rf & 1) {
|
|
917
|
+
i0.ɵɵelementStart(0, "div", 0);
|
|
918
|
+
i0.ɵɵtemplate(1, CredentialsOverviewResourceComponent_mj_loading_1_Template, 1, 0, "mj-loading", 1)(2, CredentialsOverviewResourceComponent_ng_container_2_Template, 116, 26, "ng-container", 2);
|
|
919
|
+
i0.ɵɵelementEnd();
|
|
920
|
+
} if (rf & 2) {
|
|
921
|
+
i0.ɵɵadvance();
|
|
922
|
+
i0.ɵɵproperty("ngIf", ctx.isLoading);
|
|
923
|
+
i0.ɵɵadvance();
|
|
924
|
+
i0.ɵɵproperty("ngIf", !ctx.isLoading);
|
|
925
|
+
} }, dependencies: [i2.NgClass, i2.NgForOf, i2.NgIf, i3.LoadingComponent], styles: [".overview-container[_ngcontent-%COMP%] {\n padding: 24px;\n height: 100%;\n overflow-y: auto;\n}\n\n\n\n.overview-header[_ngcontent-%COMP%] {\n display: flex;\n justify-content: space-between;\n align-items: flex-start;\n margin-bottom: 24px;\n}\n\n.header-left[_ngcontent-%COMP%] {\n flex: 1;\n}\n\n.overview-title[_ngcontent-%COMP%] {\n font-size: 24px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n margin: 0 0 4px 0;\n}\n\n.overview-subtitle[_ngcontent-%COMP%] {\n font-size: 14px;\n color: var(--text-secondary, #6b7280);\n margin: 0;\n}\n\n.header-actions[_ngcontent-%COMP%] {\n display: flex;\n gap: 12px;\n}\n\n.btn-refresh[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 40px;\n height: 40px;\n background: var(--card-background, #ffffff);\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.btn-refresh[_ngcontent-%COMP%]:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.btn-refresh[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: var(--text-secondary, #6b7280);\n}\n\n.btn-primary[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 10px 20px;\n background: linear-gradient(135deg, #6366f1 0%, #4f46e5 100%);\n color: white;\n border: none;\n border-radius: 8px;\n font-weight: 600;\n font-size: 14px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.btn-primary[_ngcontent-%COMP%]:hover {\n transform: translateY(-1px);\n box-shadow: 0 4px 12px rgba(99, 102, 241, 0.4);\n}\n\n\n\n.health-banner[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n padding: 20px 24px;\n background: linear-gradient(135deg, #ecfdf5 0%, #d1fae5 100%);\n border: 1px solid #a7f3d0;\n border-radius: 16px;\n margin-bottom: 24px;\n}\n\n.health-banner.health-warning[_ngcontent-%COMP%] {\n background: linear-gradient(135deg, #fffbeb 0%, #fef3c7 100%);\n border-color: #fcd34d;\n}\n\n.health-banner.health-critical[_ngcontent-%COMP%] {\n background: linear-gradient(135deg, #fef2f2 0%, #fee2e2 100%);\n border-color: #fca5a5;\n}\n\n.health-score-container[_ngcontent-%COMP%] {\n margin-right: 24px;\n}\n\n.health-score-ring[_ngcontent-%COMP%] {\n position: relative;\n width: 80px;\n height: 80px;\n}\n\n.circular-chart[_ngcontent-%COMP%] {\n display: block;\n margin: 0 auto;\n max-height: 80px;\n transform: rotate(-90deg);\n}\n\n.circle-bg[_ngcontent-%COMP%] {\n fill: none;\n stroke: #e5e7eb;\n stroke-width: 3.8;\n}\n\n.circle[_ngcontent-%COMP%] {\n fill: none;\n stroke-width: 3.8;\n stroke-linecap: round;\n stroke: #10b981;\n animation: _ngcontent-%COMP%_progress 1s ease-out forwards;\n}\n\n.health-banner.health-warning[_ngcontent-%COMP%] .circle[_ngcontent-%COMP%] {\n stroke: #f59e0b;\n}\n\n.health-banner.health-critical[_ngcontent-%COMP%] .circle[_ngcontent-%COMP%] {\n stroke: #ef4444;\n}\n\n@keyframes _ngcontent-%COMP%_progress {\n 0% {\n stroke-dasharray: 0 100;\n }\n}\n\n.health-score-value[_ngcontent-%COMP%] {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n font-size: 20px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.health-info[_ngcontent-%COMP%] {\n flex: 1;\n}\n\n.health-label[_ngcontent-%COMP%] {\n font-size: 18px;\n font-weight: 700;\n color: #059669;\n margin-bottom: 4px;\n}\n\n.health-banner.health-warning[_ngcontent-%COMP%] .health-label[_ngcontent-%COMP%] {\n color: #d97706;\n}\n\n.health-banner.health-critical[_ngcontent-%COMP%] .health-label[_ngcontent-%COMP%] {\n color: #dc2626;\n}\n\n.health-details[_ngcontent-%COMP%] {\n display: flex;\n gap: 16px;\n flex-wrap: wrap;\n}\n\n.health-alert[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #dc2626;\n font-weight: 500;\n font-size: 14px;\n}\n\n.health-warning-text[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #d97706;\n font-weight: 500;\n font-size: 14px;\n cursor: pointer;\n}\n\n.health-warning-text[_ngcontent-%COMP%]:hover {\n text-decoration: underline;\n}\n\n.health-ok[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #059669;\n font-weight: 500;\n font-size: 14px;\n}\n\n\n\n.kpi-row[_ngcontent-%COMP%] {\n display: grid;\n grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));\n gap: 16px;\n margin-bottom: 24px;\n}\n\n.kpi-card[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n padding: 16px 20px;\n background: var(--card-background, #ffffff);\n border-radius: 12px;\n box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);\n transition: transform 0.2s ease, box-shadow 0.2s ease;\n}\n\n.kpi-card.clickable[_ngcontent-%COMP%] {\n cursor: pointer;\n}\n\n.kpi-card.clickable[_ngcontent-%COMP%]:hover {\n transform: translateY(-2px);\n box-shadow: 0 4px 16px rgba(0, 0, 0, 0.12);\n}\n\n.kpi-card.active[_ngcontent-%COMP%] .kpi-icon[_ngcontent-%COMP%] {\n background: linear-gradient(135deg, #10b981 0%, #059669 100%);\n}\n\n.kpi-card.warning[_ngcontent-%COMP%] .kpi-icon[_ngcontent-%COMP%] {\n background: linear-gradient(135deg, #f59e0b 0%, #d97706 100%);\n}\n\n.kpi-card.danger[_ngcontent-%COMP%] .kpi-icon[_ngcontent-%COMP%] {\n background: linear-gradient(135deg, #ef4444 0%, #dc2626 100%);\n}\n\n.kpi-icon[_ngcontent-%COMP%] {\n width: 48px;\n height: 48px;\n display: flex;\n align-items: center;\n justify-content: center;\n background: linear-gradient(135deg, #6366f1 0%, #4f46e5 100%);\n border-radius: 10px;\n margin-right: 14px;\n flex-shrink: 0;\n}\n\n.kpi-icon[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 20px;\n color: white;\n}\n\n.kpi-content[_ngcontent-%COMP%] {\n flex: 1;\n min-width: 0;\n}\n\n.kpi-value[_ngcontent-%COMP%] {\n font-size: 24px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n line-height: 1.2;\n}\n\n.kpi-label[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n margin-top: 2px;\n white-space: nowrap;\n}\n\n.kpi-trend[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n margin-left: 8px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.kpi-trend.success[_ngcontent-%COMP%] {\n color: #10b981;\n}\n\n.kpi-trend.warning[_ngcontent-%COMP%] {\n color: #f59e0b;\n}\n\n.kpi-trend[_ngcontent-%COMP%] .percentage[_ngcontent-%COMP%] {\n font-size: 12px;\n font-weight: 600;\n}\n\n\n\n.content-grid[_ngcontent-%COMP%] {\n display: grid;\n grid-template-columns: 1fr 1fr;\n grid-template-rows: auto auto;\n gap: 20px;\n margin-bottom: 24px;\n}\n\n.category-panel[_ngcontent-%COMP%] {\n grid-row: span 2;\n}\n\n.panel[_ngcontent-%COMP%] {\n background: var(--card-background, #ffffff);\n border-radius: 12px;\n box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);\n overflow: hidden;\n display: flex;\n flex-direction: column;\n}\n\n.panel-header[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 16px 20px;\n background: var(--header-background, #f9fafb);\n border-bottom: 1px solid var(--border-color, #e5e7eb);\n}\n\n.panel-title[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 10px;\n font-weight: 600;\n font-size: 14px;\n color: var(--text-primary, #1f2937);\n}\n\n.panel-title[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: var(--accent-color, #6366f1);\n}\n\n.panel-subtitle[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.panel-action[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 6px;\n padding: 6px 12px;\n background: transparent;\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 6px;\n font-size: 12px;\n font-weight: 500;\n color: var(--text-secondary, #6b7280);\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.panel-action[_ngcontent-%COMP%]:hover {\n background: var(--accent-color, #6366f1);\n border-color: var(--accent-color, #6366f1);\n color: white;\n}\n\n.panel-body[_ngcontent-%COMP%] {\n padding: 20px;\n flex: 1;\n overflow-y: auto;\n}\n\n\n\n.category-chart[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n gap: 24px;\n height: 100%;\n}\n\n.donut-chart-container[_ngcontent-%COMP%] {\n position: relative;\n width: 200px;\n height: 200px;\n margin: 0 auto;\n}\n\n.donut-chart[_ngcontent-%COMP%] {\n width: 100%;\n height: 100%;\n transform: rotate(-90deg);\n}\n\n.donut-segment[_ngcontent-%COMP%] {\n cursor: pointer;\n transition: opacity 0.2s ease;\n}\n\n.donut-segment[_ngcontent-%COMP%]:hover {\n opacity: 0.8;\n}\n\n.donut-center[_ngcontent-%COMP%] {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n text-align: center;\n}\n\n.donut-total[_ngcontent-%COMP%] {\n font-size: 32px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.donut-label[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n\n\n.category-legend[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.legend-item[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n padding: 10px 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.legend-item[_ngcontent-%COMP%]:hover {\n background: var(--item-hover, #f3f4f6);\n transform: translateX(4px);\n}\n\n.legend-color[_ngcontent-%COMP%] {\n width: 12px;\n height: 12px;\n border-radius: 4px;\n margin-right: 12px;\n flex-shrink: 0;\n}\n\n.legend-info[_ngcontent-%COMP%] {\n flex: 1;\n}\n\n.legend-name[_ngcontent-%COMP%] {\n font-size: 14px;\n font-weight: 500;\n color: var(--text-primary, #1f2937);\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n.legend-name[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n.legend-value[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n.legend-arrow[_ngcontent-%COMP%] {\n color: var(--text-tertiary, #9ca3af);\n font-size: 10px;\n}\n\n\n\n.type-list[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n gap: 12px;\n}\n\n.type-item[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.type-item[_ngcontent-%COMP%]:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.type-info[_ngcontent-%COMP%] {\n flex: 1;\n min-width: 0;\n}\n\n.type-name[_ngcontent-%COMP%] {\n font-size: 14px;\n font-weight: 600;\n color: var(--text-primary, #1f2937);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.type-category[_ngcontent-%COMP%] {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n margin-top: 2px;\n}\n\n.type-stats[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n align-items: flex-end;\n gap: 4px;\n flex-shrink: 0;\n margin-left: 16px;\n}\n\n.type-count[_ngcontent-%COMP%] {\n display: flex;\n align-items: baseline;\n gap: 4px;\n}\n\n.count-value[_ngcontent-%COMP%] {\n font-size: 16px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.count-label[_ngcontent-%COMP%] {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.type-bar[_ngcontent-%COMP%] {\n width: 100px;\n height: 4px;\n background: #e5e7eb;\n border-radius: 2px;\n overflow: hidden;\n}\n\n.type-bar-fill[_ngcontent-%COMP%] {\n height: 100%;\n background: linear-gradient(90deg, #6366f1, #8b5cf6);\n border-radius: 2px;\n transition: width 0.3s ease;\n}\n\n.type-indicators[_ngcontent-%COMP%] {\n display: flex;\n gap: 8px;\n}\n\n.indicator[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 4px;\n font-size: 11px;\n}\n\n.indicator.active[_ngcontent-%COMP%] {\n color: #10b981;\n}\n\n.indicator.warning[_ngcontent-%COMP%] {\n color: #f59e0b;\n}\n\n.indicator[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 6px;\n}\n\n\n\n.activity-list[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.activity-item[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n padding: 10px 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.activity-item[_ngcontent-%COMP%]:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.activity-icon[_ngcontent-%COMP%] {\n width: 32px;\n height: 32px;\n display: flex;\n align-items: center;\n justify-content: center;\n background: var(--icon-background, #e0e7ff);\n border-radius: 6px;\n margin-right: 12px;\n flex-shrink: 0;\n}\n\n.activity-icon[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 12px;\n color: var(--accent-color, #6366f1);\n}\n\n.activity-icon.action-created[_ngcontent-%COMP%] {\n background: #d1fae5;\n}\n\n.activity-icon.action-created[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: #059669;\n}\n\n.activity-icon.action-updated[_ngcontent-%COMP%] {\n background: #e0e7ff;\n}\n\n.activity-icon.action-updated[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: #6366f1;\n}\n\n.activity-icon.action-accessed[_ngcontent-%COMP%] {\n background: #fef3c7;\n}\n\n.activity-icon.action-accessed[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: #d97706;\n}\n\n.activity-icon.action-rotated[_ngcontent-%COMP%] {\n background: #dbeafe;\n}\n\n.activity-icon.action-rotated[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n color: #3b82f6;\n}\n\n.activity-info[_ngcontent-%COMP%] {\n flex: 1;\n min-width: 0;\n}\n\n.activity-name[_ngcontent-%COMP%] {\n font-weight: 500;\n font-size: 13px;\n color: var(--text-primary, #1f2937);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.activity-meta[_ngcontent-%COMP%] {\n display: flex;\n align-items: center;\n gap: 6px;\n margin-top: 2px;\n font-size: 11px;\n color: var(--text-secondary, #6b7280);\n}\n\n.activity-type[_ngcontent-%COMP%] {\n background: var(--tag-background, #e5e7eb);\n padding: 1px 6px;\n border-radius: 4px;\n}\n\n.activity-action[_ngcontent-%COMP%] {\n font-weight: 500;\n}\n\n.activity-time[_ngcontent-%COMP%] {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n white-space: nowrap;\n}\n\n\n\n.quick-actions[_ngcontent-%COMP%] {\n margin-bottom: 24px;\n}\n\n.quick-actions-title[_ngcontent-%COMP%] {\n font-size: 14px;\n font-weight: 600;\n color: var(--text-primary, #1f2937);\n margin-bottom: 12px;\n}\n\n.quick-actions-grid[_ngcontent-%COMP%] {\n display: grid;\n grid-template-columns: repeat(auto-fit, minmax(140px, 1fr));\n gap: 12px;\n}\n\n.quick-action[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n align-items: center;\n gap: 8px;\n padding: 16px;\n background: var(--card-background, #ffffff);\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 10px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.quick-action[_ngcontent-%COMP%]:hover {\n border-color: var(--accent-color, #6366f1);\n background: #f5f3ff;\n transform: translateY(-2px);\n}\n\n.quick-action[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 20px;\n color: var(--accent-color, #6366f1);\n}\n\n.quick-action[_ngcontent-%COMP%] span[_ngcontent-%COMP%] {\n font-size: 12px;\n font-weight: 500;\n color: var(--text-secondary, #6b7280);\n}\n\n\n\n.empty-state[_ngcontent-%COMP%] {\n display: flex;\n flex-direction: column;\n align-items: center;\n justify-content: center;\n padding: 32px;\n color: var(--text-secondary, #6b7280);\n text-align: center;\n}\n\n.empty-state[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 32px;\n margin-bottom: 12px;\n opacity: 0.5;\n}\n\n\n\n.security-notice[_ngcontent-%COMP%] {\n display: flex;\n align-items: flex-start;\n padding: 16px 20px;\n background: linear-gradient(135deg, #eff6ff 0%, #dbeafe 100%);\n border-radius: 12px;\n border: 1px solid #bfdbfe;\n}\n\n.security-notice[_ngcontent-%COMP%] i[_ngcontent-%COMP%] {\n font-size: 20px;\n color: #3b82f6;\n margin-right: 12px;\n margin-top: 2px;\n}\n\n.notice-content[_ngcontent-%COMP%] {\n font-size: 13px;\n color: #1e40af;\n line-height: 1.5;\n}\n\n.notice-content[_ngcontent-%COMP%] strong[_ngcontent-%COMP%] {\n font-weight: 600;\n}\n\n\n\n@media (max-width: 1024px) {\n .content-grid[_ngcontent-%COMP%] {\n grid-template-columns: 1fr;\n }\n\n .category-panel[_ngcontent-%COMP%] {\n grid-row: auto;\n }\n\n .category-chart[_ngcontent-%COMP%] {\n flex-direction: row;\n align-items: center;\n }\n\n .donut-chart-container[_ngcontent-%COMP%] {\n width: 160px;\n height: 160px;\n }\n\n .category-legend[_ngcontent-%COMP%] {\n flex: 1;\n }\n}\n\n@media (max-width: 768px) {\n .overview-container[_ngcontent-%COMP%] {\n padding: 16px;\n }\n\n .overview-header[_ngcontent-%COMP%] {\n flex-direction: column;\n gap: 16px;\n }\n\n .header-actions[_ngcontent-%COMP%] {\n width: 100%;\n justify-content: flex-end;\n }\n\n .health-banner[_ngcontent-%COMP%] {\n flex-direction: column;\n text-align: center;\n }\n\n .health-score-container[_ngcontent-%COMP%] {\n margin-right: 0;\n margin-bottom: 16px;\n }\n\n .kpi-row[_ngcontent-%COMP%] {\n grid-template-columns: repeat(2, 1fr);\n }\n\n .category-chart[_ngcontent-%COMP%] {\n flex-direction: column;\n }\n\n .quick-actions-grid[_ngcontent-%COMP%] {\n grid-template-columns: repeat(2, 1fr);\n }\n}"], changeDetection: 0 });
|
|
926
|
+
};
|
|
927
|
+
CredentialsOverviewResourceComponent = __decorate([
|
|
928
|
+
RegisterClass(BaseResourceComponent, 'CredentialsOverviewResource')
|
|
929
|
+
], CredentialsOverviewResourceComponent);
|
|
930
|
+
export { CredentialsOverviewResourceComponent };
|
|
931
|
+
(() => { (typeof ngDevMode === "undefined" || ngDevMode) && i0.ɵsetClassMetadata(CredentialsOverviewResourceComponent, [{
|
|
932
|
+
type: Component,
|
|
933
|
+
args: [{ selector: 'mj-credentials-overview-resource', changeDetection: ChangeDetectionStrategy.OnPush, template: "<div class=\"overview-container\">\n <mj-loading *ngIf=\"isLoading\" text=\"Loading overview...\"></mj-loading>\n\n <ng-container *ngIf=\"!isLoading\">\n <!-- Header with Actions -->\n <div class=\"overview-header\">\n <div class=\"header-left\">\n <h2 class=\"overview-title\">Credential Overview</h2>\n <p class=\"overview-subtitle\">Monitor and manage your organization's credentials</p>\n </div>\n <div class=\"header-actions\">\n <button class=\"btn-refresh\" (click)=\"refresh()\" title=\"Refresh\">\n <i class=\"fa-solid fa-refresh\"></i>\n </button>\n <button class=\"btn-primary\" *ngIf=\"UserCanCreateCredentials\" (click)=\"createNewCredential()\">\n <i class=\"fa-solid fa-plus\"></i>\n <span>New Credential</span>\n </button>\n </div>\n </div>\n\n <!-- Health Score Banner -->\n <div class=\"health-banner\" [ngClass]=\"getHealthClass()\">\n <div class=\"health-score-container\">\n <div class=\"health-score-ring\">\n <svg viewBox=\"0 0 36 36\" class=\"circular-chart\">\n <path class=\"circle-bg\"\n d=\"M18 2.0845\n a 15.9155 15.9155 0 0 1 0 31.831\n a 15.9155 15.9155 0 0 1 0 -31.831\"\n />\n <path class=\"circle\"\n [attr.stroke-dasharray]=\"getHealthScore() + ', 100'\"\n d=\"M18 2.0845\n a 15.9155 15.9155 0 0 1 0 31.831\n a 15.9155 15.9155 0 0 1 0 -31.831\"\n />\n </svg>\n <div class=\"health-score-value\">{{getHealthScore()}}</div>\n </div>\n </div>\n <div class=\"health-info\">\n <div class=\"health-label\">{{getHealthLabel()}}</div>\n <div class=\"health-details\">\n <span *ngIf=\"expiredCredentials > 0\" class=\"health-alert\">\n <i class=\"fa-solid fa-circle-exclamation\"></i>\n {{expiredCredentials}} expired\n </span>\n <span *ngIf=\"expiringSoonCount > 0\" class=\"health-warning-text\" (click)=\"viewExpiringCredentials()\">\n <i class=\"fa-solid fa-clock\"></i>\n {{expiringSoonCount}} expiring soon\n </span>\n <span *ngIf=\"expiredCredentials === 0 && expiringSoonCount === 0\" class=\"health-ok\">\n <i class=\"fa-solid fa-check-circle\"></i>\n All credentials healthy\n </span>\n </div>\n </div>\n </div>\n\n <!-- KPI Cards Row -->\n <div class=\"kpi-row\">\n <div class=\"kpi-card clickable\" (click)=\"viewAllCredentials()\">\n <div class=\"kpi-icon\">\n <i class=\"fa-solid fa-key\"></i>\n </div>\n <div class=\"kpi-content\">\n <div class=\"kpi-value\">{{totalCredentials}}</div>\n <div class=\"kpi-label\">Total Credentials</div>\n </div>\n <div class=\"kpi-trend\">\n <i class=\"fa-solid fa-arrow-right\"></i>\n </div>\n </div>\n\n <div class=\"kpi-card active clickable\" (click)=\"viewAllCredentials()\">\n <div class=\"kpi-icon\">\n <i class=\"fa-solid fa-check-circle\"></i>\n </div>\n <div class=\"kpi-content\">\n <div class=\"kpi-value\">{{activeCredentials}}</div>\n <div class=\"kpi-label\">Active</div>\n </div>\n <div class=\"kpi-trend success\">\n <span class=\"percentage\">{{totalCredentials > 0 ? (activeCredentials / totalCredentials * 100).toFixed(0) : 0}}%</span>\n </div>\n </div>\n\n <div class=\"kpi-card\">\n <div class=\"kpi-icon\">\n <i class=\"fa-solid fa-cubes\"></i>\n </div>\n <div class=\"kpi-content\">\n <div class=\"kpi-value\">{{credentialTypes}}</div>\n <div class=\"kpi-label\">Types</div>\n </div>\n </div>\n\n <div class=\"kpi-card clickable\" [class.warning]=\"expiringSoonCount > 0\" (click)=\"viewExpiringCredentials()\">\n <div class=\"kpi-icon\">\n <i class=\"fa-solid fa-clock\"></i>\n </div>\n <div class=\"kpi-content\">\n <div class=\"kpi-value\">{{expiringSoonCount}}</div>\n <div class=\"kpi-label\">Expiring Soon</div>\n </div>\n <div class=\"kpi-trend warning\" *ngIf=\"expiringSoonCount > 0\">\n <i class=\"fa-solid fa-arrow-right\"></i>\n </div>\n </div>\n\n <div class=\"kpi-card\" [class.danger]=\"expiredCredentials > 0\">\n <div class=\"kpi-icon\">\n <i class=\"fa-solid fa-circle-xmark\"></i>\n </div>\n <div class=\"kpi-content\">\n <div class=\"kpi-value\">{{expiredCredentials}}</div>\n <div class=\"kpi-label\">Expired</div>\n </div>\n </div>\n </div>\n\n <!-- Content Grid -->\n <div class=\"content-grid\">\n <!-- Category Distribution Chart -->\n <div class=\"panel category-panel\">\n <div class=\"panel-header\">\n <div class=\"panel-title\">\n <i class=\"fa-solid fa-chart-pie\"></i>\n <span>Credentials by Category</span>\n </div>\n <span class=\"panel-subtitle\">Click to filter by category</span>\n </div>\n <div class=\"panel-body\">\n <div class=\"category-chart\" *ngIf=\"categoryStats.length > 0\">\n <!-- Visual Donut Chart -->\n <div class=\"donut-chart-container\">\n <svg viewBox=\"0 0 100 100\" class=\"donut-chart\">\n <circle cx=\"50\" cy=\"50\" r=\"40\" fill=\"none\" stroke=\"#e5e7eb\" stroke-width=\"12\"/>\n <ng-container *ngFor=\"let stat of categoryStats; let i = index\">\n <circle\n cx=\"50\" cy=\"50\" r=\"40\"\n fill=\"none\"\n [attr.stroke]=\"stat.color\"\n stroke-width=\"12\"\n [attr.stroke-dasharray]=\"stat.percentage * 2.51 + ' ' + (251 - stat.percentage * 2.51)\"\n [attr.stroke-dashoffset]=\"getDonutOffset(i)\"\n class=\"donut-segment\"\n (click)=\"onCategoryClick(stat)\"\n />\n </ng-container>\n </svg>\n <div class=\"donut-center\">\n <div class=\"donut-total\">{{totalCredentials}}</div>\n <div class=\"donut-label\">Total</div>\n </div>\n </div>\n <!-- Legend -->\n <div class=\"category-legend\">\n <div class=\"legend-item\" *ngFor=\"let stat of categoryStats\" (click)=\"onCategoryClick(stat)\">\n <div class=\"legend-color\" [style.backgroundColor]=\"stat.color\"></div>\n <div class=\"legend-info\">\n <div class=\"legend-name\">\n <i [class]=\"stat.iconClass\"></i>\n {{stat.category}}\n </div>\n <div class=\"legend-value\">{{stat.count}} ({{stat.percentage}}%)</div>\n </div>\n <i class=\"fa-solid fa-chevron-right legend-arrow\"></i>\n </div>\n </div>\n </div>\n <div class=\"empty-state\" *ngIf=\"categoryStats.length === 0\">\n <i class=\"fa-solid fa-folder-open\"></i>\n <span>No credentials configured</span>\n </div>\n </div>\n </div>\n\n <!-- Types Breakdown -->\n <div class=\"panel types-panel\">\n <div class=\"panel-header\">\n <div class=\"panel-title\">\n <i class=\"fa-solid fa-cubes\"></i>\n <span>Top Credential Types</span>\n </div>\n <button class=\"panel-action\" (click)=\"viewAllTypes()\">\n View All <i class=\"fa-solid fa-arrow-right\"></i>\n </button>\n </div>\n <div class=\"panel-body\">\n <div class=\"type-list\" *ngIf=\"typeStats.length > 0\">\n <div class=\"type-item\" *ngFor=\"let type of typeStats.slice(0, 6)\" (click)=\"onTypeClick(type)\">\n <div class=\"type-info\">\n <div class=\"type-name\">{{type.typeName}}</div>\n <div class=\"type-category\">{{type.category}}</div>\n </div>\n <div class=\"type-stats\">\n <div class=\"type-count\">\n <span class=\"count-value\">{{type.credentialCount}}</span>\n <span class=\"count-label\">credentials</span>\n </div>\n <div class=\"type-bar\">\n <div class=\"type-bar-fill\"\n [style.width.%]=\"totalCredentials > 0 ? (type.credentialCount / totalCredentials * 100) : 0\">\n </div>\n </div>\n <div class=\"type-indicators\">\n <span class=\"indicator active\" *ngIf=\"type.activeCount > 0\" title=\"Active\">\n <i class=\"fa-solid fa-circle\"></i> {{type.activeCount}}\n </span>\n <span class=\"indicator warning\" *ngIf=\"type.expiringCount > 0\" title=\"Expiring Soon\">\n <i class=\"fa-solid fa-clock\"></i> {{type.expiringCount}}\n </span>\n </div>\n </div>\n </div>\n </div>\n <div class=\"empty-state\" *ngIf=\"typeStats.length === 0\">\n <i class=\"fa-solid fa-shapes\"></i>\n <span>No credential types configured</span>\n </div>\n </div>\n </div>\n\n <!-- Recent Activity -->\n <div class=\"panel activity-panel\">\n <div class=\"panel-header\">\n <div class=\"panel-title\">\n <i class=\"fa-solid fa-clock-rotate-left\"></i>\n <span>Recent Activity</span>\n </div>\n <button class=\"panel-action\" (click)=\"viewAuditLog()\">\n View All <i class=\"fa-solid fa-arrow-right\"></i>\n </button>\n </div>\n <div class=\"panel-body\">\n <div class=\"activity-list\" *ngIf=\"recentActivity.length > 0\">\n <div class=\"activity-item\" *ngFor=\"let activity of recentActivity\" (click)=\"onActivityClick(activity)\">\n <div class=\"activity-icon\" [ngClass]=\"getActionClass(activity.action)\">\n <i [class]=\"getActionIcon(activity.action)\"></i>\n </div>\n <div class=\"activity-info\">\n <div class=\"activity-name\">{{activity.credentialName}}</div>\n <div class=\"activity-meta\">\n <span class=\"activity-type\">{{activity.typeName}}</span>\n <span class=\"activity-action\">{{activity.action}}</span>\n <span class=\"activity-user\" *ngIf=\"activity.user\">by {{activity.user}}</span>\n </div>\n </div>\n <div class=\"activity-time\">\n {{formatDate(activity.date)}}\n </div>\n </div>\n </div>\n <div class=\"empty-state\" *ngIf=\"recentActivity.length === 0\">\n <i class=\"fa-solid fa-inbox\"></i>\n <span>No recent activity</span>\n </div>\n </div>\n </div>\n </div>\n\n <!-- Quick Actions -->\n <div class=\"quick-actions\" *ngIf=\"UserCanCreateCredentials\">\n <div class=\"quick-actions-title\">Quick Actions</div>\n <div class=\"quick-actions-grid\">\n <button class=\"quick-action\" (click)=\"createNewCredential()\">\n <i class=\"fa-solid fa-plus\"></i>\n <span>Add Credential</span>\n </button>\n <button class=\"quick-action\" (click)=\"viewAllTypes()\">\n <i class=\"fa-solid fa-shapes\"></i>\n <span>Manage Types</span>\n </button>\n <button class=\"quick-action\" (click)=\"viewAllCategories()\">\n <i class=\"fa-solid fa-folder-tree\"></i>\n <span>Categories</span>\n </button>\n <button class=\"quick-action\" (click)=\"viewAuditLog()\">\n <i class=\"fa-solid fa-clipboard-list\"></i>\n <span>Audit Log</span>\n </button>\n </div>\n </div>\n\n <!-- Security Notice -->\n <div class=\"security-notice\">\n <i class=\"fa-solid fa-shield-check\"></i>\n <div class=\"notice-content\">\n <strong>Security Note:</strong> All credential values are encrypted.\n Access to credentials is logged in the audit trail for compliance and security monitoring.\n </div>\n </div>\n </ng-container>\n</div>\n", styles: [".overview-container {\n padding: 24px;\n height: 100%;\n overflow-y: auto;\n}\n\n/* Header */\n.overview-header {\n display: flex;\n justify-content: space-between;\n align-items: flex-start;\n margin-bottom: 24px;\n}\n\n.header-left {\n flex: 1;\n}\n\n.overview-title {\n font-size: 24px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n margin: 0 0 4px 0;\n}\n\n.overview-subtitle {\n font-size: 14px;\n color: var(--text-secondary, #6b7280);\n margin: 0;\n}\n\n.header-actions {\n display: flex;\n gap: 12px;\n}\n\n.btn-refresh {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 40px;\n height: 40px;\n background: var(--card-background, #ffffff);\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.btn-refresh:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.btn-refresh i {\n color: var(--text-secondary, #6b7280);\n}\n\n.btn-primary {\n display: flex;\n align-items: center;\n gap: 8px;\n padding: 10px 20px;\n background: linear-gradient(135deg, #6366f1 0%, #4f46e5 100%);\n color: white;\n border: none;\n border-radius: 8px;\n font-weight: 600;\n font-size: 14px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.btn-primary:hover {\n transform: translateY(-1px);\n box-shadow: 0 4px 12px rgba(99, 102, 241, 0.4);\n}\n\n/* Health Banner */\n.health-banner {\n display: flex;\n align-items: center;\n padding: 20px 24px;\n background: linear-gradient(135deg, #ecfdf5 0%, #d1fae5 100%);\n border: 1px solid #a7f3d0;\n border-radius: 16px;\n margin-bottom: 24px;\n}\n\n.health-banner.health-warning {\n background: linear-gradient(135deg, #fffbeb 0%, #fef3c7 100%);\n border-color: #fcd34d;\n}\n\n.health-banner.health-critical {\n background: linear-gradient(135deg, #fef2f2 0%, #fee2e2 100%);\n border-color: #fca5a5;\n}\n\n.health-score-container {\n margin-right: 24px;\n}\n\n.health-score-ring {\n position: relative;\n width: 80px;\n height: 80px;\n}\n\n.circular-chart {\n display: block;\n margin: 0 auto;\n max-height: 80px;\n transform: rotate(-90deg);\n}\n\n.circle-bg {\n fill: none;\n stroke: #e5e7eb;\n stroke-width: 3.8;\n}\n\n.circle {\n fill: none;\n stroke-width: 3.8;\n stroke-linecap: round;\n stroke: #10b981;\n animation: progress 1s ease-out forwards;\n}\n\n.health-banner.health-warning .circle {\n stroke: #f59e0b;\n}\n\n.health-banner.health-critical .circle {\n stroke: #ef4444;\n}\n\n@keyframes progress {\n 0% {\n stroke-dasharray: 0 100;\n }\n}\n\n.health-score-value {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n font-size: 20px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.health-info {\n flex: 1;\n}\n\n.health-label {\n font-size: 18px;\n font-weight: 700;\n color: #059669;\n margin-bottom: 4px;\n}\n\n.health-banner.health-warning .health-label {\n color: #d97706;\n}\n\n.health-banner.health-critical .health-label {\n color: #dc2626;\n}\n\n.health-details {\n display: flex;\n gap: 16px;\n flex-wrap: wrap;\n}\n\n.health-alert {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #dc2626;\n font-weight: 500;\n font-size: 14px;\n}\n\n.health-warning-text {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #d97706;\n font-weight: 500;\n font-size: 14px;\n cursor: pointer;\n}\n\n.health-warning-text:hover {\n text-decoration: underline;\n}\n\n.health-ok {\n display: flex;\n align-items: center;\n gap: 6px;\n color: #059669;\n font-weight: 500;\n font-size: 14px;\n}\n\n/* KPI Cards */\n.kpi-row {\n display: grid;\n grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));\n gap: 16px;\n margin-bottom: 24px;\n}\n\n.kpi-card {\n display: flex;\n align-items: center;\n padding: 16px 20px;\n background: var(--card-background, #ffffff);\n border-radius: 12px;\n box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);\n transition: transform 0.2s ease, box-shadow 0.2s ease;\n}\n\n.kpi-card.clickable {\n cursor: pointer;\n}\n\n.kpi-card.clickable:hover {\n transform: translateY(-2px);\n box-shadow: 0 4px 16px rgba(0, 0, 0, 0.12);\n}\n\n.kpi-card.active .kpi-icon {\n background: linear-gradient(135deg, #10b981 0%, #059669 100%);\n}\n\n.kpi-card.warning .kpi-icon {\n background: linear-gradient(135deg, #f59e0b 0%, #d97706 100%);\n}\n\n.kpi-card.danger .kpi-icon {\n background: linear-gradient(135deg, #ef4444 0%, #dc2626 100%);\n}\n\n.kpi-icon {\n width: 48px;\n height: 48px;\n display: flex;\n align-items: center;\n justify-content: center;\n background: linear-gradient(135deg, #6366f1 0%, #4f46e5 100%);\n border-radius: 10px;\n margin-right: 14px;\n flex-shrink: 0;\n}\n\n.kpi-icon i {\n font-size: 20px;\n color: white;\n}\n\n.kpi-content {\n flex: 1;\n min-width: 0;\n}\n\n.kpi-value {\n font-size: 24px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n line-height: 1.2;\n}\n\n.kpi-label {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n margin-top: 2px;\n white-space: nowrap;\n}\n\n.kpi-trend {\n display: flex;\n align-items: center;\n margin-left: 8px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.kpi-trend.success {\n color: #10b981;\n}\n\n.kpi-trend.warning {\n color: #f59e0b;\n}\n\n.kpi-trend .percentage {\n font-size: 12px;\n font-weight: 600;\n}\n\n/* Content Grid */\n.content-grid {\n display: grid;\n grid-template-columns: 1fr 1fr;\n grid-template-rows: auto auto;\n gap: 20px;\n margin-bottom: 24px;\n}\n\n.category-panel {\n grid-row: span 2;\n}\n\n.panel {\n background: var(--card-background, #ffffff);\n border-radius: 12px;\n box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);\n overflow: hidden;\n display: flex;\n flex-direction: column;\n}\n\n.panel-header {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 16px 20px;\n background: var(--header-background, #f9fafb);\n border-bottom: 1px solid var(--border-color, #e5e7eb);\n}\n\n.panel-title {\n display: flex;\n align-items: center;\n gap: 10px;\n font-weight: 600;\n font-size: 14px;\n color: var(--text-primary, #1f2937);\n}\n\n.panel-title i {\n color: var(--accent-color, #6366f1);\n}\n\n.panel-subtitle {\n font-size: 12px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.panel-action {\n display: flex;\n align-items: center;\n gap: 6px;\n padding: 6px 12px;\n background: transparent;\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 6px;\n font-size: 12px;\n font-weight: 500;\n color: var(--text-secondary, #6b7280);\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.panel-action:hover {\n background: var(--accent-color, #6366f1);\n border-color: var(--accent-color, #6366f1);\n color: white;\n}\n\n.panel-body {\n padding: 20px;\n flex: 1;\n overflow-y: auto;\n}\n\n/* Category Chart */\n.category-chart {\n display: flex;\n flex-direction: column;\n gap: 24px;\n height: 100%;\n}\n\n.donut-chart-container {\n position: relative;\n width: 200px;\n height: 200px;\n margin: 0 auto;\n}\n\n.donut-chart {\n width: 100%;\n height: 100%;\n transform: rotate(-90deg);\n}\n\n.donut-segment {\n cursor: pointer;\n transition: opacity 0.2s ease;\n}\n\n.donut-segment:hover {\n opacity: 0.8;\n}\n\n.donut-center {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n text-align: center;\n}\n\n.donut-total {\n font-size: 32px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.donut-label {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n/* Category Legend */\n.category-legend {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.legend-item {\n display: flex;\n align-items: center;\n padding: 10px 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.legend-item:hover {\n background: var(--item-hover, #f3f4f6);\n transform: translateX(4px);\n}\n\n.legend-color {\n width: 12px;\n height: 12px;\n border-radius: 4px;\n margin-right: 12px;\n flex-shrink: 0;\n}\n\n.legend-info {\n flex: 1;\n}\n\n.legend-name {\n font-size: 14px;\n font-weight: 500;\n color: var(--text-primary, #1f2937);\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n.legend-name i {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n.legend-value {\n font-size: 12px;\n color: var(--text-secondary, #6b7280);\n}\n\n.legend-arrow {\n color: var(--text-tertiary, #9ca3af);\n font-size: 10px;\n}\n\n/* Type List */\n.type-list {\n display: flex;\n flex-direction: column;\n gap: 12px;\n}\n\n.type-item {\n display: flex;\n align-items: center;\n justify-content: space-between;\n padding: 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.type-item:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.type-info {\n flex: 1;\n min-width: 0;\n}\n\n.type-name {\n font-size: 14px;\n font-weight: 600;\n color: var(--text-primary, #1f2937);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.type-category {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n margin-top: 2px;\n}\n\n.type-stats {\n display: flex;\n flex-direction: column;\n align-items: flex-end;\n gap: 4px;\n flex-shrink: 0;\n margin-left: 16px;\n}\n\n.type-count {\n display: flex;\n align-items: baseline;\n gap: 4px;\n}\n\n.count-value {\n font-size: 16px;\n font-weight: 700;\n color: var(--text-primary, #1f2937);\n}\n\n.count-label {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n}\n\n.type-bar {\n width: 100px;\n height: 4px;\n background: #e5e7eb;\n border-radius: 2px;\n overflow: hidden;\n}\n\n.type-bar-fill {\n height: 100%;\n background: linear-gradient(90deg, #6366f1, #8b5cf6);\n border-radius: 2px;\n transition: width 0.3s ease;\n}\n\n.type-indicators {\n display: flex;\n gap: 8px;\n}\n\n.indicator {\n display: flex;\n align-items: center;\n gap: 4px;\n font-size: 11px;\n}\n\n.indicator.active {\n color: #10b981;\n}\n\n.indicator.warning {\n color: #f59e0b;\n}\n\n.indicator i {\n font-size: 6px;\n}\n\n/* Activity List */\n.activity-list {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.activity-item {\n display: flex;\n align-items: center;\n padding: 10px 12px;\n background: var(--item-background, #f9fafb);\n border-radius: 8px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.activity-item:hover {\n background: var(--item-hover, #f3f4f6);\n}\n\n.activity-icon {\n width: 32px;\n height: 32px;\n display: flex;\n align-items: center;\n justify-content: center;\n background: var(--icon-background, #e0e7ff);\n border-radius: 6px;\n margin-right: 12px;\n flex-shrink: 0;\n}\n\n.activity-icon i {\n font-size: 12px;\n color: var(--accent-color, #6366f1);\n}\n\n.activity-icon.action-created {\n background: #d1fae5;\n}\n\n.activity-icon.action-created i {\n color: #059669;\n}\n\n.activity-icon.action-updated {\n background: #e0e7ff;\n}\n\n.activity-icon.action-updated i {\n color: #6366f1;\n}\n\n.activity-icon.action-accessed {\n background: #fef3c7;\n}\n\n.activity-icon.action-accessed i {\n color: #d97706;\n}\n\n.activity-icon.action-rotated {\n background: #dbeafe;\n}\n\n.activity-icon.action-rotated i {\n color: #3b82f6;\n}\n\n.activity-info {\n flex: 1;\n min-width: 0;\n}\n\n.activity-name {\n font-weight: 500;\n font-size: 13px;\n color: var(--text-primary, #1f2937);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.activity-meta {\n display: flex;\n align-items: center;\n gap: 6px;\n margin-top: 2px;\n font-size: 11px;\n color: var(--text-secondary, #6b7280);\n}\n\n.activity-type {\n background: var(--tag-background, #e5e7eb);\n padding: 1px 6px;\n border-radius: 4px;\n}\n\n.activity-action {\n font-weight: 500;\n}\n\n.activity-time {\n font-size: 11px;\n color: var(--text-tertiary, #9ca3af);\n white-space: nowrap;\n}\n\n/* Quick Actions */\n.quick-actions {\n margin-bottom: 24px;\n}\n\n.quick-actions-title {\n font-size: 14px;\n font-weight: 600;\n color: var(--text-primary, #1f2937);\n margin-bottom: 12px;\n}\n\n.quick-actions-grid {\n display: grid;\n grid-template-columns: repeat(auto-fit, minmax(140px, 1fr));\n gap: 12px;\n}\n\n.quick-action {\n display: flex;\n flex-direction: column;\n align-items: center;\n gap: 8px;\n padding: 16px;\n background: var(--card-background, #ffffff);\n border: 1px solid var(--border-color, #e5e7eb);\n border-radius: 10px;\n cursor: pointer;\n transition: all 0.2s ease;\n}\n\n.quick-action:hover {\n border-color: var(--accent-color, #6366f1);\n background: #f5f3ff;\n transform: translateY(-2px);\n}\n\n.quick-action i {\n font-size: 20px;\n color: var(--accent-color, #6366f1);\n}\n\n.quick-action span {\n font-size: 12px;\n font-weight: 500;\n color: var(--text-secondary, #6b7280);\n}\n\n/* Empty State */\n.empty-state {\n display: flex;\n flex-direction: column;\n align-items: center;\n justify-content: center;\n padding: 32px;\n color: var(--text-secondary, #6b7280);\n text-align: center;\n}\n\n.empty-state i {\n font-size: 32px;\n margin-bottom: 12px;\n opacity: 0.5;\n}\n\n/* Security Notice */\n.security-notice {\n display: flex;\n align-items: flex-start;\n padding: 16px 20px;\n background: linear-gradient(135deg, #eff6ff 0%, #dbeafe 100%);\n border-radius: 12px;\n border: 1px solid #bfdbfe;\n}\n\n.security-notice i {\n font-size: 20px;\n color: #3b82f6;\n margin-right: 12px;\n margin-top: 2px;\n}\n\n.notice-content {\n font-size: 13px;\n color: #1e40af;\n line-height: 1.5;\n}\n\n.notice-content strong {\n font-weight: 600;\n}\n\n/* Responsive */\n@media (max-width: 1024px) {\n .content-grid {\n grid-template-columns: 1fr;\n }\n\n .category-panel {\n grid-row: auto;\n }\n\n .category-chart {\n flex-direction: row;\n align-items: center;\n }\n\n .donut-chart-container {\n width: 160px;\n height: 160px;\n }\n\n .category-legend {\n flex: 1;\n }\n}\n\n@media (max-width: 768px) {\n .overview-container {\n padding: 16px;\n }\n\n .overview-header {\n flex-direction: column;\n gap: 16px;\n }\n\n .header-actions {\n width: 100%;\n justify-content: flex-end;\n }\n\n .health-banner {\n flex-direction: column;\n text-align: center;\n }\n\n .health-score-container {\n margin-right: 0;\n margin-bottom: 16px;\n }\n\n .kpi-row {\n grid-template-columns: repeat(2, 1fr);\n }\n\n .category-chart {\n flex-direction: column;\n }\n\n .quick-actions-grid {\n grid-template-columns: repeat(2, 1fr);\n }\n}\n"] }]
|
|
934
|
+
}], () => [{ type: i0.ChangeDetectorRef }, { type: i1.NavigationService }], null); })();
|
|
935
|
+
(() => { (typeof ngDevMode === "undefined" || ngDevMode) && i0.ɵsetClassDebugInfo(CredentialsOverviewResourceComponent, { className: "CredentialsOverviewResourceComponent", filePath: "src/Credentials/components/credentials-overview-resource.component.ts", lineNumber: 54 }); })();
|
|
936
|
+
//# sourceMappingURL=credentials-overview-resource.component.js.map
|