mirror of
https://github.com/labring/FastGPT.git
synced 2025-07-27 16:33:49 +00:00

* feat: org CRUD (#3380) * feat: add org schema * feat: org manage UI * feat: OrgInfoModal * feat: org tree view * feat: org management * fix: init root org * feat: org permission for app * feat: org support for dataset * fix: disable org role control * styles: opt type signatures * fix: remove unused permission * feat: delete org collaborator * perf: Team org ui (#3499) * perf: org ui * perf: org ui * feat: org auth for app & dataset (#3498) * feat: auth org resource permission * feat: org auth support for app & dataset * perf: org permission check (#3500) * i18n (#3501) * name * i18n * feat: support dataset changeOwner (#3483) * feat: support dataset changeOwner * chore: update dataset change owner api * feat: permission manage UI for org (#3503) * perf: password check;perf: image upload check;perf: sso login check (#3509) * perf: password check * perf: image upload check * perf: sso login check * force show update notification modal & fix login page text (#3512) * fix login page English text * update notification modal * perf: notify account (#3515) * perf(plugin): improve searXNG empty result handling and documentation (#3507) * perf(plugin): improve searXNG empty result handling and documentation * 修改了文档和代码部分无搜索的结果的反馈 * refactor: org pathId (#3516) * optimize payment process (#3517) * feat: support wecom sso (#3518) * feat: support wecom sso * chore: remove unused wecom js-sdk dependency * fix qrcode script (#3520) * fix qrcode script * i18n * perf: full text collection and search code;perf: rename function (#3519) * perf: full text collection and search code * perf: rename function * perf: notify modal * remove invalid code * perf: sso login * perf: pay process * 4.8.18 test (#3524) * perf: remove local token * perf: index * perf: file encoding;perf: leave team code;@c121914yu perf: full text search code (#3528) * perf: text encoding * perf: leave team code * perf: full text search code * fix: http status * perf: embedding search and vector avatar * perf: async read file (#3531) * refactor: team permission manager (#3535) * perf: classify org, group and member * refactor: team per manager * fix: missing functions * 4.8.18 test (#3543) * perf: login check * doc * perf: llm model config * perf: team clb config * fix: MemberModal UI (#3553) * fix: adapt MemberModal title and icon * fix: adapt member modal * fix: search input placeholder * fix: add button text * perf: org permission (#3556) * docs:用户答疑的官方文档补充 (#3540) * docs:用户答疑的官方文档补充 * 问题回答的内容修补 * share link random avatar (#3541) * share link random avatar * fix * delete unused code * share page avatar (#3558) * feat: init 4818 * share page avatar * feat: tmp upgrade code (#3559) * feat: tmp upgrade code * fulltext search test * update action * full text tmp code (#3561) * full text tmp code * fix: init * fix: init * remove tmp code * remove tmp code * 4818-alpha * 4.8.18 test (#3562) * full text tmp code * fix: init * upgrade code * account log * account log * perf: dockerfile * upgrade code * chore: update docs app template submission (#3564) --------- Co-authored-by: a.e. <49438478+I-Info@users.noreply.github.com> Co-authored-by: Finley Ge <32237950+FinleyGe@users.noreply.github.com> Co-authored-by: heheer <heheer@sealos.io> Co-authored-by: Jiangween <145003935+Jiangween@users.noreply.github.com>
203 lines
5.0 KiB
TypeScript
203 lines
5.0 KiB
TypeScript
import { mongoSessionRun } from '../../common/mongo/sessionRun';
|
|
import { MongoResourcePermission } from './schema';
|
|
import type { ClientSession, Model } from 'mongoose';
|
|
import type { PerResourceTypeEnum } from '@fastgpt/global/support/permission/constant';
|
|
import type { PermissionValueType } from '@fastgpt/global/support/permission/type';
|
|
import { getResourceClbsAndGroups } from './controller';
|
|
import type { RequireOnlyOne } from '@fastgpt/global/common/type/utils';
|
|
import type { ParentIdType } from '@fastgpt/global/common/parentFolder/type';
|
|
|
|
export type SyncChildrenPermissionResourceType = {
|
|
_id: string;
|
|
type: string;
|
|
teamId: string;
|
|
parentId?: ParentIdType;
|
|
};
|
|
export type UpdateCollaboratorItem = {
|
|
permission: PermissionValueType;
|
|
} & RequireOnlyOne<{
|
|
tmbId: string;
|
|
groupId: string;
|
|
orgId: string;
|
|
}>;
|
|
|
|
// sync the permission to all children folders.
|
|
export async function syncChildrenPermission({
|
|
resource,
|
|
folderTypeList,
|
|
resourceType,
|
|
resourceModel,
|
|
session,
|
|
|
|
collaborators
|
|
}: {
|
|
resource: SyncChildrenPermissionResourceType;
|
|
|
|
// when the resource is a folder
|
|
folderTypeList: string[];
|
|
|
|
resourceModel: typeof Model;
|
|
resourceType: PerResourceTypeEnum;
|
|
|
|
// should be provided when inheritPermission is true
|
|
session: ClientSession;
|
|
|
|
collaborators?: UpdateCollaboratorItem[];
|
|
}) {
|
|
// only folder has permission
|
|
const isFolder = folderTypeList.includes(resource.type);
|
|
|
|
if (!isFolder) return;
|
|
|
|
// get all folders and the resource permission of the app
|
|
const allFolders = await resourceModel
|
|
.find(
|
|
{
|
|
teamId: resource.teamId,
|
|
type: { $in: folderTypeList },
|
|
inheritPermission: true
|
|
},
|
|
'_id parentId'
|
|
)
|
|
.lean<SyncChildrenPermissionResourceType[]>()
|
|
.session(session);
|
|
|
|
// bfs to get all children
|
|
const queue = [String(resource._id)];
|
|
const children: string[] = [];
|
|
while (queue.length) {
|
|
const parentId = queue.shift();
|
|
const folderChildren = allFolders.filter(
|
|
(folder) => String(folder.parentId) === String(parentId)
|
|
);
|
|
children.push(...folderChildren.map((folder) => folder._id));
|
|
queue.push(...folderChildren.map((folder) => folder._id));
|
|
}
|
|
if (!children.length) return;
|
|
|
|
// sync the resource permission
|
|
if (collaborators) {
|
|
// Update the collaborators of all children
|
|
for await (const childId of children) {
|
|
await syncCollaborators({
|
|
resourceType,
|
|
session,
|
|
collaborators,
|
|
teamId: resource.teamId,
|
|
resourceId: childId
|
|
});
|
|
}
|
|
}
|
|
}
|
|
|
|
/* Resume the inherit permission of the resource.
|
|
1. Folder: Sync parent's defaultPermission and clbs, and sync its children.
|
|
2. Resource: Sync parent's defaultPermission, and delete all its clbs.
|
|
*/
|
|
export async function resumeInheritPermission({
|
|
resource,
|
|
folderTypeList,
|
|
resourceType,
|
|
resourceModel,
|
|
session
|
|
}: {
|
|
resource: SyncChildrenPermissionResourceType;
|
|
folderTypeList: string[];
|
|
resourceType: PerResourceTypeEnum;
|
|
resourceModel: typeof Model;
|
|
session?: ClientSession;
|
|
}) {
|
|
const isFolder = folderTypeList.includes(resource.type);
|
|
|
|
const fn = async (session: ClientSession) => {
|
|
// update the resource permission
|
|
await resourceModel.updateOne(
|
|
{
|
|
_id: resource._id
|
|
},
|
|
{
|
|
inheritPermission: true
|
|
},
|
|
{ session }
|
|
);
|
|
|
|
// Folder resource, need to sync children
|
|
if (isFolder) {
|
|
const parentClbsAndGroups = await getResourceClbsAndGroups({
|
|
resourceId: resource.parentId,
|
|
teamId: resource.teamId,
|
|
resourceType,
|
|
session
|
|
});
|
|
|
|
// sync self
|
|
await syncCollaborators({
|
|
resourceType,
|
|
collaborators: parentClbsAndGroups,
|
|
teamId: resource.teamId,
|
|
resourceId: resource._id,
|
|
session
|
|
});
|
|
// sync children
|
|
await syncChildrenPermission({
|
|
resource: {
|
|
...resource
|
|
},
|
|
resourceModel,
|
|
folderTypeList,
|
|
resourceType,
|
|
session,
|
|
collaborators: parentClbsAndGroups
|
|
});
|
|
} else {
|
|
// Not folder, delete all clb
|
|
await MongoResourcePermission.deleteMany({ resourceId: resource._id }, { session });
|
|
}
|
|
};
|
|
|
|
if (session) {
|
|
return fn(session);
|
|
} else {
|
|
return mongoSessionRun(fn);
|
|
}
|
|
}
|
|
|
|
/*
|
|
Delete all the collaborators and then insert the new collaborators.
|
|
*/
|
|
export async function syncCollaborators({
|
|
resourceType,
|
|
teamId,
|
|
resourceId,
|
|
collaborators,
|
|
session
|
|
}: {
|
|
resourceType: PerResourceTypeEnum;
|
|
teamId: string;
|
|
resourceId: string;
|
|
collaborators: UpdateCollaboratorItem[];
|
|
session: ClientSession;
|
|
}) {
|
|
await MongoResourcePermission.deleteMany(
|
|
{
|
|
resourceType,
|
|
teamId,
|
|
resourceId
|
|
},
|
|
{ session }
|
|
);
|
|
await MongoResourcePermission.insertMany(
|
|
collaborators.map((item) => ({
|
|
teamId: teamId,
|
|
resourceId,
|
|
resourceType: resourceType,
|
|
tmbId: item.tmbId,
|
|
groupId: item.groupId,
|
|
permission: item.permission
|
|
})),
|
|
{
|
|
session
|
|
}
|
|
);
|
|
}
|