@posiwise/smart-crm 0.0.34 → 0.0.36
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/esm2022/index.mjs +6 -3
- package/esm2022/lib/private/components/smart-crm-accounts/smart-crm-account-files/smart-crm-account-files.component.mjs +3 -3
- package/esm2022/lib/private/components/smart-crm-accounts/smart-crm-account-info/smart-crm-account-info.component.mjs +16 -15
- package/esm2022/lib/private/components/smart-crm-accounts/smart-crm-accounts.component.mjs +3 -3
- package/esm2022/lib/private/components/smart-crm-configuration/smart-crm-actions/smart-crm-actions.component.mjs +2 -2
- package/esm2022/lib/private/components/smart-crm-configuration/smart-crm-configuration.component.mjs +2 -2
- package/esm2022/lib/private/components/smart-crm-contacts/smart-crm-contact-info/smart-crm-contact-info.component.mjs +6 -5
- package/esm2022/lib/private/components/smart-crm-contacts/smart-crm-contacts.component.mjs +21 -9
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-account-insight/smart-crm-account-insight.component.mjs +196 -0
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-analysis-insight/smart-crm-analysis.component.mjs +128 -0
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-contact-insight/smart-crm-contact-insight.component.mjs +94 -0
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-insight.component.mjs +19 -6
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-marketing-insight/smart-crm-marketing-insight.component.mjs +78 -0
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-opportunities-insight/smart-crm-opportunities-insight.component.mjs +145 -0
- package/esm2022/lib/private/components/smart-crm-marketing/smart-crm-marketing-list/smart-crm-marketing-list.component.mjs +3 -3
- package/esm2022/lib/private/components/smart-crm-opportunities/smart-crm-board/smart-crm-board.component.mjs +2 -2
- package/esm2022/lib/private/components/smart-crm-opportunities/smart-crm-opportunities-list/smart-crm-opportunities-details/smart-crm-opportunities-details.component.mjs +3 -3
- package/esm2022/lib/private/components/smart-crm-opportunities/smart-crm-opportunities-list/smart-crm-opportunities-info/smart-crm-opportunities-info.component.mjs +5 -7
- package/esm2022/lib/private/components/smart-crm-opportunities/smart-crm-opportunities-list/smart-crm-opportunities-list.component.mjs +3 -4
- package/esm2022/lib/private/components/smart-crm-opportunities/smart-crm-opportunities.component.mjs +2 -2
- package/esm2022/lib/private/components/smart-crm-summary/smart-crm-summary-actions/smart-crm-summary-actions.component.mjs +2 -2
- package/esm2022/lib/private/components/smart-crm-summary/smart-crm-summary.component.mjs +6 -8
- package/esm2022/lib/private/smart-crm-private.module.mjs +26 -11
- package/esm2022/lib/public/components/smart-crm-signup/smart-crm-signup.component.mjs +2 -2
- package/fesm2022/posiwise-smart-crm.mjs +756 -396
- package/fesm2022/posiwise-smart-crm.mjs.map +1 -1
- package/index.d.ts +5 -2
- package/lib/private/components/{smart-crm-summary/smart-crm-summary-others/smart-crm-summary-others.component.d.ts → smart-crm-insight/smart-crm-account-insight/smart-crm-account-insight.component.d.ts} +9 -7
- package/lib/private/components/smart-crm-insight/smart-crm-analysis-insight/smart-crm-analysis.component.d.ts +56 -0
- package/lib/private/components/smart-crm-insight/smart-crm-contact-insight/smart-crm-contact-insight.component.d.ts +61 -0
- package/lib/private/components/smart-crm-insight/smart-crm-insight.component.d.ts +4 -0
- package/lib/private/components/smart-crm-insight/smart-crm-marketing-insight/smart-crm-marketing-insight.component.d.ts +52 -0
- package/lib/private/components/smart-crm-insight/smart-crm-opportunities-insight/smart-crm-opportunities-insight.component.d.ts +79 -0
- package/lib/private/smart-crm-private.module.d.ts +47 -44
- package/package.json +1 -1
- package/esm2022/lib/private/components/smart-crm-insight/smart-crm-overview/smart-crm-overview.component.mjs +0 -55
- package/esm2022/lib/private/components/smart-crm-summary/smart-crm-summary-others/smart-crm-summary-others.component.mjs +0 -195
- package/lib/private/components/smart-crm-insight/smart-crm-overview/smart-crm-overview.component.d.ts +0 -20
|
@@ -1,195 +0,0 @@
|
|
|
1
|
-
import { Component, Injector } from '@angular/core';
|
|
2
|
-
import { CrmService } from '@posiwise/smart-crm-shared';
|
|
3
|
-
import { AppBaseComponent } from '@posiwise/app-base-component';
|
|
4
|
-
import { ROUTERS } from '../../../../shared/routers/routers';
|
|
5
|
-
import * as i0 from "@angular/core";
|
|
6
|
-
import * as i1 from "@posiwise/smart-crm-shared";
|
|
7
|
-
import * as i2 from "@angular/common";
|
|
8
|
-
import * as i3 from "@posiwise/directives";
|
|
9
|
-
import * as i4 from "@ng-bootstrap/ng-bootstrap";
|
|
10
|
-
import * as i5 from "@angular/router";
|
|
11
|
-
import * as i6 from "primeng/api";
|
|
12
|
-
import * as i7 from "primeng/progressspinner";
|
|
13
|
-
import * as i8 from "primeng/table";
|
|
14
|
-
import * as i9 from "@posiwise/shared-components";
|
|
15
|
-
import * as i10 from "@posiwise/pipes";
|
|
16
|
-
import * as i11 from "@jsverse/transloco";
|
|
17
|
-
export class SmartCrmSummaryOthersComponent extends AppBaseComponent {
|
|
18
|
-
constructor(crmService, injector) {
|
|
19
|
-
super(injector);
|
|
20
|
-
this.crmService = crmService;
|
|
21
|
-
this.routers = ROUTERS;
|
|
22
|
-
this.signUpLastNinetyDaysLoaded = false;
|
|
23
|
-
this.accountLastActivitiesLoaded = false;
|
|
24
|
-
this.churnedAccountLoaded = false;
|
|
25
|
-
this.activeOpportunitiesLoaded = false;
|
|
26
|
-
this.accountAtRiskDetailsLoaded = false;
|
|
27
|
-
this.contactRenewalLoaded = false;
|
|
28
|
-
this.creditCardExpiringDetailsLoaded = false;
|
|
29
|
-
this.magicMomentLoaded = false;
|
|
30
|
-
}
|
|
31
|
-
ngOnInit() {
|
|
32
|
-
this.getUserSubscription().subscribe(response => {
|
|
33
|
-
this.subscription = response;
|
|
34
|
-
if (this.subscription?.id) {
|
|
35
|
-
this.hasAccess = this.hasAdminAccess(this.subscription.id);
|
|
36
|
-
this.getUserInfo();
|
|
37
|
-
}
|
|
38
|
-
});
|
|
39
|
-
}
|
|
40
|
-
getUserInfo() {
|
|
41
|
-
this.userStore().subscribe(user => {
|
|
42
|
-
if (user) {
|
|
43
|
-
this.user = user;
|
|
44
|
-
this.userId = user.id;
|
|
45
|
-
if (this.permissionService.isGranted('Pages.Beta') ||
|
|
46
|
-
this.permissionService.isSuperAdmin()) {
|
|
47
|
-
this.getSignedUpLastNinetyDays();
|
|
48
|
-
this.getActiveOpportunities();
|
|
49
|
-
this.getChurnedAccounts();
|
|
50
|
-
this.getAccountLastActivities();
|
|
51
|
-
this.getAccountAtRiskDetails();
|
|
52
|
-
this.getContactRenewal();
|
|
53
|
-
this.getCreditCardExpiringDetails();
|
|
54
|
-
this.getMagicMoment();
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
});
|
|
58
|
-
}
|
|
59
|
-
/** Function to call signed up last 90 days details */
|
|
60
|
-
getSignedUpLastNinetyDays() {
|
|
61
|
-
this.crmService
|
|
62
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_signed_up_last_90_days')
|
|
63
|
-
.subscribe(response => {
|
|
64
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
65
|
-
this.signedUpLastThirtyDays = [];
|
|
66
|
-
}
|
|
67
|
-
else
|
|
68
|
-
this.signedUpLastThirtyDays = response;
|
|
69
|
-
})
|
|
70
|
-
.add(() => {
|
|
71
|
-
this.signUpLastNinetyDaysLoaded = true;
|
|
72
|
-
});
|
|
73
|
-
}
|
|
74
|
-
getAccountLastActivities() {
|
|
75
|
-
this.crmService
|
|
76
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_last_activities')
|
|
77
|
-
.subscribe(response => {
|
|
78
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
79
|
-
this.accountLastActivities = [];
|
|
80
|
-
}
|
|
81
|
-
else {
|
|
82
|
-
this.accountLastActivities = response;
|
|
83
|
-
this.actionNames = response?.map(action => {
|
|
84
|
-
return action?.crm_action?.name;
|
|
85
|
-
});
|
|
86
|
-
}
|
|
87
|
-
console.log(this.accountLastActivities);
|
|
88
|
-
})
|
|
89
|
-
.add(() => {
|
|
90
|
-
this.accountLastActivitiesLoaded = true;
|
|
91
|
-
});
|
|
92
|
-
}
|
|
93
|
-
getChurnedAccounts() {
|
|
94
|
-
this.crmService
|
|
95
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_accounts_churned')
|
|
96
|
-
.subscribe(response => {
|
|
97
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
98
|
-
this.churnedAccounts = [];
|
|
99
|
-
}
|
|
100
|
-
else
|
|
101
|
-
this.churnedAccounts = response;
|
|
102
|
-
})
|
|
103
|
-
.add(() => {
|
|
104
|
-
this.churnedAccountLoaded = true;
|
|
105
|
-
});
|
|
106
|
-
}
|
|
107
|
-
/** Function to call Active Opportunities details */
|
|
108
|
-
getActiveOpportunities() {
|
|
109
|
-
this.crmService
|
|
110
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_active_opportunities')
|
|
111
|
-
.subscribe(response => {
|
|
112
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
113
|
-
this.activeOpportunities = [];
|
|
114
|
-
}
|
|
115
|
-
else
|
|
116
|
-
this.activeOpportunities = response;
|
|
117
|
-
})
|
|
118
|
-
.add(() => {
|
|
119
|
-
this.activeOpportunitiesLoaded = true;
|
|
120
|
-
});
|
|
121
|
-
}
|
|
122
|
-
/** Function to call Account At Risk details */
|
|
123
|
-
getAccountAtRiskDetails() {
|
|
124
|
-
this.crmService
|
|
125
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_accounts_at_risk')
|
|
126
|
-
.subscribe(response => {
|
|
127
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
128
|
-
this.accountAtRisk = [];
|
|
129
|
-
}
|
|
130
|
-
else
|
|
131
|
-
this.accountAtRisk = response;
|
|
132
|
-
})
|
|
133
|
-
.add(() => {
|
|
134
|
-
this.accountAtRiskDetailsLoaded = true;
|
|
135
|
-
});
|
|
136
|
-
}
|
|
137
|
-
/** Function to call Contract renewal details */
|
|
138
|
-
getContactRenewal() {
|
|
139
|
-
this.crmService
|
|
140
|
-
.getCrmAnalytics(this.subscription?.id, 'accounts_contract_renewal')
|
|
141
|
-
.subscribe(response => {
|
|
142
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
143
|
-
this.ContractRenewal = [];
|
|
144
|
-
}
|
|
145
|
-
else
|
|
146
|
-
this.ContractRenewal = response;
|
|
147
|
-
})
|
|
148
|
-
.add(() => {
|
|
149
|
-
this.contactRenewalLoaded = true;
|
|
150
|
-
});
|
|
151
|
-
}
|
|
152
|
-
/** Function to call Credit Card Expiring details */
|
|
153
|
-
getCreditCardExpiringDetails() {
|
|
154
|
-
this.crmService
|
|
155
|
-
.getCrmAnalytics(this.subscription?.id, 'credit_card_expiring')
|
|
156
|
-
.subscribe(response => {
|
|
157
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
158
|
-
this.creditCardExpiring = [];
|
|
159
|
-
}
|
|
160
|
-
else
|
|
161
|
-
this.creditCardExpiring = response;
|
|
162
|
-
})
|
|
163
|
-
.add(() => {
|
|
164
|
-
this.creditCardExpiringDetailsLoaded = true;
|
|
165
|
-
});
|
|
166
|
-
}
|
|
167
|
-
/** Function to call magic moment */
|
|
168
|
-
getMagicMoment() {
|
|
169
|
-
this.crmService
|
|
170
|
-
.getCrmAnalytics(this.subscription?.id, 'magic_moment')
|
|
171
|
-
.subscribe(response => {
|
|
172
|
-
if (typeof response === 'object' && Object.keys(response).length === 0) {
|
|
173
|
-
this.magicMoment = [];
|
|
174
|
-
}
|
|
175
|
-
else
|
|
176
|
-
this.magicMoment = response;
|
|
177
|
-
})
|
|
178
|
-
.add(() => {
|
|
179
|
-
this.magicMomentLoaded = true;
|
|
180
|
-
});
|
|
181
|
-
}
|
|
182
|
-
checkPermission(permission) {
|
|
183
|
-
return this.permissionService.evaluatePermissions(permission);
|
|
184
|
-
}
|
|
185
|
-
ngOnDestroy() {
|
|
186
|
-
super.ngOnDestroy();
|
|
187
|
-
}
|
|
188
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: SmartCrmSummaryOthersComponent, deps: [{ token: i1.CrmService }, { token: i0.Injector }], target: i0.ɵɵFactoryTarget.Component }); }
|
|
189
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.11", type: SmartCrmSummaryOthersComponent, selector: "pw-smart-crm-summary-others", usesInheritance: true, ngImport: i0, template: "<div class=\"row\">\n <ng-container class=\"mt-5\"\n *rbacAllow=\"'Pages.Beta'\">\n <!-- Signed up last 90 days -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Signed up Last 90 Days</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!signUpLastNinetyDaysLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"signedUpLastThirtyDays?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"signedUpLastThirtyDays\"\n [paginator]=\"true\"\n [rows]=\"20\"\n [totalRecords]=\"signedUpLastThirtyDays.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-signUp>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, signUp.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"signUp.crm_account_name\">{{ signUp?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ signUp.expected_mrr / 100 | currency: signUp.currency }}\n </td>\n <td data-head=\"SignUpAt\">\n {{ signUp.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"signedUpLastThirtyDays.length!== 0\">{{ 'Label.Total' | transloco }}: {{ signedUpLastThirtyDays.length }}</span>\n </div>\n <div *ngIf=\"signedUpLastThirtyDays?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Active Opportunities -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Active Opportunities</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!activeOpportunitiesLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"activeOpportunities?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"activeOpportunities\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"activeOpportunities.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.Title' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.OneTimeAmount' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.WinChance' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-opportunities>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, opportunities.crm_account?.id]\" class=\"name-link\">\n <span [ngbTooltip]=\"opportunities.crm_account?.name\">{{ opportunities.crm_account?.name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"Title\">\n <a [ngbTooltip]=\"opportunities?.title\" *ngIf=\"\n hasAccess ||\n opportunities?.owner_id === userId ||\n checkPermission('Pages.Product.CRM.Role.Admin')\n \" [routerLink]=\"[\n '/' + subscription?.slug + routers.opportunityInfo,\n opportunities.id\n ]\">\n <span>{{ opportunities?.title | textTruncate: 20 }} </span>\n </a>\n </td>\n <td data-head=\"One Time Amount\"> {{ opportunities.one_time_amount / 100 | currency }} </td>\n <td data-head=\"Monthly Amount\"> {{ opportunities.monthly_amount / 100 | currency }} </td>\n <td data-head=\"Win Chance\"> {{ opportunities.win_chances / 100 | percent }} <span class=\"text-danger\"\n *ngIf=\"opportunities.cancelled\">!Cancelled!</span>\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"activeOpportunities.length !== 0\">{{ 'Label.Total' | transloco }}: {{ activeOpportunities.length }}</span>\n </div>\n <div *ngIf=\"activeOpportunities?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Last Activities</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!accountLastActivitiesLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"accountLastActivities?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"accountLastActivities\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"accountLastActivities.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Owner' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Contact' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Action' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.When' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\" let-activities>\n <tr>\n <td data-head=\"Owner\"> {{ activities.owner?.first_name.charAt(0) }}. {{ activities.owner?.last_name }} </td>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, activities.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"activities.crm_account?.name\">{{ activities.crm_account?.name }}</span>\n </a>\n </td>\n <td data-head=\"Contact\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.contactInfo, activities.crm_contact_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"activities.crm_contact ? activities.crm_contact.first_name + ' ' + activities.crm_contact.last_name : ''\">{{ (activities.crm_contact?.first_name + ' ' + activities.crm_contact?.last_name) | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"Action\">\n <span [ngbTooltip]=\"activities.comment\" [appDynamicBadge]=\"{\n itemsArray: actionNames,\n item: activities.crm_action?.name\n }\"\n color=\"blue-grey\"\n class=\"badge\">{{ activities.crm_action?.name }}</span>\n </td>\n <td data-head=\"When\">{{ activities.when | date:'dd-MMM-YYYY' }}</td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"accountLastActivities.length !== 0\">{{ 'Label.Total' | transloco }}: {{ accountLastActivities.length }}</span>\n </div>\n <div *ngIf=\"accountLastActivities?.length === 0 && accountLastActivitiesLoaded\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n\n\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Churned Last 90 Days</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!churnedAccountLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"churnedAccounts?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"churnedAccounts\"\n [paginator]=\"true\"\n [rows]=\"20\"\n [totalRecords]=\"churnedAccounts.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.UnsubscribedAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"churnedAccounts?.length !== 0\">{{ 'Label.Total' | transloco }}: {{ churnedAccounts.length }}</span>\n </div>\n <div *ngIf=\"churnedAccounts?.length === 0 && churnedAccountLoaded\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n\n <!-- Accounts at risk -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Accounts at Risk</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!accountAtRiskDetailsLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"accountAtRisk?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"accountAtRisk\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"accountAtRisk.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"accountAtRisk.length !== 0\">{{ 'Label.Total' | transloco }}: {{ accountAtRisk.length }}</span>\n </div>\n <div *ngIf=\"accountAtRisk?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Contract renewal -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Contract Renewal</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!contactRenewalLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"ContractRenewal?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"ContractRenewal\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"ContractRenewal.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"ContractRenewal.length !== 0\">{{ 'Label.Total' | transloco }}: {{ ContractRenewal.length }}</span>\n </div>\n <div *ngIf=\"ContractRenewal?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Credit Card Expiring -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Credit Card Expiring</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!creditCardExpiringDetailsLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"creditCardExpiring?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"creditCardExpiring\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"creditCardExpiring.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"creditCardExpiring.length !== 0\">{{ 'Label.Total' | transloco }}: {{ creditCardExpiring.length }}</span>\n </div>\n <div *ngIf=\"creditCardExpiring?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Magic Moment -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Magic Moment</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!magicMomentLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"magicMoment?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"magicMoment\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"magicMoment.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"magicMoment.length !==0 \">{{ 'Label.Total' | transloco }}: {{ magicMoment.length }}</span>\n </div>\n <div *ngIf=\"magicMoment?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n </ng-container>\n</div>\n", dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i3.DynamicBadgeDirective, selector: "[appDynamicBadge]", inputs: ["appDynamicBadge", "color"] }, { kind: "directive", type: i3.RbacAllowDirective, selector: "[rbacAllow]", inputs: ["rbacAllow"] }, { kind: "directive", type: i4.NgbTooltip, selector: "[ngbTooltip]", inputs: ["animation", "autoClose", "placement", "popperOptions", "triggers", "positionTarget", "container", "disableTooltip", "tooltipClass", "tooltipContext", "openDelay", "closeDelay", "ngbTooltip"], outputs: ["shown", "hidden"], exportAs: ["ngbTooltip"] }, { kind: "directive", type: i5.RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: i6.PrimeTemplate, selector: "[pTemplate]", inputs: ["type", "pTemplate"] }, { kind: "component", type: i7.ProgressSpinner, selector: "p-progressSpinner", inputs: ["styleClass", "style", "strokeWidth", "fill", "animationDuration", "ariaLabel"] }, { kind: "component", type: i8.Table, selector: "p-table", inputs: ["frozenColumns", "frozenValue", "style", "styleClass", "tableStyle", "tableStyleClass", "paginator", "pageLinks", "rowsPerPageOptions", "alwaysShowPaginator", "paginatorPosition", "paginatorStyleClass", "paginatorDropdownAppendTo", "paginatorDropdownScrollHeight", "currentPageReportTemplate", "showCurrentPageReport", "showJumpToPageDropdown", "showJumpToPageInput", "showFirstLastIcon", "showPageLinks", "defaultSortOrder", "sortMode", "resetPageOnSort", "selectionMode", "selectionPageOnly", "contextMenuSelection", "contextMenuSelectionMode", "dataKey", "metaKeySelection", "rowSelectable", "rowTrackBy", "lazy", "lazyLoadOnInit", "compareSelectionBy", "csvSeparator", "exportFilename", "filters", "globalFilterFields", "filterDelay", "filterLocale", "expandedRowKeys", "editingRowKeys", "rowExpandMode", "scrollable", "scrollDirection", "rowGroupMode", "scrollHeight", "virtualScroll", "virtualScrollItemSize", "virtualScrollOptions", "virtualScrollDelay", "frozenWidth", "responsive", "contextMenu", "resizableColumns", "columnResizeMode", "reorderableColumns", "loading", "loadingIcon", "showLoader", "rowHover", "customSort", "showInitialSortBadge", "autoLayout", "exportFunction", "exportHeader", "stateKey", "stateStorage", "editMode", "groupRowsBy", "groupRowsByOrder", "responsiveLayout", "breakpoint", "paginatorLocale", "value", "columns", "first", "rows", "totalRecords", "sortField", "sortOrder", "multiSortMeta", "selection", "selectAll", "virtualRowHeight"], outputs: ["contextMenuSelectionChange", "selectAllChange", "selectionChange", "onRowSelect", "onRowUnselect", "onPage", "onSort", "onFilter", "onLazyLoad", "onRowExpand", "onRowCollapse", "onContextMenuSelect", "onColResize", "onColReorder", "onRowReorder", "onEditInit", "onEditComplete", "onEditCancel", "onHeaderCheckboxToggle", "sortFunction", "firstChange", "rowsChange", "onStateSave", "onStateRestore"] }, { kind: "component", type: i9.NoDataComponent, selector: "pw-no-data", inputs: ["message", "description", "withImage"] }, { kind: "pipe", type: i2.PercentPipe, name: "percent" }, { kind: "pipe", type: i2.CurrencyPipe, name: "currency" }, { kind: "pipe", type: i2.DatePipe, name: "date" }, { kind: "pipe", type: i10.DateFormatPipe, name: "dateFormat" }, { kind: "pipe", type: i10.TextTruncatePipe, name: "textTruncate" }, { kind: "pipe", type: i11.TranslocoPipe, name: "transloco" }] }); }
|
|
190
|
-
}
|
|
191
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: SmartCrmSummaryOthersComponent, decorators: [{
|
|
192
|
-
type: Component,
|
|
193
|
-
args: [{ selector: 'pw-smart-crm-summary-others', template: "<div class=\"row\">\n <ng-container class=\"mt-5\"\n *rbacAllow=\"'Pages.Beta'\">\n <!-- Signed up last 90 days -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Signed up Last 90 Days</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!signUpLastNinetyDaysLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"signedUpLastThirtyDays?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"signedUpLastThirtyDays\"\n [paginator]=\"true\"\n [rows]=\"20\"\n [totalRecords]=\"signedUpLastThirtyDays.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-signUp>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, signUp.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"signUp.crm_account_name\">{{ signUp?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ signUp.expected_mrr / 100 | currency: signUp.currency }}\n </td>\n <td data-head=\"SignUpAt\">\n {{ signUp.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"signedUpLastThirtyDays.length!== 0\">{{ 'Label.Total' | transloco }}: {{ signedUpLastThirtyDays.length }}</span>\n </div>\n <div *ngIf=\"signedUpLastThirtyDays?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Active Opportunities -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Active Opportunities</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!activeOpportunitiesLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"activeOpportunities?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"activeOpportunities\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"activeOpportunities.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.Title' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.OneTimeAmount' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.Summary.WinChance' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-opportunities>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, opportunities.crm_account?.id]\" class=\"name-link\">\n <span [ngbTooltip]=\"opportunities.crm_account?.name\">{{ opportunities.crm_account?.name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"Title\">\n <a [ngbTooltip]=\"opportunities?.title\" *ngIf=\"\n hasAccess ||\n opportunities?.owner_id === userId ||\n checkPermission('Pages.Product.CRM.Role.Admin')\n \" [routerLink]=\"[\n '/' + subscription?.slug + routers.opportunityInfo,\n opportunities.id\n ]\">\n <span>{{ opportunities?.title | textTruncate: 20 }} </span>\n </a>\n </td>\n <td data-head=\"One Time Amount\"> {{ opportunities.one_time_amount / 100 | currency }} </td>\n <td data-head=\"Monthly Amount\"> {{ opportunities.monthly_amount / 100 | currency }} </td>\n <td data-head=\"Win Chance\"> {{ opportunities.win_chances / 100 | percent }} <span class=\"text-danger\"\n *ngIf=\"opportunities.cancelled\">!Cancelled!</span>\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"activeOpportunities.length !== 0\">{{ 'Label.Total' | transloco }}: {{ activeOpportunities.length }}</span>\n </div>\n <div *ngIf=\"activeOpportunities?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Last Activities</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!accountLastActivitiesLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"accountLastActivities?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"accountLastActivities\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"accountLastActivities.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Owner' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Contact' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Action' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.When' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\" let-activities>\n <tr>\n <td data-head=\"Owner\"> {{ activities.owner?.first_name.charAt(0) }}. {{ activities.owner?.last_name }} </td>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, activities.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"activities.crm_account?.name\">{{ activities.crm_account?.name }}</span>\n </a>\n </td>\n <td data-head=\"Contact\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.contactInfo, activities.crm_contact_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"activities.crm_contact ? activities.crm_contact.first_name + ' ' + activities.crm_contact.last_name : ''\">{{ (activities.crm_contact?.first_name + ' ' + activities.crm_contact?.last_name) | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"Action\">\n <span [ngbTooltip]=\"activities.comment\" [appDynamicBadge]=\"{\n itemsArray: actionNames,\n item: activities.crm_action?.name\n }\"\n color=\"blue-grey\"\n class=\"badge\">{{ activities.crm_action?.name }}</span>\n </td>\n <td data-head=\"When\">{{ activities.when | date:'dd-MMM-YYYY' }}</td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"accountLastActivities.length !== 0\">{{ 'Label.Total' | transloco }}: {{ accountLastActivities.length }}</span>\n </div>\n <div *ngIf=\"accountLastActivities?.length === 0 && accountLastActivitiesLoaded\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n\n\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Churned Last 90 Days</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!churnedAccountLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"churnedAccounts?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"churnedAccounts\"\n [paginator]=\"true\"\n [rows]=\"20\"\n [totalRecords]=\"churnedAccounts.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.UnsubscribedAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"churnedAccounts?.length !== 0\">{{ 'Label.Total' | transloco }}: {{ churnedAccounts.length }}</span>\n </div>\n <div *ngIf=\"churnedAccounts?.length === 0 && churnedAccountLoaded\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n\n <!-- Accounts at risk -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Accounts at Risk</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!accountAtRiskDetailsLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"accountAtRisk?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"accountAtRisk\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"accountAtRisk.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"accountAtRisk.length !== 0\">{{ 'Label.Total' | transloco }}: {{ accountAtRisk.length }}</span>\n </div>\n <div *ngIf=\"accountAtRisk?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Contract renewal -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Contract Renewal</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!contactRenewalLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"ContractRenewal?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"ContractRenewal\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"ContractRenewal.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"ContractRenewal.length !== 0\">{{ 'Label.Total' | transloco }}: {{ ContractRenewal.length }}</span>\n </div>\n <div *ngIf=\"ContractRenewal?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Credit Card Expiring -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Credit Card Expiring</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!creditCardExpiringDetailsLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"creditCardExpiring?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"creditCardExpiring\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"creditCardExpiring.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.CCExpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n <td data-head=\"ExpAt\">\n {{ account.cc_expiring_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"creditCardExpiring.length !== 0\">{{ 'Label.Total' | transloco }}: {{ creditCardExpiring.length }}</span>\n </div>\n <div *ngIf=\"creditCardExpiring?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n <!-- Magic Moment -->\n <div class=\"col-12 col-md-6 mb-3 analytics\">\n <h5 class=\"accordion-heading\">Magic Moment</h5>\n <div class=\"w-100 text-center mt-3\">\n <ng-template [ngIf]=\"!magicMomentLoaded\">\n <p-progressSpinner strokeWidth=\"2\"> </p-progressSpinner>\n </ng-template>\n </div>\n <div class=\"primeng-datatable-container table-responsive\"\n *ngIf=\"magicMoment?.length\">\n <p-table class=\"table\"\n #dt\n [value]=\"magicMoment\"\n [paginator]=\"true\"\n [rows]=\"20\"\n\n [totalRecords]=\"magicMoment.length\"\n>\n <ng-template pTemplate=\"header\">\n <tr>\n <th scope=\"true\">{{ 'Crm.Summary.Account' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.MRR' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.Quarter' | transloco }}</th>\n <th scope=\"true\"> {{ 'Crm.AccountMessage.Month' | transloco }}</th>\n <th scope=\"true\">{{ 'Crm.AccountMessage.SignUpAt' | transloco }}</th>\n </tr>\n </ng-template>\n <ng-template pTemplate=\"body\"\n let-account>\n <tr>\n <td data-head=\"Account\">\n <a [routerLink]=\"['/' + subscription?.slug + routers.accountInfo, account.crm_account_id]\" class=\"name-link\">\n <span [ngbTooltip]=\"account.crm_account_name\">{{ account?.crm_account_name | textTruncate:20 }}</span>\n </a>\n </td>\n <td data-head=\"MRR\">\n {{ account.expected_mrr / 100 | currency: account.currency }}\n </td>\n <td data-head=\"Quarter\">{{ account.sessions_last_quarter }}</td>\n <td data-head=\"Month\">{{ account.sessions_last_month }}</td>\n <td data-head=\"SignUpAt\">\n {{ account.signed_up_at | dateFormat }}\n </td>\n </tr>\n </ng-template>\n </p-table>\n <span class=\"total-records-count\" *ngIf=\"magicMoment.length !==0 \">{{ 'Label.Total' | transloco }}: {{ magicMoment.length }}</span>\n </div>\n <div *ngIf=\"magicMoment?.length === 0\">\n <pw-no-data [withImage]=\"true\" [message]=\"'Crm.Summary.NoInsightMessage' | transloco\"> </pw-no-data>\n </div>\n </div>\n </ng-container>\n</div>\n" }]
|
|
194
|
-
}], ctorParameters: () => [{ type: i1.CrmService }, { type: i0.Injector }] });
|
|
195
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic21hcnQtY3JtLXN1bW1hcnktb3RoZXJzLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uLy4uLy4uLy4uL2xpYnMvc21hcnQtY3JtL3NyYy9saWIvcHJpdmF0ZS9jb21wb25lbnRzL3NtYXJ0LWNybS1zdW1tYXJ5L3NtYXJ0LWNybS1zdW1tYXJ5LW90aGVycy9zbWFydC1jcm0tc3VtbWFyeS1vdGhlcnMuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vLi4vLi4vLi4vbGlicy9zbWFydC1jcm0vc3JjL2xpYi9wcml2YXRlL2NvbXBvbmVudHMvc21hcnQtY3JtLXN1bW1hcnkvc21hcnQtY3JtLXN1bW1hcnktb3RoZXJzL3NtYXJ0LWNybS1zdW1tYXJ5LW90aGVycy5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsU0FBUyxFQUFFLFFBQVEsRUFBcUIsTUFBTSxlQUFlLENBQUM7QUFDdkUsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBRXhELE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLDhCQUE4QixDQUFDO0FBT2hFLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxvQ0FBb0MsQ0FBQzs7Ozs7Ozs7Ozs7OztBQU03RCxNQUFNLE9BQU8sOEJBQStCLFNBQVEsZ0JBQWdCO0lBMkNoRSxZQUNxQixVQUFzQixFQUN2QyxRQUFrQjtRQUVsQixLQUFLLENBQUMsUUFBUSxDQUFDLENBQUM7UUFIQyxlQUFVLEdBQVYsVUFBVSxDQUFZO1FBL0IzQyxZQUFPLEdBQUcsT0FBTyxDQUFDO1FBUWxCLCtCQUEwQixHQUFHLEtBQUssQ0FBQztRQUVuQyxnQ0FBMkIsR0FBRyxLQUFLLENBQUM7UUFFcEMseUJBQW9CLEdBQUcsS0FBSyxDQUFDO1FBRTdCLDhCQUF5QixHQUFHLEtBQUssQ0FBQztRQUVsQywrQkFBMEIsR0FBRyxLQUFLLENBQUM7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LEVBQUU7WUFDTixJQUFJLENBQUMsaUJBQWlCLEdBQUcsSUFBSSxDQUFDO1FBQ2xDLENBQUMsQ0FBQyxDQUFDO0lBQ1gsQ0FBQztJQUVELGVBQWUsQ0FBQyxVQUFrQjtRQUM5QixPQUFPLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxtQkFBbUIsQ0FBQyxVQUFVLENBQUMsQ0FBQztJQUNsRSxDQUFDO0lBRVEsV0FBVztRQUNoQixLQUFLLENBQUMsV0FBVyxFQUFFLENBQUM7SUFDeEIsQ0FBQzsrR0EzTVEsOEJBQThCO21HQUE5Qiw4QkFBOEIsMEZDaEIzQyxpenBCQTJiQTs7NEZEM2FhLDhCQUE4QjtrQkFKMUMsU0FBUzsrQkFDSSw2QkFBNkIiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBDb21wb25lbnQsIEluamVjdG9yLCBPbkRlc3Ryb3ksIE9uSW5pdCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgQ3JtU2VydmljZSB9IGZyb20gJ0Bwb3Npd2lzZS9zbWFydC1jcm0tc2hhcmVkJztcblxuaW1wb3J0IHsgQXBwQmFzZUNvbXBvbmVudCB9IGZyb20gJ0Bwb3Npd2lzZS9hcHAtYmFzZS1jb21wb25lbnQnO1xuaW1wb3J0IHtcbiAgICBTdWJzY3JpcHRpb24sXG4gICAgVXNlcixcbiAgICBhY3RpdmVPcHBvcnR1bml0aWVzLFxuICAgIHNpZ25lZFVwTGFzdFRoaXJ0eURheXNcbn0gZnJvbSAnQHBvc2l3aXNlL2NvbW1vbi11dGlsaXRpZXMnO1xuaW1wb3J0IHsgUk9VVEVSUyB9IGZyb20gJy4uLy4uLy4uLy4uL3NoYXJlZC9yb3V0ZXJzL3JvdXRlcnMnO1xuXG5AQ29tcG9uZW50KHtcbiAgICBzZWxlY3RvcjogJ3B3LXNtYXJ0LWNybS1zdW1tYXJ5LW90aGVycycsXG4gICAgdGVtcGxhdGVVcmw6ICcuL3NtYXJ0LWNybS1zdW1tYXJ5LW90aGVycy5jb21wb25lbnQuaHRtbCdcbn0pXG5leHBvcnQgY2xhc3MgU21hcnRDcm1TdW1tYXJ5T3RoZXJzQ29tcG9uZW50IGV4dGVuZHMgQXBwQmFzZUNvbXBvbmVudCBpbXBsZW1lbnRzIE9uSW5pdCwgT25EZXN0cm95IHtcbiAgICBzaWduZWRVcExhc3RUaGlydHlEYXlzOiBzaWduZWRVcExhc3RUaGlydHlEYXlzW107XG5cbiAgICBhY3RpdmVPcHBvcnR1bml0aWVzOiBhY3RpdmVPcHBvcnR1bml0aWVzW107XG5cbiAgICBhY2NvdW50QXRSaXNrOiBbXTtcblxuICAgIENvbnRyYWN0UmVuZXdhbDogW107XG5cbiAgICBjaHVybmVkQWNjb3VudHM6IFtdO1xuXG4gICAgYWNjb3VudExhc3RBY3Rpdml0aWVzOiBbXTtcblxuICAgIHJvdXRlcnMgPSBST1VURVJTO1xuXG4gICAgY3JlZGl0Q2FyZEV4cGlyaW5nOiBbXTtcblxuICAgIG1hZ2ljTW9tZW50OiBbXTtcblxuICAgIHVzZXI6IFVzZXI7XG5cbiAgICBzaWduVXBMYXN0TmluZXR5RGF5c0xvYWRlZCA9IGZhbHNlO1xuXG4gICAgYWNjb3VudExhc3RBY3Rpdml0aWVzTG9hZGVkID0gZmFsc2U7XG5cbiAgICBjaHVybmVkQWNjb3VudExvYWRlZCA9IGZhbHNlO1xuXG4gICAgYWN0aXZlT3Bwb3J0dW5pdGllc0xvYWRlZCA9IGZhbHNlO1xuXG4gICAgYWNjb3VudEF0Umlza0RldGFpbHNMb2FkZWQgPSBmYWxzZTtcblxuICAgIGNvbnRhY3RSZW5ld2FsTG9hZGVkID0gZmFsc2U7XG5cbiAgICBjcmVkaXRDYXJkRXhwaXJpbmdEZXRhaWxzTG9hZGVkID0gZmFsc2U7XG5cbiAgICBtYWdpY01vbWVudExvYWRlZCA9IGZhbHNlO1xuXG4gICAgc3Vic2NyaXB0aW9uOiBTdWJzY3JpcHRpb247XG4gICAgaGFzQWNjZXNzOiBib29sZWFuO1xuICAgIHVzZXJJZDogbnVtYmVyO1xuXG4gICAgYWN0aW9uTmFtZXM7XG5cbiAgICBjb25zdHJ1Y3RvcihcbiAgICAgICAgcHJpdmF0ZSByZWFkb25seSBjcm1TZXJ2aWNlOiBDcm1TZXJ2aWNlLFxuICAgICAgICBpbmplY3RvcjogSW5qZWN0b3JcbiAgICApIHtcbiAgICAgICAgc3VwZXIoaW5qZWN0b3IpO1xuICAgIH1cblxuICAgIG5nT25Jbml0KCk6IHZvaWQge1xuICAgICAgICB0aGlzLmdldFVzZXJTdWJzY3JpcHRpb24oKS5zdWJzY3JpYmUocmVzcG9uc2UgPT4ge1xuICAgICAgICAgICAgdGhpcy5zdWJzY3JpcHRpb24gPSByZXNwb25zZTtcbiAgICAgICAgICAgIGlmICh0aGlzLnN1YnNjcmlwdGlvbj8uaWQpIHtcbiAgICAgICAgICAgICAgICB0aGlzLmhhc0FjY2VzcyA9IHRoaXMuaGFzQWRtaW5BY2Nlc3ModGhpcy5zdWJzY3JpcHRpb24uaWQpO1xuICAgICAgICAgICAgICAgIHRoaXMuZ2V0VXNlckluZm8oKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgcHJpdmF0ZSBnZXRVc2VySW5mbygpIHtcbiAgICAgICAgdGhpcy51c2VyU3RvcmUoKS5zdWJzY3JpYmUodXNlciA9PiB7XG4gICAgICAgICAgICBpZiAodXNlcikge1xuICAgICAgICAgICAgICAgIHRoaXMudXNlciA9IHVzZXI7XG4gICAgICAgICAgICAgICAgdGhpcy51c2VySWQgPSB1c2VyLmlkO1xuICAgICAgICAgICAgICAgIGlmIChcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5wZXJtaXNzaW9uU2VydmljZS5pc0dyYW50ZWQoJ1BhZ2VzLkJldGEnKSB8fFxuICAgICAgICAgICAgICAgICAgICB0aGlzLnBlcm1pc3Npb25TZXJ2aWNlLmlzU3VwZXJBZG1pbigpXG4gICAgICAgICAgICAgICAgKSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuZ2V0U2lnbmVkVXBMYXN0TmluZXR5RGF5cygpO1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmdldEFjdGl2ZU9wcG9ydHVuaXRpZXMoKTtcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5nZXRDaHVybmVkQWNjb3VudHMoKTtcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5nZXRBY2NvdW50TGFzdEFjdGl2aXRpZXMoKTtcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5nZXRBY2NvdW50QXRSaXNrRGV0YWlscygpO1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmdldENvbnRhY3RSZW5ld2FsKCk7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuZ2V0Q3JlZGl0Q2FyZEV4cGlyaW5nRGV0YWlscygpO1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmdldE1hZ2ljTW9tZW50KCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICB9XG5cbiAgICAvKiogRnVuY3Rpb24gdG8gY2FsbCBzaWduZWQgdXAgbGFzdCA5MCBkYXlzIGRldGFpbHMgKi9cbiAgICBwcml2YXRlIGdldFNpZ25lZFVwTGFzdE5pbmV0eURheXMoKSB7XG4gICAgICAgIHRoaXMuY3JtU2VydmljZVxuICAgICAgICAgICAgLmdldENybUFuYWx5dGljcyh0aGlzLnN1YnNjcmlwdGlvbj8uaWQsICdhY2NvdW50c19zaWduZWRfdXBfbGFzdF85MF9kYXlzJylcbiAgICAgICAgICAgIC5zdWJzY3JpYmUocmVzcG9uc2UgPT4ge1xuICAgICAgICAgICAgICAgIGlmICh0eXBlb2YgcmVzcG9uc2UgPT09ICdvYmplY3QnICYmIE9iamVjdC5rZXlzKHJlc3BvbnNlKS5sZW5ndGggPT09IDApIHtcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5zaWduZWRVcExhc3RUaGlydHlEYXlzID0gW107XG4gICAgICAgICAgICAgICAgfSBlbHNlIHRoaXMuc2lnbmVkVXBMYXN0VGhpcnR5RGF5cyA9IHJlc3BvbnNlO1xuICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIC5hZGQoKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMuc2lnblVwTGFzdE5pbmV0eURheXNMb2FkZWQgPSB0cnVlO1xuICAgICAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgcHJpdmF0ZSBnZXRBY2NvdW50TGFzdEFjdGl2aXRpZXMoKSB7XG4gICAgICAgIHRoaXMuY3JtU2VydmljZVxuICAgICAgICAgICAgLmdldENybUFuYWx5dGljcyh0aGlzLnN1YnNjcmlwdGlvbj8uaWQsICdhY2NvdW50c19sYXN0X2FjdGl2aXRpZXMnKVxuICAgICAgICAgICAgLnN1YnNjcmliZShyZXNwb25zZSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiByZXNwb25zZSA9PT0gJ29iamVjdCcgJiYgT2JqZWN0LmtleXMocmVzcG9uc2UpLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmFjY291bnRMYXN0QWN0aXZpdGllcyA9IFtdO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuYWNjb3VudExhc3RBY3Rpdml0aWVzID0gcmVzcG9uc2U7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuYWN0aW9uTmFtZXMgPSByZXNwb25zZT8ubWFwKGFjdGlvbiA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gYWN0aW9uPy5jcm1fYWN0aW9uPy5uYW1lO1xuICAgICAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgY29uc29sZS5sb2codGhpcy5hY2NvdW50TGFzdEFjdGl2aXRpZXMpO1xuICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIC5hZGQoKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMuYWNjb3VudExhc3RBY3Rpdml0aWVzTG9hZGVkID0gdHJ1ZTtcbiAgICAgICAgICAgIH0pO1xuICAgIH1cblxuICAgIHByaXZhdGUgZ2V0Q2h1cm5lZEFjY291bnRzKCkge1xuICAgICAgICB0aGlzLmNybVNlcnZpY2VcbiAgICAgICAgICAgIC5nZXRDcm1BbmFseXRpY3ModGhpcy5zdWJzY3JpcHRpb24/LmlkLCAnYWNjb3VudHNfYWNjb3VudHNfY2h1cm5lZCcpXG4gICAgICAgICAgICAuc3Vic2NyaWJlKHJlc3BvbnNlID0+IHtcbiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIHJlc3BvbnNlID09PSAnb2JqZWN0JyAmJiBPYmplY3Qua2V5cyhyZXNwb25zZSkubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuY2h1cm5lZEFjY291bnRzID0gW107XG4gICAgICAgICAgICAgICAgfSBlbHNlIHRoaXMuY2h1cm5lZEFjY291bnRzID0gcmVzcG9uc2U7XG4gICAgICAgICAgICB9KVxuICAgICAgICAgICAgLmFkZCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5jaHVybmVkQWNjb3VudExvYWRlZCA9IHRydWU7XG4gICAgICAgICAgICB9KTtcbiAgICB9XG5cbiAgICAvKiogRnVuY3Rpb24gdG8gY2FsbCBBY3RpdmUgT3Bwb3J0dW5pdGllcyBkZXRhaWxzICovXG4gICAgcHJpdmF0ZSBnZXRBY3RpdmVPcHBvcnR1bml0aWVzKCkge1xuICAgICAgICB0aGlzLmNybVNlcnZpY2VcbiAgICAgICAgICAgIC5nZXRDcm1BbmFseXRpY3ModGhpcy5zdWJzY3JpcHRpb24/LmlkLCAnYWNjb3VudHNfYWN0aXZlX29wcG9ydHVuaXRpZXMnKVxuICAgICAgICAgICAgLnN1YnNjcmliZShyZXNwb25zZSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiByZXNwb25zZSA9PT0gJ29iamVjdCcgJiYgT2JqZWN0LmtleXMocmVzcG9uc2UpLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmFjdGl2ZU9wcG9ydHVuaXRpZXMgPSBbXTtcbiAgICAgICAgICAgICAgICB9IGVsc2UgdGhpcy5hY3RpdmVPcHBvcnR1bml0aWVzID0gcmVzcG9uc2U7XG4gICAgICAgICAgICB9KVxuICAgICAgICAgICAgLmFkZCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5hY3RpdmVPcHBvcnR1bml0aWVzTG9hZGVkID0gdHJ1ZTtcbiAgICAgICAgICAgIH0pO1xuICAgIH1cblxuICAgIC8qKiBGdW5jdGlvbiB0byBjYWxsIEFjY291bnQgQXQgUmlzayBkZXRhaWxzICovXG4gICAgcHJpdmF0ZSBnZXRBY2NvdW50QXRSaXNrRGV0YWlscygpIHtcbiAgICAgICAgdGhpcy5jcm1TZXJ2aWNlXG4gICAgICAgICAgICAuZ2V0Q3JtQW5hbHl0aWNzKHRoaXMuc3Vic2NyaXB0aW9uPy5pZCwgJ2FjY291bnRzX2FjY291bnRzX2F0X3Jpc2snKVxuICAgICAgICAgICAgLnN1YnNjcmliZShyZXNwb25zZSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiByZXNwb25zZSA9PT0gJ29iamVjdCcgJiYgT2JqZWN0LmtleXMocmVzcG9uc2UpLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmFjY291bnRBdFJpc2sgPSBbXTtcbiAgICAgICAgICAgICAgICB9IGVsc2UgdGhpcy5hY2NvdW50QXRSaXNrID0gcmVzcG9uc2U7XG4gICAgICAgICAgICB9KVxuICAgICAgICAgICAgLmFkZCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5hY2NvdW50QXRSaXNrRGV0YWlsc0xvYWRlZCA9IHRydWU7XG4gICAgICAgICAgICB9KTtcbiAgICB9XG5cbiAgICAvKiogRnVuY3Rpb24gdG8gY2FsbCBDb250cmFjdCByZW5ld2FsIGRldGFpbHMgKi9cbiAgICBwcml2YXRlIGdldENvbnRhY3RSZW5ld2FsKCkge1xuICAgICAgICB0aGlzLmNybVNlcnZpY2VcbiAgICAgICAgICAgIC5nZXRDcm1BbmFseXRpY3ModGhpcy5zdWJzY3JpcHRpb24/LmlkLCAnYWNjb3VudHNfY29udHJhY3RfcmVuZXdhbCcpXG4gICAgICAgICAgICAuc3Vic2NyaWJlKHJlc3BvbnNlID0+IHtcbiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIHJlc3BvbnNlID09PSAnb2JqZWN0JyAmJiBPYmplY3Qua2V5cyhyZXNwb25zZSkubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMuQ29udHJhY3RSZW5ld2FsID0gW107XG4gICAgICAgICAgICAgICAgfSBlbHNlIHRoaXMuQ29udHJhY3RSZW5ld2FsID0gcmVzcG9uc2U7XG4gICAgICAgICAgICB9KVxuICAgICAgICAgICAgLmFkZCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5jb250YWN0UmVuZXdhbExvYWRlZCA9IHRydWU7XG4gICAgICAgICAgICB9KTtcbiAgICB9XG5cbiAgICAvKiogRnVuY3Rpb24gdG8gY2FsbCBDcmVkaXQgQ2FyZCBFeHBpcmluZyBkZXRhaWxzICovXG4gICAgcHJpdmF0ZSBnZXRDcmVkaXRDYXJkRXhwaXJpbmdEZXRhaWxzKCkge1xuICAgICAgICB0aGlzLmNybVNlcnZpY2VcbiAgICAgICAgICAgIC5nZXRDcm1BbmFseXRpY3ModGhpcy5zdWJzY3JpcHRpb24/LmlkLCAnY3JlZGl0X2NhcmRfZXhwaXJpbmcnKVxuICAgICAgICAgICAgLnN1YnNjcmliZShyZXNwb25zZSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiByZXNwb25zZSA9PT0gJ29iamVjdCcgJiYgT2JqZWN0LmtleXMocmVzcG9uc2UpLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICAgICAgICAgICAgICB0aGlzLmNyZWRpdENhcmRFeHBpcmluZyA9IFtdO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB0aGlzLmNyZWRpdENhcmRFeHBpcmluZyA9IHJlc3BvbnNlO1xuICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIC5hZGQoKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMuY3JlZGl0Q2FyZEV4cGlyaW5nRGV0YWlsc0xvYWRlZCA9IHRydWU7XG4gICAgICAgICAgICB9KTtcbiAgICB9XG4gICAgLyoqIEZ1bmN0aW9uIHRvIGNhbGwgbWFnaWMgbW9tZW50ICovXG4gICAgcHJpdmF0ZSBnZXRNYWdpY01vbWVudCgpIHtcbiAgICAgICAgdGhpcy5jcm1TZXJ2aWNlXG4gICAgICAgICAgICAuZ2V0Q3JtQW5hbHl0aWNzKHRoaXMuc3Vic2NyaXB0aW9uPy5pZCwgJ21hZ2ljX21vbWVudCcpXG4gICAgICAgICAgICAuc3Vic2NyaWJlKHJlc3BvbnNlID0+IHtcbiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIHJlc3BvbnNlID09PSAnb2JqZWN0JyAmJiBPYmplY3Qua2V5cyhyZXNwb25zZSkubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMubWFnaWNNb21lbnQgPSBbXTtcbiAgICAgICAgICAgICAgICB9IGVsc2UgdGhpcy5tYWdpY01vbWVudCA9IHJlc3BvbnNlO1xuICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIC5hZGQoKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMubWFnaWNNb21lbnRMb2FkZWQgPSB0cnVlO1xuICAgICAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgY2hlY2tQZXJtaXNzaW9uKHBlcm1pc3Npb246IHN0cmluZykge1xuICAgICAgICByZXR1cm4gdGhpcy5wZXJtaXNzaW9uU2VydmljZS5ldmFsdWF0ZVBlcm1pc3Npb25zKHBlcm1pc3Npb24pO1xuICAgIH1cblxuICAgIG92ZXJyaWRlIG5nT25EZXN0cm95KCkge1xuICAgICAgICBzdXBlci5uZ09uRGVzdHJveSgpO1xuICAgIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJyb3dcIj5cbiAgPG5nLWNvbnRhaW5lciBjbGFzcz1cIm10LTVcIlxuICAgICpyYmFjQWxsb3c9XCInUGFnZXMuQmV0YSdcIj5cbiAgICA8IS0tIFNpZ25lZCB1cCBsYXN0IDkwIGRheXMgLS0+XG4gICAgPGRpdiBjbGFzcz1cImNvbC0xMiBjb2wtbWQtNiBtYi0zIGFuYWx5dGljc1wiPlxuICAgICAgPGg1IGNsYXNzPVwiYWNjb3JkaW9uLWhlYWRpbmdcIj5TaWduZWQgdXAgTGFzdCA5MCBEYXlzPC9oNT5cbiAgICAgIDxkaXYgY2xhc3M9XCJ3LTEwMCB0ZXh0LWNlbnRlciBtdC0zXCI+XG4gICAgICAgIDxuZy10ZW1wbGF0ZSBbbmdJZl09XCIhc2lnblVwTGFzdE5pbmV0eURheXNMb2FkZWRcIj5cbiAgICAgICAgICA8cC1wcm9ncmVzc1NwaW5uZXIgc3Ryb2tlV2lkdGg9XCIyXCI+IDwvcC1wcm9ncmVzc1NwaW5uZXI+XG4gICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgY2xhc3M9XCJwcmltZW5nLWRhdGF0YWJsZS1jb250YWluZXIgdGFibGUtcmVzcG9uc2l2ZVwiXG4gICAgICAgICpuZ0lmPVwic2lnbmVkVXBMYXN0VGhpcnR5RGF5cz8ubGVuZ3RoXCI+XG4gICAgICAgIDxwLXRhYmxlIGNsYXNzPVwidGFibGVcIlxuICAgICAgICAgICNkdFxuICAgICAgICAgIFt2YWx1ZV09XCJzaWduZWRVcExhc3RUaGlydHlEYXlzXCJcbiAgICAgICAgICBbcGFnaW5hdG9yXT1cInRydWVcIlxuICAgICAgICAgIFtyb3dzXT1cIjIwXCJcbiAgICAgICAgICBbdG90YWxSZWNvcmRzXT1cInNpZ25lZFVwTGFzdFRoaXJ0eURheXMubGVuZ3RoXCJcbj5cbiAgICAgICAgICA8bmctdGVtcGxhdGUgcFRlbXBsYXRlPVwiaGVhZGVyXCI+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLlN1bW1hcnkuQWNjb3VudCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5NUlInIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuU2lnblVwQXQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgIDwvdHI+XG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgICA8bmctdGVtcGxhdGUgcFRlbXBsYXRlPVwiYm9keVwiXG4gICAgICAgICAgICBsZXQtc2lnblVwPlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWNjb3VudFwiPlxuICAgICAgICAgICAgICAgIDxhIFtyb3V0ZXJMaW5rXT1cIlsnLycgKyBzdWJzY3JpcHRpb24/LnNsdWcgKyByb3V0ZXJzLmFjY291bnRJbmZvLCBzaWduVXAuY3JtX2FjY291bnRfaWRdXCIgY2xhc3M9XCJuYW1lLWxpbmtcIj5cbiAgICAgICAgICAgICAgICAgIDxzcGFuIFtuZ2JUb29sdGlwXT1cInNpZ25VcC5jcm1fYWNjb3VudF9uYW1lXCI+e3sgc2lnblVwPy5jcm1fYWNjb3VudF9uYW1lIHwgdGV4dFRydW5jYXRlOjIwIH19PC9zcGFuPlxuICAgICAgICAgICAgICAgIDwvYT5cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIk1SUlwiPlxuICAgICAgICAgICAgICAgIHt7IHNpZ25VcC5leHBlY3RlZF9tcnIgLyAxMDAgfCBjdXJyZW5jeTogc2lnblVwLmN1cnJlbmN5IH19XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJTaWduVXBBdFwiPlxuICAgICAgICAgICAgICAgIHt7IHNpZ25VcC5zaWduZWRfdXBfYXQgfCBkYXRlRm9ybWF0IH19XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICA8L3RyPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgIDwvcC10YWJsZT5cbiAgICAgICAgPHNwYW4gY2xhc3M9XCJ0b3RhbC1yZWNvcmRzLWNvdW50XCIgKm5nSWY9XCJzaWduZWRVcExhc3RUaGlydHlEYXlzLmxlbmd0aCE9PSAwXCI+e3sgJ0xhYmVsLlRvdGFsJyB8IHRyYW5zbG9jbyB9fToge3sgc2lnbmVkVXBMYXN0VGhpcnR5RGF5cy5sZW5ndGggfX08L3NwYW4+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgKm5nSWY9XCJzaWduZWRVcExhc3RUaGlydHlEYXlzPy5sZW5ndGggPT09IDBcIj5cbiAgICAgICAgPHB3LW5vLWRhdGEgW3dpdGhJbWFnZV09XCJ0cnVlXCIgW21lc3NhZ2VdPVwiJ0NybS5TdW1tYXJ5Lk5vSW5zaWdodE1lc3NhZ2UnIHwgdHJhbnNsb2NvXCI+IDwvcHctbm8tZGF0YT5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICAgIDwhLS0gQWN0aXZlIE9wcG9ydHVuaXRpZXMgLS0+XG4gICAgPGRpdiBjbGFzcz1cImNvbC0xMiBjb2wtbWQtNiBtYi0zIGFuYWx5dGljc1wiPlxuICAgICAgPGg1IGNsYXNzPVwiYWNjb3JkaW9uLWhlYWRpbmdcIj5BY3RpdmUgT3Bwb3J0dW5pdGllczwvaDU+XG4gICAgICA8ZGl2IGNsYXNzPVwidy0xMDAgdGV4dC1jZW50ZXIgbXQtM1wiPlxuICAgICAgICA8bmctdGVtcGxhdGUgW25nSWZdPVwiIWFjdGl2ZU9wcG9ydHVuaXRpZXNMb2FkZWRcIj5cbiAgICAgICAgICA8cC1wcm9ncmVzc1NwaW5uZXIgc3Ryb2tlV2lkdGg9XCIyXCI+IDwvcC1wcm9ncmVzc1NwaW5uZXI+XG4gICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgY2xhc3M9XCJwcmltZW5nLWRhdGF0YWJsZS1jb250YWluZXIgdGFibGUtcmVzcG9uc2l2ZVwiXG4gICAgICAgICpuZ0lmPVwiYWN0aXZlT3Bwb3J0dW5pdGllcz8ubGVuZ3RoXCI+XG4gICAgICAgIDxwLXRhYmxlIGNsYXNzPVwidGFibGVcIlxuICAgICAgICAgICNkdFxuICAgICAgICAgIFt2YWx1ZV09XCJhY3RpdmVPcHBvcnR1bml0aWVzXCJcbiAgICAgICAgICBbcGFnaW5hdG9yXT1cInRydWVcIlxuICAgICAgICAgIFtyb3dzXT1cIjIwXCJcblxuICAgICAgICAgIFt0b3RhbFJlY29yZHNdPVwiYWN0aXZlT3Bwb3J0dW5pdGllcy5sZW5ndGhcIlxuPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJoZWFkZXJcIj5cbiAgICAgICAgICAgIDx0cj5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uU3VtbWFyeS5BY2NvdW50JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLlN1bW1hcnkuVGl0bGUnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uU3VtbWFyeS5PbmVUaW1lQW1vdW50JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLk1SUicgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5TdW1tYXJ5LldpbkNoYW5jZScgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJib2R5XCJcbiAgICAgICAgICAgIGxldC1vcHBvcnR1bml0aWVzPlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWNjb3VudFwiPlxuICAgICAgICAgICAgICAgIDxhIFtyb3V0ZXJMaW5rXT1cIlsnLycgKyBzdWJzY3JpcHRpb24/LnNsdWcgKyByb3V0ZXJzLmFjY291bnRJbmZvLCBvcHBvcnR1bml0aWVzLmNybV9hY2NvdW50Py5pZF1cIiBjbGFzcz1cIm5hbWUtbGlua1wiPlxuICAgICAgICAgICAgICAgICAgPHNwYW4gW25nYlRvb2x0aXBdPVwib3Bwb3J0dW5pdGllcy5jcm1fYWNjb3VudD8ubmFtZVwiPnt7IG9wcG9ydHVuaXRpZXMuY3JtX2FjY291bnQ/Lm5hbWUgfCB0ZXh0VHJ1bmNhdGU6MjAgfX08L3NwYW4+XG4gICAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiVGl0bGVcIj5cbiAgICAgICAgICAgICAgICA8YSBbbmdiVG9vbHRpcF09XCJvcHBvcnR1bml0aWVzPy50aXRsZVwiICpuZ0lmPVwiXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoYXNBY2Nlc3MgfHxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wcG9ydHVuaXRpZXM/Lm93bmVyX2lkID09PSB1c2VySWQgfHxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoZWNrUGVybWlzc2lvbignUGFnZXMuUHJvZHVjdC5DUk0uUm9sZS5BZG1pbicpXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFwiIFtyb3V0ZXJMaW5rXT1cIltcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICcvJyArIHN1YnNjcmlwdGlvbj8uc2x1ZyArIHJvdXRlcnMub3Bwb3J0dW5pdHlJbmZvLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3Bwb3J0dW5pdGllcy5pZFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBdXCI+XG4gICAgICAgICAgICAgICAgPHNwYW4+e3sgb3Bwb3J0dW5pdGllcz8udGl0bGUgfCB0ZXh0VHJ1bmNhdGU6IDIwIH19IDwvc3Bhbj5cbiAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiT25lIFRpbWUgQW1vdW50XCI+IHt7IG9wcG9ydHVuaXRpZXMub25lX3RpbWVfYW1vdW50IC8gMTAwIHwgY3VycmVuY3kgfX0gPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIk1vbnRobHkgQW1vdW50XCI+IHt7IG9wcG9ydHVuaXRpZXMubW9udGhseV9hbW91bnQgLyAxMDAgfCBjdXJyZW5jeSB9fSA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiV2luIENoYW5jZVwiPiB7eyBvcHBvcnR1bml0aWVzLndpbl9jaGFuY2VzIC8gMTAwIHwgcGVyY2VudCB9fSA8c3BhbiBjbGFzcz1cInRleHQtZGFuZ2VyXCJcbiAgICAgICAgICAgICAgICAgICpuZ0lmPVwib3Bwb3J0dW5pdGllcy5jYW5jZWxsZWRcIj4hQ2FuY2VsbGVkITwvc3Bhbj5cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgIDwvdHI+XG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9wLXRhYmxlPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRvdGFsLXJlY29yZHMtY291bnRcIiAqbmdJZj1cImFjdGl2ZU9wcG9ydHVuaXRpZXMubGVuZ3RoICE9PSAwXCI+e3sgJ0xhYmVsLlRvdGFsJyB8IHRyYW5zbG9jbyB9fToge3sgYWN0aXZlT3Bwb3J0dW5pdGllcy5sZW5ndGggfX08L3NwYW4+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgKm5nSWY9XCJhY3RpdmVPcHBvcnR1bml0aWVzPy5sZW5ndGggPT09IDBcIj5cbiAgICAgICAgPHB3LW5vLWRhdGEgW3dpdGhJbWFnZV09XCJ0cnVlXCIgW21lc3NhZ2VdPVwiJ0NybS5TdW1tYXJ5Lk5vSW5zaWdodE1lc3NhZ2UnIHwgdHJhbnNsb2NvXCI+IDwvcHctbm8tZGF0YT5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICAgIDxkaXYgY2xhc3M9XCJjb2wtMTIgY29sLW1kLTYgbWItMyBhbmFseXRpY3NcIj5cbiAgICAgIDxoNSBjbGFzcz1cImFjY29yZGlvbi1oZWFkaW5nXCI+TGFzdCBBY3Rpdml0aWVzPC9oNT5cbiAgICAgIDxkaXYgY2xhc3M9XCJ3LTEwMCB0ZXh0LWNlbnRlciBtdC0zXCI+XG4gICAgICAgIDxuZy10ZW1wbGF0ZSBbbmdJZl09XCIhYWNjb3VudExhc3RBY3Rpdml0aWVzTG9hZGVkXCI+XG4gICAgICAgICAgPHAtcHJvZ3Jlc3NTcGlubmVyIHN0cm9rZVdpZHRoPVwiMlwiPiA8L3AtcHJvZ3Jlc3NTcGlubmVyPlxuICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2IGNsYXNzPVwicHJpbWVuZy1kYXRhdGFibGUtY29udGFpbmVyIHRhYmxlLXJlc3BvbnNpdmVcIlxuICAgICAgICAqbmdJZj1cImFjY291bnRMYXN0QWN0aXZpdGllcz8ubGVuZ3RoXCI+XG4gICAgICAgIDxwLXRhYmxlIGNsYXNzPVwidGFibGVcIlxuICAgICAgICAgICNkdFxuICAgICAgICAgIFt2YWx1ZV09XCJhY2NvdW50TGFzdEFjdGl2aXRpZXNcIlxuICAgICAgICAgIFtwYWdpbmF0b3JdPVwidHJ1ZVwiXG4gICAgICAgICAgW3Jvd3NdPVwiMjBcIlxuXG4gICAgICAgICAgW3RvdGFsUmVjb3Jkc109XCJhY2NvdW50TGFzdEFjdGl2aXRpZXMubGVuZ3RoXCJcbj5cbiAgICAgICAgICA8bmctdGVtcGxhdGUgcFRlbXBsYXRlPVwiaGVhZGVyXCI+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLk93bmVyJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLkFjY291bnQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuQ29udGFjdCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5BY3Rpb24nIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuV2hlbicgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJib2R5XCIgbGV0LWFjdGl2aXRpZXM+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJPd25lclwiPiB7eyBhY3Rpdml0aWVzLm93bmVyPy5maXJzdF9uYW1lLmNoYXJBdCgwKSB9fS4ge3sgYWN0aXZpdGllcy5vd25lcj8ubGFzdF9uYW1lIH19IDwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJBY2NvdW50XCI+XG4gICAgICAgICAgICAgICAgPGEgW3JvdXRlckxpbmtdPVwiWycvJyArIHN1YnNjcmlwdGlvbj8uc2x1ZyArIHJvdXRlcnMuYWNjb3VudEluZm8sIGFjdGl2aXRpZXMuY3JtX2FjY291bnRfaWRdXCIgY2xhc3M9XCJuYW1lLWxpbmtcIj5cbiAgICAgICAgICAgICAgICAgIDxzcGFuIFtuZ2JUb29sdGlwXT1cImFjdGl2aXRpZXMuY3JtX2FjY291bnQ/Lm5hbWVcIj57eyBhY3Rpdml0aWVzLmNybV9hY2NvdW50Py5uYW1lIH19PC9zcGFuPlxuICAgICAgICAgICAgICAgIDwvYT5cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIkNvbnRhY3RcIj5cbiAgICAgICAgICAgICAgICA8YSBbcm91dGVyTGlua109XCJbJy8nICsgc3Vic2NyaXB0aW9uPy5zbHVnICsgcm91dGVycy5jb250YWN0SW5mbywgYWN0aXZpdGllcy5jcm1fY29udGFjdF9pZF1cIiBjbGFzcz1cIm5hbWUtbGlua1wiPlxuICAgICAgICAgICAgICAgICAgPHNwYW4gW25nYlRvb2x0aXBdPVwiYWN0aXZpdGllcy5jcm1fY29udGFjdCA/IGFjdGl2aXRpZXMuY3JtX2NvbnRhY3QuZmlyc3RfbmFtZSArICcgJyArIGFjdGl2aXRpZXMuY3JtX2NvbnRhY3QubGFzdF9uYW1lIDogJydcIj57eyAoYWN0aXZpdGllcy5jcm1fY29udGFjdD8uZmlyc3RfbmFtZSArICcgJyArIGFjdGl2aXRpZXMuY3JtX2NvbnRhY3Q/Lmxhc3RfbmFtZSkgfCB0ZXh0VHJ1bmNhdGU6MjAgfX08L3NwYW4+XG4gICAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWN0aW9uXCI+XG4gICAgICAgICAgICAgICAgPHNwYW4gW25nYlRvb2x0aXBdPVwiYWN0aXZpdGllcy5jb21tZW50XCIgW2FwcER5bmFtaWNCYWRnZV09XCJ7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaXRlbXNBcnJheTogYWN0aW9uTmFtZXMsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaXRlbTogYWN0aXZpdGllcy5jcm1fYWN0aW9uPy5uYW1lXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9XCJcbiAgICAgICAgICAgICAgICAgIGNvbG9yPVwiYmx1ZS1ncmV5XCJcbiAgICAgICAgICAgICAgICAgIGNsYXNzPVwiYmFkZ2VcIj57eyBhY3Rpdml0aWVzLmNybV9hY3Rpb24/Lm5hbWUgfX08L3NwYW4+XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJXaGVuXCI+e3sgYWN0aXZpdGllcy53aGVuIHwgZGF0ZTonZGQtTU1NLVlZWVknIH19PC90ZD5cbiAgICAgICAgICAgIDwvdHI+XG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9wLXRhYmxlPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRvdGFsLXJlY29yZHMtY291bnRcIiAqbmdJZj1cImFjY291bnRMYXN0QWN0aXZpdGllcy5sZW5ndGggIT09IDBcIj57eyAnTGFiZWwuVG90YWwnIHwgdHJhbnNsb2NvIH19OiB7eyBhY2NvdW50TGFzdEFjdGl2aXRpZXMubGVuZ3RoIH19PC9zcGFuPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2ICpuZ0lmPVwiYWNjb3VudExhc3RBY3Rpdml0aWVzPy5sZW5ndGggPT09IDAgJiYgYWNjb3VudExhc3RBY3Rpdml0aWVzTG9hZGVkXCI+XG4gICAgICAgIDxwdy1uby1kYXRhIFt3aXRoSW1hZ2VdPVwidHJ1ZVwiIFttZXNzYWdlXT1cIidDcm0uU3VtbWFyeS5Ob0luc2lnaHRNZXNzYWdlJyB8IHRyYW5zbG9jb1wiPiA8L3B3LW5vLWRhdGE+XG4gICAgICA8L2Rpdj5cbiAgICA8L2Rpdj5cblxuXG4gICAgPGRpdiBjbGFzcz1cImNvbC0xMiBjb2wtbWQtNiBtYi0zIGFuYWx5dGljc1wiPlxuICAgICAgPGg1IGNsYXNzPVwiYWNjb3JkaW9uLWhlYWRpbmdcIj5DaHVybmVkIExhc3QgOTAgRGF5czwvaDU+XG4gICAgICA8ZGl2IGNsYXNzPVwidy0xMDAgdGV4dC1jZW50ZXIgbXQtM1wiPlxuICAgICAgICA8bmctdGVtcGxhdGUgW25nSWZdPVwiIWNodXJuZWRBY2NvdW50TG9hZGVkXCI+XG4gICAgICAgICAgPHAtcHJvZ3Jlc3NTcGlubmVyIHN0cm9rZVdpZHRoPVwiMlwiPiA8L3AtcHJvZ3Jlc3NTcGlubmVyPlxuICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2IGNsYXNzPVwicHJpbWVuZy1kYXRhdGFibGUtY29udGFpbmVyIHRhYmxlLXJlc3BvbnNpdmVcIlxuICAgICAgICAqbmdJZj1cImNodXJuZWRBY2NvdW50cz8ubGVuZ3RoXCI+XG4gICAgICAgIDxwLXRhYmxlIGNsYXNzPVwidGFibGVcIlxuICAgICAgICAgICNkdFxuICAgICAgICAgIFt2YWx1ZV09XCJjaHVybmVkQWNjb3VudHNcIlxuICAgICAgICAgIFtwYWdpbmF0b3JdPVwidHJ1ZVwiXG4gICAgICAgICAgW3Jvd3NdPVwiMjBcIlxuICAgICAgICAgIFt0b3RhbFJlY29yZHNdPVwiY2h1cm5lZEFjY291bnRzLmxlbmd0aFwiXG4+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlIHBUZW1wbGF0ZT1cImhlYWRlclwiPlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5BY2NvdW50JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLk1SUicgfCB0cmFuc2xvY28gfX08L3RoPlxuXG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLlF1YXJ0ZXInIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPiB7eyAnQ3JtLkFjY291bnRNZXNzYWdlLk1vbnRoJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuVW5zdWJzY3JpYmVkQXQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuQ0NFeHBBdCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJib2R5XCJcbiAgICAgICAgICBsZXQtYWNjb3VudD5cbiAgICAgICAgICA8dHI+XG4gICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWNjb3VudFwiPlxuICAgICAgICAgICAgICA8YSBbcm91dGVyTGlua109XCJbJy8nICsgc3Vic2NyaXB0aW9uPy5zbHVnICsgcm91dGVycy5hY2NvdW50SW5mbywgYWNjb3VudC5jcm1fYWNjb3VudF9pZF1cIiBjbGFzcz1cIm5hbWUtbGlua1wiPlxuICAgICAgICAgICAgICAgIDxzcGFuIFtuZ2JUb29sdGlwXT1cImFjY291bnQuY3JtX2FjY291bnRfbmFtZVwiPnt7IGFjY291bnQuY3JtX2FjY291bnRfbmFtZSB8IHRleHRUcnVuY2F0ZToyMCB9fTwvc3Bhbj5cbiAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJNUlJcIj5cbiAgICAgICAgICAgICAge3sgYWNjb3VudC5leHBlY3RlZF9tcnIgLyAxMDAgfCBjdXJyZW5jeTogYWNjb3VudC5jdXJyZW5jeSB9fVxuICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJRdWFydGVyXCI+e3sgYWNjb3VudC5zZXNzaW9uc19sYXN0X3F1YXJ0ZXIgfX08L3RkPlxuICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIk1vbnRoXCI+e3sgYWNjb3VudC5zZXNzaW9uc19sYXN0X21vbnRoIH19PC90ZD5cbiAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJTaWduVXBBdFwiPlxuICAgICAgICAgICAgICB7eyBhY2NvdW50LnNpZ25lZF91cF9hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiRXhwQXRcIj5cbiAgICAgICAgICAgICAge3sgYWNjb3VudC5jY19leHBpcmluZ19hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgPC90cj5cbiAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9wLXRhYmxlPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRvdGFsLXJlY29yZHMtY291bnRcIiAqbmdJZj1cImNodXJuZWRBY2NvdW50cz8ubGVuZ3RoICE9PSAwXCI+e3sgJ0xhYmVsLlRvdGFsJyB8IHRyYW5zbG9jbyB9fToge3sgY2h1cm5lZEFjY291bnRzLmxlbmd0aCB9fTwvc3Bhbj5cbiAgICAgIDwvZGl2PlxuICAgICAgPGRpdiAqbmdJZj1cImNodXJuZWRBY2NvdW50cz8ubGVuZ3RoID09PSAwICYmIGNodXJuZWRBY2NvdW50TG9hZGVkXCI+XG4gICAgICAgIDxwdy1uby1kYXRhIFt3aXRoSW1hZ2VdPVwidHJ1ZVwiIFttZXNzYWdlXT1cIidDcm0uU3VtbWFyeS5Ob0luc2lnaHRNZXNzYWdlJyB8IHRyYW5zbG9jb1wiPiA8L3B3LW5vLWRhdGE+XG4gICAgICA8L2Rpdj5cbiAgICA8L2Rpdj5cblxuICAgIDwhLS0gQWNjb3VudHMgYXQgcmlzayAtLT5cbiAgICA8ZGl2IGNsYXNzPVwiY29sLTEyIGNvbC1tZC02IG1iLTMgYW5hbHl0aWNzXCI+XG4gICAgICA8aDUgY2xhc3M9XCJhY2NvcmRpb24taGVhZGluZ1wiPkFjY291bnRzIGF0IFJpc2s8L2g1PlxuICAgICAgPGRpdiBjbGFzcz1cInctMTAwIHRleHQtY2VudGVyIG10LTNcIj5cbiAgICAgICAgPG5nLXRlbXBsYXRlIFtuZ0lmXT1cIiFhY2NvdW50QXRSaXNrRGV0YWlsc0xvYWRlZFwiPlxuICAgICAgICAgIDxwLXByb2dyZXNzU3Bpbm5lciBzdHJva2VXaWR0aD1cIjJcIj4gPC9wLXByb2dyZXNzU3Bpbm5lcj5cbiAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgIDwvZGl2PlxuICAgICAgPGRpdiBjbGFzcz1cInByaW1lbmctZGF0YXRhYmxlLWNvbnRhaW5lciB0YWJsZS1yZXNwb25zaXZlXCJcbiAgICAgICAgKm5nSWY9XCJhY2NvdW50QXRSaXNrPy5sZW5ndGhcIj5cbiAgICAgICAgPHAtdGFibGUgY2xhc3M9XCJ0YWJsZVwiXG4gICAgICAgICAgI2R0XG4gICAgICAgICAgW3ZhbHVlXT1cImFjY291bnRBdFJpc2tcIlxuICAgICAgICAgIFtwYWdpbmF0b3JdPVwidHJ1ZVwiXG4gICAgICAgICAgW3Jvd3NdPVwiMjBcIlxuXG4gICAgICAgICAgW3RvdGFsUmVjb3Jkc109XCJhY2NvdW50QXRSaXNrLmxlbmd0aFwiXG4+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlIHBUZW1wbGF0ZT1cImhlYWRlclwiPlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5TdW1tYXJ5LkFjY291bnQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuTVJSJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLlF1YXJ0ZXInIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPiB7eyAnQ3JtLkFjY291bnRNZXNzYWdlLk1vbnRoJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLlNpZ25VcEF0JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICA8L3RyPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlIHBUZW1wbGF0ZT1cImJvZHlcIlxuICAgICAgICAgICAgbGV0LWFjY291bnQ+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJBY2NvdW50XCI+XG4gICAgICAgICAgICAgICAgPGEgW3JvdXRlckxpbmtdPVwiWycvJyArIHN1YnNjcmlwdGlvbj8uc2x1ZyArIHJvdXRlcnMuYWNjb3VudEluZm8sIGFjY291bnQuY3JtX2FjY291bnRfaWRdXCIgY2xhc3M9XCJuYW1lLWxpbmtcIj5cbiAgICAgICAgICAgICAgICAgIDxzcGFuIFtuZ2JUb29sdGlwXT1cImFjY291bnQuY3JtX2FjY291bnRfbmFtZVwiPnt7IGFjY291bnQ/LmNybV9hY2NvdW50X25hbWUgfCB0ZXh0VHJ1bmNhdGU6MjAgfX08L3NwYW4+XG4gICAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiTVJSXCI+XG4gICAgICAgICAgICAgICAge3sgYWNjb3VudC5leHBlY3RlZF9tcnIgLyAxMDAgfCBjdXJyZW5jeTogYWNjb3VudC5jdXJyZW5jeSB9fVxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiUXVhcnRlclwiPnt7IGFjY291bnQuc2Vzc2lvbnNfbGFzdF9xdWFydGVyIH19PC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIk1vbnRoXCI+e3sgYWNjb3VudC5zZXNzaW9uc19sYXN0X21vbnRoIH19PC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIlNpZ25VcEF0XCI+XG4gICAgICAgICAgICAgICAge3sgYWNjb3VudC5zaWduZWRfdXBfYXQgfCBkYXRlRm9ybWF0IH19XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICA8L3RyPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgIDwvcC10YWJsZT5cbiAgICAgICAgPHNwYW4gY2xhc3M9XCJ0b3RhbC1yZWNvcmRzLWNvdW50XCIgICpuZ0lmPVwiYWNjb3VudEF0Umlzay5sZW5ndGggIT09IDBcIj57eyAnTGFiZWwuVG90YWwnIHwgdHJhbnNsb2NvIH19OiB7eyBhY2NvdW50QXRSaXNrLmxlbmd0aCB9fTwvc3Bhbj5cbiAgICAgIDwvZGl2PlxuICAgICAgPGRpdiAqbmdJZj1cImFjY291bnRBdFJpc2s/Lmxlbmd0aCA9PT0gMFwiPlxuICAgICAgICA8cHctbm8tZGF0YSBbd2l0aEltYWdlXT1cInRydWVcIiBbbWVzc2FnZV09XCInQ3JtLlN1bW1hcnkuTm9JbnNpZ2h0TWVzc2FnZScgfCB0cmFuc2xvY29cIj4gPC9wdy1uby1kYXRhPlxuICAgICAgPC9kaXY+XG4gICAgPC9kaXY+XG4gICAgPCEtLSBDb250cmFjdCByZW5ld2FsIC0tPlxuICAgIDxkaXYgY2xhc3M9XCJjb2wtMTIgY29sLW1kLTYgbWItMyBhbmFseXRpY3NcIj5cbiAgICAgIDxoNSBjbGFzcz1cImFjY29yZGlvbi1oZWFkaW5nXCI+Q29udHJhY3QgUmVuZXdhbDwvaDU+XG4gICAgICA8ZGl2IGNsYXNzPVwidy0xMDAgdGV4dC1jZW50ZXIgbXQtM1wiPlxuICAgICAgICA8bmctdGVtcGxhdGUgW25nSWZdPVwiIWNvbnRhY3RSZW5ld2FsTG9hZGVkXCI+XG4gICAgICAgICAgPHAtcHJvZ3Jlc3NTcGlubmVyIHN0cm9rZVdpZHRoPVwiMlwiPiA8L3AtcHJvZ3Jlc3NTcGlubmVyPlxuICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2IGNsYXNzPVwicHJpbWVuZy1kYXRhdGFibGUtY29udGFpbmVyIHRhYmxlLXJlc3BvbnNpdmVcIlxuICAgICAgICAqbmdJZj1cIkNvbnRyYWN0UmVuZXdhbD8ubGVuZ3RoXCI+XG4gICAgICAgIDxwLXRhYmxlIGNsYXNzPVwidGFibGVcIlxuICAgICAgICAgICNkdFxuICAgICAgICAgIFt2YWx1ZV09XCJDb250cmFjdFJlbmV3YWxcIlxuICAgICAgICAgIFtwYWdpbmF0b3JdPVwidHJ1ZVwiXG4gICAgICAgICAgW3Jvd3NdPVwiMjBcIlxuXG4gICAgICAgICAgW3RvdGFsUmVjb3Jkc109XCJDb250cmFjdFJlbmV3YWwubGVuZ3RoXCJcbj5cbiAgICAgICAgICA8bmctdGVtcGxhdGUgcFRlbXBsYXRlPVwiaGVhZGVyXCI+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLkFjY291bnQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuTVJSJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuUXVhcnRlcicgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+IHt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuTW9udGgnIHwgdHJhbnNsb2NvIH19PC90aD5cblxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5TaWduVXBBdCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5DQ0V4cEF0JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICA8L3RyPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlIHBUZW1wbGF0ZT1cImJvZHlcIlxuICAgICAgICAgICAgbGV0LWFjY291bnQ+XG4gICAgICAgICAgICA8dHI+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJBY2NvdW50XCI+XG4gICAgICAgICAgICAgICAgPGEgW3JvdXRlckxpbmtdPVwiWycvJyArIHN1YnNjcmlwdGlvbj8uc2x1ZyArIHJvdXRlcnMuYWNjb3VudEluZm8sIGFjY291bnQuY3JtX2FjY291bnRfaWRdXCIgY2xhc3M9XCJuYW1lLWxpbmtcIj5cbiAgICAgICAgICAgICAgICAgIDxzcGFuIFtuZ2JUb29sdGlwXT1cImFjY291bnQuY3JtX2FjY291bnRfbmFtZVwiPnt7IGFjY291bnQuY3JtX2FjY291bnRfbmFtZSB8IHRleHRUcnVuY2F0ZToyMCB9fTwvc3Bhbj5cbiAgICAgICAgICAgICAgICA8L2E+XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJNUlJcIj5cbiAgICAgICAgICAgICAgICB7eyBhY2NvdW50LmV4cGVjdGVkX21yciAvIDEwMCB8IGN1cnJlbmN5OiBhY2NvdW50LmN1cnJlbmN5IH19XG4gICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJRdWFydGVyXCI+e3sgYWNjb3VudC5zZXNzaW9uc19sYXN0X3F1YXJ0ZXIgfX08L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiTW9udGhcIj57eyBhY2NvdW50LnNlc3Npb25zX2xhc3RfbW9udGggfX08L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiU2lnblVwQXRcIj5cbiAgICAgICAgICAgICAgICB7eyBhY2NvdW50LnNpZ25lZF91cF9hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIkV4cEF0XCI+XG4gICAgICAgICAgICAgICAge3sgYWNjb3VudC5jY19leHBpcmluZ19hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgIDwvdHI+XG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9wLXRhYmxlPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRvdGFsLXJlY29yZHMtY291bnRcIiAqbmdJZj1cIkNvbnRyYWN0UmVuZXdhbC5sZW5ndGggIT09IDBcIj57eyAnTGFiZWwuVG90YWwnIHwgdHJhbnNsb2NvIH19OiB7eyBDb250cmFjdFJlbmV3YWwubGVuZ3RoIH19PC9zcGFuPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2ICpuZ0lmPVwiQ29udHJhY3RSZW5ld2FsPy5sZW5ndGggPT09IDBcIj5cbiAgICAgICAgPHB3LW5vLWRhdGEgW3dpdGhJbWFnZV09XCJ0cnVlXCIgW21lc3NhZ2VdPVwiJ0NybS5TdW1tYXJ5Lk5vSW5zaWdodE1lc3NhZ2UnIHwgdHJhbnNsb2NvXCI+IDwvcHctbm8tZGF0YT5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICAgIDwhLS0gQ3JlZGl0IENhcmQgRXhwaXJpbmcgLS0+XG4gICAgPGRpdiBjbGFzcz1cImNvbC0xMiBjb2wtbWQtNiBtYi0zIGFuYWx5dGljc1wiPlxuICAgICAgPGg1IGNsYXNzPVwiYWNjb3JkaW9uLWhlYWRpbmdcIj5DcmVkaXQgQ2FyZCBFeHBpcmluZzwvaDU+XG4gICAgICA8ZGl2IGNsYXNzPVwidy0xMDAgdGV4dC1jZW50ZXIgbXQtM1wiPlxuICAgICAgICA8bmctdGVtcGxhdGUgW25nSWZdPVwiIWNyZWRpdENhcmRFeHBpcmluZ0RldGFpbHNMb2FkZWRcIj5cbiAgICAgICAgICA8cC1wcm9ncmVzc1NwaW5uZXIgc3Ryb2tlV2lkdGg9XCIyXCI+IDwvcC1wcm9ncmVzc1NwaW5uZXI+XG4gICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgY2xhc3M9XCJwcmltZW5nLWRhdGF0YWJsZS1jb250YWluZXIgdGFibGUtcmVzcG9uc2l2ZVwiXG4gICAgICAgICpuZ0lmPVwiY3JlZGl0Q2FyZEV4cGlyaW5nPy5sZW5ndGhcIj5cbiAgICAgICAgPHAtdGFibGUgY2xhc3M9XCJ0YWJsZVwiXG4gICAgICAgICAgI2R0XG4gICAgICAgICAgW3ZhbHVlXT1cImNyZWRpdENhcmRFeHBpcmluZ1wiXG4gICAgICAgICAgW3BhZ2luYXRvcl09XCJ0cnVlXCJcbiAgICAgICAgICBbcm93c109XCIyMFwiXG5cbiAgICAgICAgICBbdG90YWxSZWNvcmRzXT1cImNyZWRpdENhcmRFeHBpcmluZy5sZW5ndGhcIlxuPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJoZWFkZXJcIj5cbiAgICAgICAgICAgIDx0cj5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuQWNjb3VudCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5NUlInIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuU2lnblVwQXQnIHwgdHJhbnNsb2NvIH19PC90aD5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uQWNjb3VudE1lc3NhZ2UuQ0NFeHBBdCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJib2R5XCJcbiAgICAgICAgICAgIGxldC1hY2NvdW50PlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWNjb3VudFwiPlxuICAgICAgICAgICAgICAgIDxhIFtyb3V0ZXJMaW5rXT1cIlsnLycgKyBzdWJzY3JpcHRpb24/LnNsdWcgKyByb3V0ZXJzLmFjY291bnRJbmZvLCBhY2NvdW50LmNybV9hY2NvdW50X2lkXVwiIGNsYXNzPVwibmFtZS1saW5rXCI+XG4gICAgICAgICAgICAgICAgICA8c3BhbiBbbmdiVG9vbHRpcF09XCJhY2NvdW50LmNybV9hY2NvdW50X25hbWVcIj57eyBhY2NvdW50LmNybV9hY2NvdW50X25hbWUgfCB0ZXh0VHJ1bmNhdGU6MjAgfX08L3NwYW4+XG4gICAgICAgICAgICAgICAgPC9hPlxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiTVJSXCI+XG4gICAgICAgICAgICAgICAge3sgYWNjb3VudC5leHBlY3RlZF9tcnIgLyAxMDAgfCBjdXJyZW5jeTogYWNjb3VudC5jdXJyZW5jeSB9fVxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiU2lnblVwQXRcIj5cbiAgICAgICAgICAgICAgICB7eyBhY2NvdW50LnNpZ25lZF91cF9hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIkV4cEF0XCI+XG4gICAgICAgICAgICAgICAge3sgYWNjb3VudC5jY19leHBpcmluZ19hdCB8IGRhdGVGb3JtYXQgfX1cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgIDwvdHI+XG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9wLXRhYmxlPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRvdGFsLXJlY29yZHMtY291bnRcIiAqbmdJZj1cImNyZWRpdENhcmRFeHBpcmluZy5sZW5ndGggIT09IDBcIj57eyAnTGFiZWwuVG90YWwnIHwgdHJhbnNsb2NvIH19OiB7eyBjcmVkaXRDYXJkRXhwaXJpbmcubGVuZ3RoIH19PC9zcGFuPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2ICpuZ0lmPVwiY3JlZGl0Q2FyZEV4cGlyaW5nPy5sZW5ndGggPT09IDBcIj5cbiAgICAgICAgPHB3LW5vLWRhdGEgW3dpdGhJbWFnZV09XCJ0cnVlXCIgW21lc3NhZ2VdPVwiJ0NybS5TdW1tYXJ5Lk5vSW5zaWdodE1lc3NhZ2UnIHwgdHJhbnNsb2NvXCI+IDwvcHctbm8tZGF0YT5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICAgIDwhLS0gTWFnaWMgTW9tZW50IC0tPlxuICAgIDxkaXYgY2xhc3M9XCJjb2wtMTIgY29sLW1kLTYgbWItMyBhbmFseXRpY3NcIj5cbiAgICAgIDxoNSBjbGFzcz1cImFjY29yZGlvbi1oZWFkaW5nXCI+TWFnaWMgTW9tZW50PC9oNT5cbiAgICAgIDxkaXYgY2xhc3M9XCJ3LTEwMCB0ZXh0LWNlbnRlciBtdC0zXCI+XG4gICAgICAgIDxuZy10ZW1wbGF0ZSBbbmdJZl09XCIhbWFnaWNNb21lbnRMb2FkZWRcIj5cbiAgICAgICAgICA8cC1wcm9ncmVzc1NwaW5uZXIgc3Ryb2tlV2lkdGg9XCIyXCI+IDwvcC1wcm9ncmVzc1NwaW5uZXI+XG4gICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkaXYgY2xhc3M9XCJwcmltZW5nLWRhdGF0YWJsZS1jb250YWluZXIgdGFibGUtcmVzcG9uc2l2ZVwiXG4gICAgICAgICpuZ0lmPVwibWFnaWNNb21lbnQ/Lmxlbmd0aFwiPlxuICAgICAgICA8cC10YWJsZSBjbGFzcz1cInRhYmxlXCJcbiAgICAgICAgICAjZHRcbiAgICAgICAgICBbdmFsdWVdPVwibWFnaWNNb21lbnRcIlxuICAgICAgICAgIFtwYWdpbmF0b3JdPVwidHJ1ZVwiXG4gICAgICAgICAgW3Jvd3NdPVwiMjBcIlxuXG4gICAgICAgICAgW3RvdGFsUmVjb3Jkc109XCJtYWdpY01vbWVudC5sZW5ndGhcIlxuPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJoZWFkZXJcIj5cbiAgICAgICAgICAgIDx0cj5cbiAgICAgICAgICAgICAgPHRoIHNjb3BlPVwidHJ1ZVwiPnt7ICdDcm0uU3VtbWFyeS5BY2NvdW50JyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj57eyAnQ3JtLkFjY291bnRNZXNzYWdlLk1SUicgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5RdWFydGVyJyB8IHRyYW5zbG9jbyB9fTwvdGg+XG4gICAgICAgICAgICAgIDx0aCBzY29wZT1cInRydWVcIj4ge3sgJ0NybS5BY2NvdW50TWVzc2FnZS5Nb250aCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgICA8dGggc2NvcGU9XCJ0cnVlXCI+e3sgJ0NybS5BY2NvdW50TWVzc2FnZS5TaWduVXBBdCcgfCB0cmFuc2xvY28gfX08L3RoPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZSBwVGVtcGxhdGU9XCJib2R5XCJcbiAgICAgICAgICAgIGxldC1hY2NvdW50PlxuICAgICAgICAgICAgPHRyPlxuICAgICAgICAgICAgICA8dGQgZGF0YS1oZWFkPVwiQWNjb3VudFwiPlxuICAgICAgICAgICAgICAgIDxhIFtyb3V0ZXJMaW5rXT1cIlsnLycgKyBzdWJzY3JpcHRpb24/LnNsdWcgKyByb3V0ZXJzLmFjY291bnRJbmZvLCBhY2NvdW50LmNybV9hY2NvdW50X2lkXVwiIGNsYXNzPVwibmFtZS1saW5rXCI+XG4gICAgICAgICAgICAgICAgICA8c3BhbiBbbmdiVG9vbHRpcF09XCJhY2NvdW50LmNybV9hY2NvdW50X25hbWVcIj57eyBhY2NvdW50Py5jcm1fYWNjb3VudF9uYW1lIHwgdGV4dFRydW5jYXRlOjIwIH19PC9zcGFuPlxuICAgICAgICAgICAgICAgIDwvYT5cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIk1SUlwiPlxuICAgICAgICAgICAgICAgIHt7IGFjY291bnQuZXhwZWN0ZWRfbXJyIC8gMTAwIHwgY3VycmVuY3k6IGFjY291bnQuY3VycmVuY3kgfX1cbiAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgPHRkIGRhdGEtaGVhZD1cIlF1YXJ0ZXJcIj57eyBhY2NvdW50LnNlc3Npb25zX2xhc3RfcXVhcnRlciB9fTwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJNb250aFwiPnt7IGFjY291bnQuc2Vzc2lvbnNfbGFzdF9tb250aCB9fTwvdGQ+XG4gICAgICAgICAgICAgIDx0ZCBkYXRhLWhlYWQ9XCJTaWduVXBBdFwiPlxuICAgICAgICAgICAgICAgIHt7IGFjY291bnQuc2lnbmVkX3VwX2F0IHwgZGF0ZUZvcm1hdCB9fVxuICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICA8L3AtdGFibGU+XG4gICAgICAgIDxzcGFuIGNsYXNzPVwidG90YWwtcmVjb3Jkcy1jb3VudFwiICpuZ0lmPVwibWFnaWNNb21lbnQubGVuZ3RoICE9PTAgXCI+e3sgJ0xhYmVsLlRvdGFsJyB8IHRyYW5zbG9jbyB9fToge3sgbWFnaWNNb21lbnQubGVuZ3RoIH19PC9zcGFuPlxuICAgICAgPC9kaXY+XG4gICAgICA8ZGl2ICpuZ0lmPVwibWFnaWNNb21lbnQ/Lmxlbmd0aCA9PT0gMFwiPlxuICAgICAgICA8cHctbm8tZGF0YSBbd2l0aEltYWdlXT1cInRydWVcIiBbbWVzc2FnZV09XCInQ3JtLlN1bW1hcnkuTm9JbnNpZ2h0TWVzc2FnZScgfCB0cmFuc2xvY29cIj4gPC9wdy1uby1kYXRhPlxuICAgICAgPC9kaXY+XG4gICAgPC9kaXY+XG4gIDwvbmctY29udGFpbmVyPlxuPC9kaXY+XG4iXX0=
|
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
import { Injector, OnDestroy, OnInit } from '@angular/core';
|
|
2
|
-
import { CrmService } from '@posiwise/smart-crm-shared';
|
|
3
|
-
import { AppBaseComponent } from '@posiwise/app-base-component';
|
|
4
|
-
import { Plotly } from '@posiwise/common-utilities';
|
|
5
|
-
import * as i0 from "@angular/core";
|
|
6
|
-
export declare class SmartCrmOverviewComponent extends AppBaseComponent implements OnInit, OnDestroy {
|
|
7
|
-
private readonly crmService;
|
|
8
|
-
graph: Plotly.Figure;
|
|
9
|
-
subscriptionId: number;
|
|
10
|
-
hasAccess: boolean;
|
|
11
|
-
userId: number;
|
|
12
|
-
isLoaded: boolean;
|
|
13
|
-
constructor(crmService: CrmService, injector: Injector);
|
|
14
|
-
ngOnInit(): void;
|
|
15
|
-
/** Function to get the data for the graph */
|
|
16
|
-
private getChartData;
|
|
17
|
-
ngOnDestroy(): void;
|
|
18
|
-
static ɵfac: i0.ɵɵFactoryDeclaration<SmartCrmOverviewComponent, never>;
|
|
19
|
-
static ɵcmp: i0.ɵɵComponentDeclaration<SmartCrmOverviewComponent, "pw-smart-crm-overview", never, {}, {}, never, never, false, never>;
|
|
20
|
-
}
|