@vritti/api-sdk 0.3.5 → 0.3.6
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/catalog-resolver.cjs +147 -125
- package/dist/catalog-resolver.cjs.map +1 -1
- package/dist/catalog-resolver.d.cts +49 -46
- package/dist/catalog-resolver.d.ts +49 -46
- package/dist/catalog-resolver.js +146 -125
- package/dist/catalog-resolver.js.map +1 -1
- package/dist/license.d.cts +1 -1
- package/dist/license.d.ts +1 -1
- package/dist/{types-C9jPdQqH.d.cts → types-BBK6MG-U.d.cts} +7 -2
- package/dist/{types-C9jPdQqH.d.ts → types-BBK6MG-U.d.ts} +7 -2
- package/package.json +1 -1
|
@@ -1,51 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
export { B as BusinessVocabulary, C as CatalogPermission,
|
|
3
|
-
|
|
4
|
-
interface SiteMatrixCell {
|
|
5
|
-
inPlan: boolean;
|
|
6
|
-
selected: boolean;
|
|
7
|
-
availableIn: string[];
|
|
8
|
-
}
|
|
9
|
-
interface SiteMatrixPermission {
|
|
10
|
-
code: string;
|
|
11
|
-
label: string;
|
|
12
|
-
dependsOn: string[];
|
|
13
|
-
web: SiteMatrixCell | null;
|
|
14
|
-
mobile: SiteMatrixCell | null;
|
|
15
|
-
}
|
|
16
|
-
interface SiteMatrixFeature {
|
|
17
|
-
code: string;
|
|
18
|
-
name: string;
|
|
19
|
-
icon: string | null;
|
|
20
|
-
scope: ScopeType;
|
|
21
|
-
applicableSiteTypes: SiteType[];
|
|
22
|
-
platforms: PlatformBucket[];
|
|
23
|
-
inPlan: boolean;
|
|
24
|
-
availableIn: string[];
|
|
25
|
-
permissions: SiteMatrixPermission[];
|
|
26
|
-
}
|
|
27
|
-
interface SiteMatrixApp {
|
|
28
|
-
code: string;
|
|
29
|
-
name: string;
|
|
30
|
-
icon: string | null;
|
|
31
|
-
unlockedCount: number;
|
|
32
|
-
totalCount: number;
|
|
33
|
-
features: SiteMatrixFeature[];
|
|
34
|
-
}
|
|
35
|
-
interface SiteMatrix {
|
|
36
|
-
plan: {
|
|
37
|
-
code: string;
|
|
38
|
-
name: string;
|
|
39
|
-
};
|
|
40
|
-
apps: SiteMatrixApp[];
|
|
41
|
-
locks: SiteFeatureLocks;
|
|
42
|
-
}
|
|
43
|
-
declare function buildSiteMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, siteType?: SiteType): SiteMatrix;
|
|
44
|
-
declare function buildPlanMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks?: SiteFeatureLocks): SiteMatrix;
|
|
1
|
+
import { V as VersionSnapshot, S as SiteFeatureLocks, P as PlatformBucket, a as SiteType, b as ScopeType, c as ServiceCode, F as FeatureCatalogEntry, R as RoleItem, d as SnapshotFeature, e as PlatformCodes, f as FeatureUnlocks, g as PlatformDenyCodes, L as LockReason } from './types-BBK6MG-U.cjs';
|
|
2
|
+
export { B as BusinessVocabulary, C as CatalogPermission, h as FeatureLocks, i as PLATFORMS, j as SERVICE_CODES, k as SITE_TYPES, l as SNAPSHOT_SCHEMA_VERSION, m as SnapshotApp, n as SnapshotAppFeatureRef, o as SnapshotBusiness, p as SnapshotMicrofrontendMobile, r as SnapshotMicrofrontendWeb, q as SnapshotMicrofrontends, s as SnapshotPermission, t as SnapshotPlan, u as SnapshotRoleTemplate, w as VocabularyEntry, v as snapshotFeatureKey } from './types-BBK6MG-U.cjs';
|
|
45
3
|
|
|
46
4
|
declare function featureAppliesAtNode(applicableSiteTypes: SiteType[], siteType: SiteType): boolean;
|
|
47
5
|
declare function findFeatureByCode(snapshot: VersionSnapshot, code: string): SnapshotFeature | undefined;
|
|
48
|
-
declare function buildSiteCatalog(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, bucket: PlatformBucket, siteType?: SiteType, scope?: ScopeType): FeatureCatalogEntry[];
|
|
6
|
+
declare function buildSiteCatalog(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, bucket: PlatformBucket, siteType?: SiteType, scope?: ScopeType, availableServices?: ServiceCode[]): FeatureCatalogEntry[];
|
|
49
7
|
declare function isPlanMember(entry: PlatformCodes | undefined): boolean;
|
|
50
8
|
declare function isSiteLockedOnPlatform(entry: SiteFeatureLocks[string] | undefined, platform: PlatformBucket, code: string): boolean;
|
|
51
9
|
declare function buildSiteRoles(snapshot: VersionSnapshot, businessCode: string | undefined): RoleItem[];
|
|
@@ -72,6 +30,7 @@ interface LockedPermission {
|
|
|
72
30
|
code: string;
|
|
73
31
|
reason: LockReason | null;
|
|
74
32
|
unlockPlans: string[];
|
|
33
|
+
missingServices: ServiceCode[];
|
|
75
34
|
}
|
|
76
35
|
interface PlanUpsell {
|
|
77
36
|
plan: string;
|
|
@@ -87,6 +46,7 @@ interface PermissionFeature {
|
|
|
87
46
|
locked: boolean;
|
|
88
47
|
lockReason: LockReason | null;
|
|
89
48
|
unlockPlans: string[];
|
|
49
|
+
missingServices: ServiceCode[];
|
|
90
50
|
lockedPermissions: LockedPermission[];
|
|
91
51
|
upsell: PlanUpsell[];
|
|
92
52
|
route: {
|
|
@@ -108,6 +68,7 @@ interface ResolveUserFeaturesParams {
|
|
|
108
68
|
platform: ClientPlatform;
|
|
109
69
|
siteType?: SiteType;
|
|
110
70
|
scope?: ScopeType;
|
|
71
|
+
availableServices?: ServiceCode[];
|
|
111
72
|
}
|
|
112
73
|
declare function resolveUserFeatures(params: ResolveUserFeaturesParams): PermissionFeature[];
|
|
113
74
|
declare function pickRouteForPlatform(entry: {
|
|
@@ -128,4 +89,46 @@ declare function pickRouteForPlatform(entry: {
|
|
|
128
89
|
routePrefix: string;
|
|
129
90
|
} | null;
|
|
130
91
|
|
|
131
|
-
|
|
92
|
+
interface SiteMatrixCell {
|
|
93
|
+
inPlan: boolean;
|
|
94
|
+
selected: boolean;
|
|
95
|
+
availableIn: string[];
|
|
96
|
+
}
|
|
97
|
+
interface SiteMatrixPermission {
|
|
98
|
+
code: string;
|
|
99
|
+
label: string;
|
|
100
|
+
dependsOn: string[];
|
|
101
|
+
web: SiteMatrixCell | null;
|
|
102
|
+
mobile: SiteMatrixCell | null;
|
|
103
|
+
}
|
|
104
|
+
interface SiteMatrixFeature {
|
|
105
|
+
code: string;
|
|
106
|
+
name: string;
|
|
107
|
+
icon: string | null;
|
|
108
|
+
scope: ScopeType;
|
|
109
|
+
applicableSiteTypes: SiteType[];
|
|
110
|
+
platforms: PlatformBucket[];
|
|
111
|
+
inPlan: boolean;
|
|
112
|
+
availableIn: string[];
|
|
113
|
+
permissions: SiteMatrixPermission[];
|
|
114
|
+
}
|
|
115
|
+
interface SiteMatrixApp {
|
|
116
|
+
code: string;
|
|
117
|
+
name: string;
|
|
118
|
+
icon: string | null;
|
|
119
|
+
unlockedCount: number;
|
|
120
|
+
totalCount: number;
|
|
121
|
+
features: SiteMatrixFeature[];
|
|
122
|
+
}
|
|
123
|
+
interface SiteMatrix {
|
|
124
|
+
plan: {
|
|
125
|
+
code: string;
|
|
126
|
+
name: string;
|
|
127
|
+
};
|
|
128
|
+
apps: SiteMatrixApp[];
|
|
129
|
+
locks: SiteFeatureLocks;
|
|
130
|
+
}
|
|
131
|
+
declare function buildSiteMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, siteType?: SiteType): SiteMatrix;
|
|
132
|
+
declare function buildPlanMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks?: SiteFeatureLocks): SiteMatrix;
|
|
133
|
+
|
|
134
|
+
export { type ClientPlatform, type ComposeRoleGrantsParams, type DependsMap, FeatureCatalogEntry, FeatureUnlocks, LockReason, type LockedPermission, type PermissionFeature, PlatformBucket, PlatformCodes, PlatformDenyCodes, type ResolveUserFeaturesParams, type RevokedGrants, RoleItem, ScopeType, ServiceCode, SiteFeatureLocks, type SiteMatrix, type SiteMatrixApp, type SiteMatrixCell, type SiteMatrixFeature, type SiteMatrixPermission, SiteType, SnapshotFeature, VersionSnapshot, buildDependsMap, buildPlanMatrix, buildSiteCatalog, buildSiteMatrix, buildSiteRoles, cascadeLocked, composeRoleGrants, featureAppliesAtNode, filterGrantedByDeps, findFeatureByCode, isPlanMember, isSiteLockedOnPlatform, pickRouteForPlatform, prereqClosure, resolveUserFeatures };
|
|
@@ -1,51 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
export { B as BusinessVocabulary, C as CatalogPermission,
|
|
3
|
-
|
|
4
|
-
interface SiteMatrixCell {
|
|
5
|
-
inPlan: boolean;
|
|
6
|
-
selected: boolean;
|
|
7
|
-
availableIn: string[];
|
|
8
|
-
}
|
|
9
|
-
interface SiteMatrixPermission {
|
|
10
|
-
code: string;
|
|
11
|
-
label: string;
|
|
12
|
-
dependsOn: string[];
|
|
13
|
-
web: SiteMatrixCell | null;
|
|
14
|
-
mobile: SiteMatrixCell | null;
|
|
15
|
-
}
|
|
16
|
-
interface SiteMatrixFeature {
|
|
17
|
-
code: string;
|
|
18
|
-
name: string;
|
|
19
|
-
icon: string | null;
|
|
20
|
-
scope: ScopeType;
|
|
21
|
-
applicableSiteTypes: SiteType[];
|
|
22
|
-
platforms: PlatformBucket[];
|
|
23
|
-
inPlan: boolean;
|
|
24
|
-
availableIn: string[];
|
|
25
|
-
permissions: SiteMatrixPermission[];
|
|
26
|
-
}
|
|
27
|
-
interface SiteMatrixApp {
|
|
28
|
-
code: string;
|
|
29
|
-
name: string;
|
|
30
|
-
icon: string | null;
|
|
31
|
-
unlockedCount: number;
|
|
32
|
-
totalCount: number;
|
|
33
|
-
features: SiteMatrixFeature[];
|
|
34
|
-
}
|
|
35
|
-
interface SiteMatrix {
|
|
36
|
-
plan: {
|
|
37
|
-
code: string;
|
|
38
|
-
name: string;
|
|
39
|
-
};
|
|
40
|
-
apps: SiteMatrixApp[];
|
|
41
|
-
locks: SiteFeatureLocks;
|
|
42
|
-
}
|
|
43
|
-
declare function buildSiteMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, siteType?: SiteType): SiteMatrix;
|
|
44
|
-
declare function buildPlanMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks?: SiteFeatureLocks): SiteMatrix;
|
|
1
|
+
import { V as VersionSnapshot, S as SiteFeatureLocks, P as PlatformBucket, a as SiteType, b as ScopeType, c as ServiceCode, F as FeatureCatalogEntry, R as RoleItem, d as SnapshotFeature, e as PlatformCodes, f as FeatureUnlocks, g as PlatformDenyCodes, L as LockReason } from './types-BBK6MG-U.js';
|
|
2
|
+
export { B as BusinessVocabulary, C as CatalogPermission, h as FeatureLocks, i as PLATFORMS, j as SERVICE_CODES, k as SITE_TYPES, l as SNAPSHOT_SCHEMA_VERSION, m as SnapshotApp, n as SnapshotAppFeatureRef, o as SnapshotBusiness, p as SnapshotMicrofrontendMobile, r as SnapshotMicrofrontendWeb, q as SnapshotMicrofrontends, s as SnapshotPermission, t as SnapshotPlan, u as SnapshotRoleTemplate, w as VocabularyEntry, v as snapshotFeatureKey } from './types-BBK6MG-U.js';
|
|
45
3
|
|
|
46
4
|
declare function featureAppliesAtNode(applicableSiteTypes: SiteType[], siteType: SiteType): boolean;
|
|
47
5
|
declare function findFeatureByCode(snapshot: VersionSnapshot, code: string): SnapshotFeature | undefined;
|
|
48
|
-
declare function buildSiteCatalog(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, bucket: PlatformBucket, siteType?: SiteType, scope?: ScopeType): FeatureCatalogEntry[];
|
|
6
|
+
declare function buildSiteCatalog(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, bucket: PlatformBucket, siteType?: SiteType, scope?: ScopeType, availableServices?: ServiceCode[]): FeatureCatalogEntry[];
|
|
49
7
|
declare function isPlanMember(entry: PlatformCodes | undefined): boolean;
|
|
50
8
|
declare function isSiteLockedOnPlatform(entry: SiteFeatureLocks[string] | undefined, platform: PlatformBucket, code: string): boolean;
|
|
51
9
|
declare function buildSiteRoles(snapshot: VersionSnapshot, businessCode: string | undefined): RoleItem[];
|
|
@@ -72,6 +30,7 @@ interface LockedPermission {
|
|
|
72
30
|
code: string;
|
|
73
31
|
reason: LockReason | null;
|
|
74
32
|
unlockPlans: string[];
|
|
33
|
+
missingServices: ServiceCode[];
|
|
75
34
|
}
|
|
76
35
|
interface PlanUpsell {
|
|
77
36
|
plan: string;
|
|
@@ -87,6 +46,7 @@ interface PermissionFeature {
|
|
|
87
46
|
locked: boolean;
|
|
88
47
|
lockReason: LockReason | null;
|
|
89
48
|
unlockPlans: string[];
|
|
49
|
+
missingServices: ServiceCode[];
|
|
90
50
|
lockedPermissions: LockedPermission[];
|
|
91
51
|
upsell: PlanUpsell[];
|
|
92
52
|
route: {
|
|
@@ -108,6 +68,7 @@ interface ResolveUserFeaturesParams {
|
|
|
108
68
|
platform: ClientPlatform;
|
|
109
69
|
siteType?: SiteType;
|
|
110
70
|
scope?: ScopeType;
|
|
71
|
+
availableServices?: ServiceCode[];
|
|
111
72
|
}
|
|
112
73
|
declare function resolveUserFeatures(params: ResolveUserFeaturesParams): PermissionFeature[];
|
|
113
74
|
declare function pickRouteForPlatform(entry: {
|
|
@@ -128,4 +89,46 @@ declare function pickRouteForPlatform(entry: {
|
|
|
128
89
|
routePrefix: string;
|
|
129
90
|
} | null;
|
|
130
91
|
|
|
131
|
-
|
|
92
|
+
interface SiteMatrixCell {
|
|
93
|
+
inPlan: boolean;
|
|
94
|
+
selected: boolean;
|
|
95
|
+
availableIn: string[];
|
|
96
|
+
}
|
|
97
|
+
interface SiteMatrixPermission {
|
|
98
|
+
code: string;
|
|
99
|
+
label: string;
|
|
100
|
+
dependsOn: string[];
|
|
101
|
+
web: SiteMatrixCell | null;
|
|
102
|
+
mobile: SiteMatrixCell | null;
|
|
103
|
+
}
|
|
104
|
+
interface SiteMatrixFeature {
|
|
105
|
+
code: string;
|
|
106
|
+
name: string;
|
|
107
|
+
icon: string | null;
|
|
108
|
+
scope: ScopeType;
|
|
109
|
+
applicableSiteTypes: SiteType[];
|
|
110
|
+
platforms: PlatformBucket[];
|
|
111
|
+
inPlan: boolean;
|
|
112
|
+
availableIn: string[];
|
|
113
|
+
permissions: SiteMatrixPermission[];
|
|
114
|
+
}
|
|
115
|
+
interface SiteMatrixApp {
|
|
116
|
+
code: string;
|
|
117
|
+
name: string;
|
|
118
|
+
icon: string | null;
|
|
119
|
+
unlockedCount: number;
|
|
120
|
+
totalCount: number;
|
|
121
|
+
features: SiteMatrixFeature[];
|
|
122
|
+
}
|
|
123
|
+
interface SiteMatrix {
|
|
124
|
+
plan: {
|
|
125
|
+
code: string;
|
|
126
|
+
name: string;
|
|
127
|
+
};
|
|
128
|
+
apps: SiteMatrixApp[];
|
|
129
|
+
locks: SiteFeatureLocks;
|
|
130
|
+
}
|
|
131
|
+
declare function buildSiteMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks: SiteFeatureLocks | undefined, siteType?: SiteType): SiteMatrix;
|
|
132
|
+
declare function buildPlanMatrix(snapshot: VersionSnapshot, businessCode: string | undefined, planCode: string | undefined, siteLocks?: SiteFeatureLocks): SiteMatrix;
|
|
133
|
+
|
|
134
|
+
export { type ClientPlatform, type ComposeRoleGrantsParams, type DependsMap, FeatureCatalogEntry, FeatureUnlocks, LockReason, type LockedPermission, type PermissionFeature, PlatformBucket, PlatformCodes, PlatformDenyCodes, type ResolveUserFeaturesParams, type RevokedGrants, RoleItem, ScopeType, ServiceCode, SiteFeatureLocks, type SiteMatrix, type SiteMatrixApp, type SiteMatrixCell, type SiteMatrixFeature, type SiteMatrixPermission, SiteType, SnapshotFeature, VersionSnapshot, buildDependsMap, buildPlanMatrix, buildSiteCatalog, buildSiteMatrix, buildSiteRoles, cascadeLocked, composeRoleGrants, featureAppliesAtNode, filterGrantedByDeps, findFeatureByCode, isPlanMember, isSiteLockedOnPlatform, pickRouteForPlatform, prereqClosure, resolveUserFeatures };
|
package/dist/catalog-resolver.js
CHANGED
|
@@ -81,6 +81,9 @@ var SITE_TYPES = [
|
|
|
81
81
|
"WAREHOUSE",
|
|
82
82
|
"PRODUCTION"
|
|
83
83
|
];
|
|
84
|
+
var SERVICE_CODES = [
|
|
85
|
+
"GITEA"
|
|
86
|
+
];
|
|
84
87
|
function snapshotFeatureKey(code, scope) {
|
|
85
88
|
return `${scope}.${code}`;
|
|
86
89
|
}
|
|
@@ -99,7 +102,7 @@ function findFeatureByCode(snapshot, code) {
|
|
|
99
102
|
return void 0;
|
|
100
103
|
}
|
|
101
104
|
__name(findFeatureByCode, "findFeatureByCode");
|
|
102
|
-
function buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, siteType, scope) {
|
|
105
|
+
function buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, siteType, scope, availableServices = []) {
|
|
103
106
|
if (!businessCode) return [];
|
|
104
107
|
const business = snapshot.businesses?.[businessCode];
|
|
105
108
|
if (!business) return [];
|
|
@@ -116,11 +119,12 @@ function buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, s
|
|
|
116
119
|
const membership = plan?.unlockedPermissions?.[feature.code];
|
|
117
120
|
const web = feature.microfrontends?.web;
|
|
118
121
|
const mobile = feature.microfrontends?.mobile;
|
|
119
|
-
const permissions = buildPermissions(feature, businessCode, membership, siteLocks, plans, bucket);
|
|
120
122
|
const memberOnBucket = membership?.[bucket] !== void 0;
|
|
121
123
|
const sitePlatformLocked = siteLocks?.[feature.code]?.[bucket] === null;
|
|
122
|
-
const
|
|
123
|
-
const
|
|
124
|
+
const missingServices = unmetServices(feature, availableServices);
|
|
125
|
+
const permissions = buildPermissions(feature, businessCode, membership, siteLocks, plans, bucket, missingServices);
|
|
126
|
+
const lockReason = resolveLockReason(!memberOnBucket, sitePlatformLocked, missingServices);
|
|
127
|
+
const locked = lockReason !== null;
|
|
124
128
|
const unlockPlans = lockReason === "PLAN" ? plansIncludingFeature(plans, feature.code, bucket) : [];
|
|
125
129
|
catalog.push({
|
|
126
130
|
code: feature.code,
|
|
@@ -146,6 +150,7 @@ function buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, s
|
|
|
146
150
|
locked,
|
|
147
151
|
lockReason,
|
|
148
152
|
unlockPlans,
|
|
153
|
+
missingServices,
|
|
149
154
|
permissions
|
|
150
155
|
});
|
|
151
156
|
}
|
|
@@ -157,12 +162,23 @@ function isPlanMember(entry) {
|
|
|
157
162
|
return !!entry && (entry.web !== void 0 || entry.mobile !== void 0);
|
|
158
163
|
}
|
|
159
164
|
__name(isPlanMember, "isPlanMember");
|
|
165
|
+
function resolveLockReason(planLocked, siteLocked, missingServices) {
|
|
166
|
+
if (planLocked) return "PLAN";
|
|
167
|
+
if (siteLocked) return "SITE";
|
|
168
|
+
if (missingServices.length > 0) return "SERVICE";
|
|
169
|
+
return null;
|
|
170
|
+
}
|
|
171
|
+
__name(resolveLockReason, "resolveLockReason");
|
|
172
|
+
function unmetServices(feature, availableServices) {
|
|
173
|
+
return (feature.requiredServices ?? []).filter((service) => !availableServices.includes(service));
|
|
174
|
+
}
|
|
175
|
+
__name(unmetServices, "unmetServices");
|
|
160
176
|
function isSiteLockedOnPlatform(entry, platform, code) {
|
|
161
177
|
const locks = entry?.[platform];
|
|
162
178
|
return locks === null || (locks?.includes(code) ?? false);
|
|
163
179
|
}
|
|
164
180
|
__name(isSiteLockedOnPlatform, "isSiteLockedOnPlatform");
|
|
165
|
-
function buildPermissions(feature, businessCode, planMembership, siteLocks, plans, bucket) {
|
|
181
|
+
function buildPermissions(feature, businessCode, planMembership, siteLocks, plans, bucket, missingServices = []) {
|
|
166
182
|
const planUnlocked = new Set(planMembership?.[bucket] ?? []);
|
|
167
183
|
const lockEntry = siteLocks?.[feature.code];
|
|
168
184
|
const perms = (feature.permissions ?? []).filter((p) => p.isGlobal || p.businesses.includes(businessCode));
|
|
@@ -180,20 +196,22 @@ function buildPermissions(feature, businessCode, planMembership, siteLocks, plan
|
|
|
180
196
|
]);
|
|
181
197
|
const lockedSet = cascadeLocked(codes, directlyLocked, deps);
|
|
182
198
|
return perms.map((p) => {
|
|
183
|
-
const locked = lockedSet.has(p.code);
|
|
184
199
|
const closure = [
|
|
185
200
|
p.code,
|
|
186
201
|
...prereqClosure(p.code, deps)
|
|
187
202
|
];
|
|
188
|
-
const
|
|
189
|
-
const
|
|
190
|
-
const
|
|
191
|
-
const
|
|
203
|
+
const cascaded = lockedSet.has(p.code);
|
|
204
|
+
const planReason = cascaded && closure.some((c) => directlyPlanLocked.has(c));
|
|
205
|
+
const siteReason = cascaded && closure.some((c) => directlySiteLocked.has(c));
|
|
206
|
+
const lockReason = resolveLockReason(planReason, siteReason, missingServices);
|
|
207
|
+
const locked = lockReason !== null;
|
|
208
|
+
const unlockPlans = lockReason === "PLAN" ? plansUnlockingClosure(plans, feature.code, closure, bucket) : [];
|
|
192
209
|
return {
|
|
193
210
|
code: p.code,
|
|
194
211
|
locked,
|
|
195
212
|
lockReason,
|
|
196
|
-
unlockPlans
|
|
213
|
+
unlockPlans,
|
|
214
|
+
missingServices
|
|
197
215
|
};
|
|
198
216
|
});
|
|
199
217
|
}
|
|
@@ -223,117 +241,6 @@ function buildSiteRoles(snapshot, businessCode) {
|
|
|
223
241
|
}
|
|
224
242
|
__name(buildSiteRoles, "buildSiteRoles");
|
|
225
243
|
|
|
226
|
-
// src/catalog-resolver/site-matrix.builder.ts
|
|
227
|
-
function buildSiteMatrix(snapshot, businessCode, planCode, siteLocks, siteType) {
|
|
228
|
-
return buildMatrix(snapshot, businessCode, planCode, siteLocks, false, siteType);
|
|
229
|
-
}
|
|
230
|
-
__name(buildSiteMatrix, "buildSiteMatrix");
|
|
231
|
-
function buildPlanMatrix(snapshot, businessCode, planCode, siteLocks) {
|
|
232
|
-
return buildMatrix(snapshot, businessCode, planCode, siteLocks, true);
|
|
233
|
-
}
|
|
234
|
-
__name(buildPlanMatrix, "buildPlanMatrix");
|
|
235
|
-
function buildMatrix(snapshot, businessCode, planCode, siteLocks, allScopes, siteType) {
|
|
236
|
-
const business = businessCode ? snapshot.businesses?.[businessCode] : void 0;
|
|
237
|
-
const plans = business?.plans ?? {};
|
|
238
|
-
const plan = planCode ? plans[planCode] : void 0;
|
|
239
|
-
const planMeta = {
|
|
240
|
-
code: planCode ?? "",
|
|
241
|
-
name: plan?.name ?? planCode ?? ""
|
|
242
|
-
};
|
|
243
|
-
const locks = siteLocks ?? {};
|
|
244
|
-
if (!business || !plan) return {
|
|
245
|
-
plan: planMeta,
|
|
246
|
-
apps: [],
|
|
247
|
-
locks
|
|
248
|
-
};
|
|
249
|
-
const apps = [];
|
|
250
|
-
for (const app of business.apps) {
|
|
251
|
-
let unlockedCount = 0;
|
|
252
|
-
let totalCount = 0;
|
|
253
|
-
const features = [];
|
|
254
|
-
for (const ref of app.features) {
|
|
255
|
-
if (!allScopes && ref.scope !== "SITE") continue;
|
|
256
|
-
const code = ref.code;
|
|
257
|
-
const feature = snapshot.features?.[snapshotFeatureKey(code, ref.scope)];
|
|
258
|
-
if (!feature) continue;
|
|
259
|
-
if (siteType !== void 0 && !featureAppliesAtNode(feature.applicableSiteTypes, siteType)) continue;
|
|
260
|
-
const platforms = PLATFORMS.filter((p) => !!feature.microfrontends?.[p]);
|
|
261
|
-
if (platforms.length === 0) continue;
|
|
262
|
-
const membership = plan.unlockedPermissions?.[code];
|
|
263
|
-
const featureInPlan = isPlanMember(membership);
|
|
264
|
-
const siteEntry = siteLocks?.[code];
|
|
265
|
-
const permissions = (feature.permissions ?? []).filter((p) => p.isGlobal || p.businesses.includes(businessCode ?? "")).map((p) => {
|
|
266
|
-
const cell = /* @__PURE__ */ __name((plat) => {
|
|
267
|
-
if (!platforms.includes(plat)) return null;
|
|
268
|
-
const planCodes = membership?.[plat];
|
|
269
|
-
const inPlan = featureInPlan && planCodes !== void 0 && planCodes.includes(p.code);
|
|
270
|
-
const selected = inPlan && !isSiteLockedOnPlatform(siteEntry, plat, p.code);
|
|
271
|
-
const availableIn = inPlan ? [] : plansUnlockingPerm(plans, code, p.code, plat, planCode);
|
|
272
|
-
totalCount += 1;
|
|
273
|
-
if (inPlan) unlockedCount += 1;
|
|
274
|
-
return {
|
|
275
|
-
inPlan,
|
|
276
|
-
selected,
|
|
277
|
-
availableIn
|
|
278
|
-
};
|
|
279
|
-
}, "cell");
|
|
280
|
-
return {
|
|
281
|
-
code: p.code,
|
|
282
|
-
label: p.label,
|
|
283
|
-
dependsOn: p.dependsOn ?? [],
|
|
284
|
-
web: cell("web"),
|
|
285
|
-
mobile: cell("mobile")
|
|
286
|
-
};
|
|
287
|
-
});
|
|
288
|
-
features.push({
|
|
289
|
-
code: feature.code,
|
|
290
|
-
name: feature.name,
|
|
291
|
-
icon: feature.lucideIcon ?? null,
|
|
292
|
-
scope: feature.scope,
|
|
293
|
-
applicableSiteTypes: feature.applicableSiteTypes,
|
|
294
|
-
platforms,
|
|
295
|
-
inPlan: featureInPlan,
|
|
296
|
-
availableIn: featureInPlan ? [] : plansIncludingFeature2(plans, code, planCode),
|
|
297
|
-
permissions
|
|
298
|
-
});
|
|
299
|
-
}
|
|
300
|
-
if (features.length === 0) continue;
|
|
301
|
-
apps.push({
|
|
302
|
-
code: app.code,
|
|
303
|
-
name: app.name,
|
|
304
|
-
icon: app.icon ?? null,
|
|
305
|
-
unlockedCount,
|
|
306
|
-
totalCount,
|
|
307
|
-
features
|
|
308
|
-
});
|
|
309
|
-
}
|
|
310
|
-
apps.sort((a, b) => a.name.localeCompare(b.name));
|
|
311
|
-
return {
|
|
312
|
-
plan: planMeta,
|
|
313
|
-
apps,
|
|
314
|
-
locks
|
|
315
|
-
};
|
|
316
|
-
}
|
|
317
|
-
__name(buildMatrix, "buildMatrix");
|
|
318
|
-
function plansUnlockingPerm(plans, featureCode, permCode, platform, excludeCode) {
|
|
319
|
-
const names = [];
|
|
320
|
-
for (const [code, p] of Object.entries(plans)) {
|
|
321
|
-
if (code === excludeCode) continue;
|
|
322
|
-
if ((p.unlockedPermissions?.[featureCode]?.[platform] ?? []).includes(permCode)) names.push(p.name);
|
|
323
|
-
}
|
|
324
|
-
return names;
|
|
325
|
-
}
|
|
326
|
-
__name(plansUnlockingPerm, "plansUnlockingPerm");
|
|
327
|
-
function plansIncludingFeature2(plans, featureCode, excludeCode) {
|
|
328
|
-
const names = [];
|
|
329
|
-
for (const [code, p] of Object.entries(plans)) {
|
|
330
|
-
if (code === excludeCode) continue;
|
|
331
|
-
if (isPlanMember(p.unlockedPermissions?.[featureCode])) names.push(p.name);
|
|
332
|
-
}
|
|
333
|
-
return names;
|
|
334
|
-
}
|
|
335
|
-
__name(plansIncludingFeature2, "plansIncludingFeature");
|
|
336
|
-
|
|
337
244
|
// src/catalog-resolver/compose-role-grants.ts
|
|
338
245
|
function unionBucket(base, add) {
|
|
339
246
|
if (base === void 0 && add === void 0) return void 0;
|
|
@@ -373,10 +280,10 @@ __name(composeRoleGrants, "composeRoleGrants");
|
|
|
373
280
|
|
|
374
281
|
// src/catalog-resolver/resolve-user-features.ts
|
|
375
282
|
function resolveUserFeatures(params) {
|
|
376
|
-
const { snapshot, businessCode, planCode, siteLocks, roleFeatures, platform, siteType, scope } = params;
|
|
283
|
+
const { snapshot, businessCode, planCode, siteLocks, roleFeatures, platform, siteType, scope, availableServices } = params;
|
|
377
284
|
const bucket = platform === "web" ? "web" : "mobile";
|
|
378
285
|
const featureByCode = /* @__PURE__ */ __name((code) => scope ? snapshot.features?.[snapshotFeatureKey(code, scope)] : findFeatureByCode(snapshot, code), "featureByCode");
|
|
379
|
-
const catalog = buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, siteType, scope);
|
|
286
|
+
const catalog = buildSiteCatalog(snapshot, businessCode, planCode, siteLocks, bucket, siteType, scope, availableServices);
|
|
380
287
|
const catalogMap = new Map(catalog.map((f) => [
|
|
381
288
|
f.code,
|
|
382
289
|
f
|
|
@@ -426,7 +333,8 @@ function resolveUserFeatures(params) {
|
|
|
426
333
|
const lockedPermissions = grantedPerms.map((c) => permByCode.get(c)).filter((p) => !!p?.locked).map((p) => ({
|
|
427
334
|
code: p.code,
|
|
428
335
|
reason: p.lockReason ?? null,
|
|
429
|
-
unlockPlans: p.unlockPlans ?? []
|
|
336
|
+
unlockPlans: p.unlockPlans ?? [],
|
|
337
|
+
missingServices: p.missingServices ?? []
|
|
430
338
|
}));
|
|
431
339
|
const upsell = catalogEntry.locked && catalogEntry.lockReason === "PLAN" ? (catalogEntry.unlockPlans ?? []).map((plan) => ({
|
|
432
340
|
plan,
|
|
@@ -442,6 +350,7 @@ function resolveUserFeatures(params) {
|
|
|
442
350
|
locked: catalogEntry.locked ?? false,
|
|
443
351
|
lockReason: catalogEntry.lockReason ?? null,
|
|
444
352
|
unlockPlans: catalogEntry.unlockPlans ?? [],
|
|
353
|
+
missingServices: catalogEntry.missingServices ?? [],
|
|
445
354
|
lockedPermissions,
|
|
446
355
|
upsell,
|
|
447
356
|
route,
|
|
@@ -472,8 +381,120 @@ function pickRouteForPlatform(entry, platform) {
|
|
|
472
381
|
};
|
|
473
382
|
}
|
|
474
383
|
__name(pickRouteForPlatform, "pickRouteForPlatform");
|
|
384
|
+
|
|
385
|
+
// src/catalog-resolver/site-matrix.builder.ts
|
|
386
|
+
function buildSiteMatrix(snapshot, businessCode, planCode, siteLocks, siteType) {
|
|
387
|
+
return buildMatrix(snapshot, businessCode, planCode, siteLocks, false, siteType);
|
|
388
|
+
}
|
|
389
|
+
__name(buildSiteMatrix, "buildSiteMatrix");
|
|
390
|
+
function buildPlanMatrix(snapshot, businessCode, planCode, siteLocks) {
|
|
391
|
+
return buildMatrix(snapshot, businessCode, planCode, siteLocks, true);
|
|
392
|
+
}
|
|
393
|
+
__name(buildPlanMatrix, "buildPlanMatrix");
|
|
394
|
+
function buildMatrix(snapshot, businessCode, planCode, siteLocks, allScopes, siteType) {
|
|
395
|
+
const business = businessCode ? snapshot.businesses?.[businessCode] : void 0;
|
|
396
|
+
const plans = business?.plans ?? {};
|
|
397
|
+
const plan = planCode ? plans[planCode] : void 0;
|
|
398
|
+
const planMeta = {
|
|
399
|
+
code: planCode ?? "",
|
|
400
|
+
name: plan?.name ?? planCode ?? ""
|
|
401
|
+
};
|
|
402
|
+
const locks = siteLocks ?? {};
|
|
403
|
+
if (!business || !plan) return {
|
|
404
|
+
plan: planMeta,
|
|
405
|
+
apps: [],
|
|
406
|
+
locks
|
|
407
|
+
};
|
|
408
|
+
const apps = [];
|
|
409
|
+
for (const app of business.apps) {
|
|
410
|
+
let unlockedCount = 0;
|
|
411
|
+
let totalCount = 0;
|
|
412
|
+
const features = [];
|
|
413
|
+
for (const ref of app.features) {
|
|
414
|
+
if (!allScopes && ref.scope !== "SITE") continue;
|
|
415
|
+
const code = ref.code;
|
|
416
|
+
const feature = snapshot.features?.[snapshotFeatureKey(code, ref.scope)];
|
|
417
|
+
if (!feature) continue;
|
|
418
|
+
if (siteType !== void 0 && !featureAppliesAtNode(feature.applicableSiteTypes, siteType)) continue;
|
|
419
|
+
const platforms = PLATFORMS.filter((p) => !!feature.microfrontends?.[p]);
|
|
420
|
+
if (platforms.length === 0) continue;
|
|
421
|
+
const membership = plan.unlockedPermissions?.[code];
|
|
422
|
+
const featureInPlan = isPlanMember(membership);
|
|
423
|
+
const siteEntry = siteLocks?.[code];
|
|
424
|
+
const permissions = (feature.permissions ?? []).filter((p) => p.isGlobal || p.businesses.includes(businessCode ?? "")).map((p) => {
|
|
425
|
+
const cell = /* @__PURE__ */ __name((plat) => {
|
|
426
|
+
if (!platforms.includes(plat)) return null;
|
|
427
|
+
const planCodes = membership?.[plat];
|
|
428
|
+
const inPlan = featureInPlan && planCodes !== void 0 && planCodes.includes(p.code);
|
|
429
|
+
const selected = inPlan && !isSiteLockedOnPlatform(siteEntry, plat, p.code);
|
|
430
|
+
const availableIn = inPlan ? [] : plansUnlockingPerm(plans, code, p.code, plat, planCode);
|
|
431
|
+
totalCount += 1;
|
|
432
|
+
if (inPlan) unlockedCount += 1;
|
|
433
|
+
return {
|
|
434
|
+
inPlan,
|
|
435
|
+
selected,
|
|
436
|
+
availableIn
|
|
437
|
+
};
|
|
438
|
+
}, "cell");
|
|
439
|
+
return {
|
|
440
|
+
code: p.code,
|
|
441
|
+
label: p.label,
|
|
442
|
+
dependsOn: p.dependsOn ?? [],
|
|
443
|
+
web: cell("web"),
|
|
444
|
+
mobile: cell("mobile")
|
|
445
|
+
};
|
|
446
|
+
});
|
|
447
|
+
features.push({
|
|
448
|
+
code: feature.code,
|
|
449
|
+
name: feature.name,
|
|
450
|
+
icon: feature.lucideIcon ?? null,
|
|
451
|
+
scope: feature.scope,
|
|
452
|
+
applicableSiteTypes: feature.applicableSiteTypes,
|
|
453
|
+
platforms,
|
|
454
|
+
inPlan: featureInPlan,
|
|
455
|
+
availableIn: featureInPlan ? [] : plansIncludingFeature2(plans, code, planCode),
|
|
456
|
+
permissions
|
|
457
|
+
});
|
|
458
|
+
}
|
|
459
|
+
if (features.length === 0) continue;
|
|
460
|
+
apps.push({
|
|
461
|
+
code: app.code,
|
|
462
|
+
name: app.name,
|
|
463
|
+
icon: app.icon ?? null,
|
|
464
|
+
unlockedCount,
|
|
465
|
+
totalCount,
|
|
466
|
+
features
|
|
467
|
+
});
|
|
468
|
+
}
|
|
469
|
+
apps.sort((a, b) => a.name.localeCompare(b.name));
|
|
470
|
+
return {
|
|
471
|
+
plan: planMeta,
|
|
472
|
+
apps,
|
|
473
|
+
locks
|
|
474
|
+
};
|
|
475
|
+
}
|
|
476
|
+
__name(buildMatrix, "buildMatrix");
|
|
477
|
+
function plansUnlockingPerm(plans, featureCode, permCode, platform, excludeCode) {
|
|
478
|
+
const names = [];
|
|
479
|
+
for (const [code, p] of Object.entries(plans)) {
|
|
480
|
+
if (code === excludeCode) continue;
|
|
481
|
+
if ((p.unlockedPermissions?.[featureCode]?.[platform] ?? []).includes(permCode)) names.push(p.name);
|
|
482
|
+
}
|
|
483
|
+
return names;
|
|
484
|
+
}
|
|
485
|
+
__name(plansUnlockingPerm, "plansUnlockingPerm");
|
|
486
|
+
function plansIncludingFeature2(plans, featureCode, excludeCode) {
|
|
487
|
+
const names = [];
|
|
488
|
+
for (const [code, p] of Object.entries(plans)) {
|
|
489
|
+
if (code === excludeCode) continue;
|
|
490
|
+
if (isPlanMember(p.unlockedPermissions?.[featureCode])) names.push(p.name);
|
|
491
|
+
}
|
|
492
|
+
return names;
|
|
493
|
+
}
|
|
494
|
+
__name(plansIncludingFeature2, "plansIncludingFeature");
|
|
475
495
|
export {
|
|
476
496
|
PLATFORMS,
|
|
497
|
+
SERVICE_CODES,
|
|
477
498
|
SITE_TYPES,
|
|
478
499
|
SNAPSHOT_SCHEMA_VERSION,
|
|
479
500
|
buildDependsMap,
|