@7365admin1/core 3.70.0 → 3.71.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -0
- package/dist/index.d.ts +3 -1
- package/dist/index.js +29 -0
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +96 -67
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
- package/test/e2e/member-list-site-scope.e2e.test.mjs +111 -0
- package/test/member-list-site-scope.test.mjs +30 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
# @iservice365/core
|
|
2
2
|
|
|
3
|
+
## 3.71.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- b9aff41: `GET /api/members?org=` lists only the sites a caller is pinned to when the caller holds no organisation-wide membership or organisation-level role there; a `siteId` outside those sites is refused. Organisation-wide members, owners/invitees and Seven365 staff are unchanged; a resident-only caller lists no staff.
|
|
8
|
+
|
|
3
9
|
## 3.70.0
|
|
4
10
|
|
|
5
11
|
### Minor Changes
|
package/dist/index.d.ts
CHANGED
|
@@ -440,13 +440,15 @@ declare function useMemberRepo(): {
|
|
|
440
440
|
getByUserIdType: (user: string | ObjectId, type: string) => Promise<TMember>;
|
|
441
441
|
getByRoleId: (role: string | ObjectId) => Promise<any>;
|
|
442
442
|
getAssignedByRoleId: (role: string | ObjectId) => Promise<TMember[]>;
|
|
443
|
-
getAll: ({ search, page, limit, user, org, siteId, type, status, }: {
|
|
443
|
+
getAll: ({ search, page, limit, user, org, siteId, siteIds, type, status, }: {
|
|
444
444
|
search?: string | undefined;
|
|
445
445
|
page?: number | undefined;
|
|
446
446
|
limit?: number | undefined;
|
|
447
447
|
user?: string | ObjectId | undefined;
|
|
448
448
|
org?: string | ObjectId | undefined;
|
|
449
449
|
siteId?: string | ObjectId | undefined;
|
|
450
|
+
/** Restrict to these sites (the caller's pinned sites); `[]` lists nothing. */
|
|
451
|
+
siteIds?: string[] | undefined;
|
|
450
452
|
type: string;
|
|
451
453
|
status: string;
|
|
452
454
|
}) => Promise<{
|
package/dist/index.js
CHANGED
|
@@ -4398,6 +4398,7 @@ function useMemberRepo() {
|
|
|
4398
4398
|
user = "",
|
|
4399
4399
|
org = "",
|
|
4400
4400
|
siteId = "",
|
|
4401
|
+
siteIds,
|
|
4401
4402
|
type = "",
|
|
4402
4403
|
status = ""
|
|
4403
4404
|
}) {
|
|
@@ -4431,6 +4432,12 @@ function useMemberRepo() {
|
|
|
4431
4432
|
throw new import_node_server_utils14.BadRequestError("Invalid site ID format.");
|
|
4432
4433
|
}
|
|
4433
4434
|
}
|
|
4435
|
+
if (siteIds) {
|
|
4436
|
+
query2.siteId = {
|
|
4437
|
+
$in: siteIds.filter((id) => import_mongodb13.ObjectId.isValid(id)).map((id) => new import_mongodb13.ObjectId(id))
|
|
4438
|
+
};
|
|
4439
|
+
cacheOptions.siteIds = [...siteIds].sort().join(",") || "no-site";
|
|
4440
|
+
}
|
|
4434
4441
|
if (user) {
|
|
4435
4442
|
try {
|
|
4436
4443
|
query2.user = new import_mongodb13.ObjectId(user);
|
|
@@ -10518,6 +10525,15 @@ function pickLookupMembership(rows, type, site = "", org = "") {
|
|
|
10518
10525
|
return inOrg;
|
|
10519
10526
|
return list.find((m) => m.type === type) ?? null;
|
|
10520
10527
|
}
|
|
10528
|
+
function memberListSiteScope(memberships, org) {
|
|
10529
|
+
const inOrg = (memberships ?? []).filter((m) => idOf2(m.org) === idOf2(org));
|
|
10530
|
+
const here = inOrg.filter((m) => m.type !== "resident");
|
|
10531
|
+
if (!inOrg.length)
|
|
10532
|
+
return null;
|
|
10533
|
+
if (here.some((m) => !idOf2(m.siteId) || m.orgLevelRole))
|
|
10534
|
+
return null;
|
|
10535
|
+
return [...new Set(here.map((m) => idOf2(m.siteId)))];
|
|
10536
|
+
}
|
|
10521
10537
|
|
|
10522
10538
|
// src/services/module-gate.service.ts
|
|
10523
10539
|
var idOf3 = (v) => v == null ? "" : String(v?._id ?? v).toLowerCase();
|
|
@@ -23704,6 +23720,18 @@ function useMemberController() {
|
|
|
23704
23720
|
await requireConsolePermission(req, "members", "view-members");
|
|
23705
23721
|
} else if (org) {
|
|
23706
23722
|
await requireOrgAccess(req, org);
|
|
23723
|
+
}
|
|
23724
|
+
let siteIds;
|
|
23725
|
+
if (org && type !== "admin") {
|
|
23726
|
+
const actor = await resolveInviteActor(callerId(req));
|
|
23727
|
+
const scope = staffMayBypass(actor) ? null : memberListSiteScope(actor.memberships, org);
|
|
23728
|
+
if (scope) {
|
|
23729
|
+
if (siteId && !scope.includes(siteId.toLowerCase())) {
|
|
23730
|
+
throw new import_node_server_utils65.UnauthorizedError("Not authorized.");
|
|
23731
|
+
}
|
|
23732
|
+
if (!siteId)
|
|
23733
|
+
siteIds = scope;
|
|
23734
|
+
}
|
|
23707
23735
|
} else if (user && user !== callerId(req)) {
|
|
23708
23736
|
await requireConsolePermission(req, "users", "see-all-users");
|
|
23709
23737
|
}
|
|
@@ -23714,6 +23742,7 @@ function useMemberController() {
|
|
|
23714
23742
|
user,
|
|
23715
23743
|
org,
|
|
23716
23744
|
siteId,
|
|
23745
|
+
siteIds,
|
|
23717
23746
|
type,
|
|
23718
23747
|
status
|
|
23719
23748
|
});
|