diff --git a/packages/data-center/src/datacenter.ts b/packages/data-center/src/datacenter.ts index 551fa009cf..e8876ac2d6 100644 --- a/packages/data-center/src/datacenter.ts +++ b/packages/data-center/src/datacenter.ts @@ -416,13 +416,14 @@ export class DataCenter { /** * accept invitation * @param {string} inviteCode + * @returns {Promise} permission */ async acceptInvitation(inviteCode: string, providerStr = 'affine') { const provider = this.providerMap.get(providerStr); if (provider) { return await provider.acceptInvitation(inviteCode); } - return []; + return null; } onMessage(cb: (message: Message) => void) { diff --git a/packages/data-center/src/provider/affine/affine.ts b/packages/data-center/src/provider/affine/affine.ts index 944d19c7fe..c8078c4cdc 100644 --- a/packages/data-center/src/provider/affine/affine.ts +++ b/packages/data-center/src/provider/affine/affine.ts @@ -102,10 +102,19 @@ export class AffineProvider extends BaseProvider { }); } - private _handlerAffineListMessage({ ws_details, metadata }: ChannelMessage) { + private async _handlerAffineListMessage({ + ws_details, + metadata, + }: ChannelMessage) { this._logger('receive server message'); - Object.entries(ws_details).forEach(async ([id, detail]) => { + const addedWorkspaces: WorkspaceUnit[] = []; + const removeWorkspaceList = this._workspaces.list().map(w => w.id); + for (const [id, detail] of Object.entries(ws_details)) { const { name, avatar } = metadata[id]; + const index = removeWorkspaceList.indexOf(id); + if (index !== -1) { + removeWorkspaceList.splice(index, 1); + } assert(name); const workspace = { name: name, @@ -122,15 +131,20 @@ export class AffineProvider extends BaseProvider { syncMode: 'core' as SyncMode, }; if (this._workspaces.get(id)) { + // update workspaces this._workspaces.update(id, workspace); } else { const workspaceUnit = await loadWorkspaceUnit( { id, ...workspace }, this._apis ); - this._workspaces.add(workspaceUnit); + addedWorkspaces.push(workspaceUnit); } - }); + } + // add workspaces + this._workspaces.add(addedWorkspaces); + // remove workspaces + this._workspaces.remove(removeWorkspaceList); } private _getWebsocketProvider(workspace: BlocksuiteWorkspace) { @@ -386,7 +400,7 @@ export class AffineProvider extends BaseProvider { return this._apis.getWorkspaceMembers({ id }); } - public override async acceptInvitation(invitingCode: string): Promise { - await this._apis.acceptInviting({ invitingCode }); + public override async acceptInvitation(invitingCode: string) { + return await this._apis.acceptInviting({ invitingCode }); } } diff --git a/packages/data-center/src/provider/affine/apis/workspace.ts b/packages/data-center/src/provider/affine/apis/workspace.ts index 83d065bbca..106dc72b04 100644 --- a/packages/data-center/src/provider/affine/apis/workspace.ts +++ b/packages/data-center/src/provider/affine/apis/workspace.ts @@ -197,13 +197,13 @@ export interface AcceptInvitingParams { export async function acceptInviting( params: AcceptInvitingParams -): Promise { - await bareClient - .post(`api/invitation/${params.invitingCode}`) - .catch(error => { - sendMessage(messageCode.acceptInvitingFailed); - throw new RequestError('accept inviting failed', error); - }); +): Promise { + try { + return bareClient.post(`api/invitation/${params.invitingCode}`).json(); + } catch (error) { + sendMessage(messageCode.acceptInvitingFailed); + throw new RequestError('accept inviting failed', error); + } } export async function uploadBlob(params: { blob: Blob }): Promise { diff --git a/packages/data-center/src/provider/base.ts b/packages/data-center/src/provider/base.ts index 0f0a23ead3..eb9a68d748 100644 --- a/packages/data-center/src/provider/base.ts +++ b/packages/data-center/src/provider/base.ts @@ -4,6 +4,7 @@ import { Logger, User } from '../types'; import type { WorkspaceUnitCollectionScope } from '../workspace-unit-collection'; import type { WorkspaceUnitCtorParams, WorkspaceUnit } from '../workspace-unit'; import { Member } from './affine/apis'; +import { Permission } from './affine/apis/workspace.js'; const defaultLogger = () => { return; @@ -233,8 +234,10 @@ export class BaseProvider { * @param {string} inviteCode * @returns */ - public async acceptInvitation(inviteCode: string): Promise { + public async acceptInvitation( + inviteCode: string + ): Promise { inviteCode; - return; + return null; } } diff --git a/packages/data-center/src/workspace-unit-collection.ts b/packages/data-center/src/workspace-unit-collection.ts index 7d55762560..b51f5d160f 100644 --- a/packages/data-center/src/workspace-unit-collection.ts +++ b/packages/data-center/src/workspace-unit-collection.ts @@ -8,7 +8,7 @@ export interface WorkspaceUnitCollectionScope { get: (workspaceId: string) => WorkspaceUnit | undefined; list: () => WorkspaceUnit[]; add: (workspace: WorkspaceUnit | WorkspaceUnit[]) => void; - remove: (workspaceId: string) => boolean; + remove: (workspaceId: string | string[]) => boolean; clear: () => void; update: ( workspaceId: string, @@ -18,7 +18,7 @@ export interface WorkspaceUnitCollectionScope { export interface WorkspaceUnitCollectionChangeEvent { added?: WorkspaceUnit[]; - deleted?: WorkspaceUnit; + deleted?: WorkspaceUnit[]; updated?: WorkspaceUnit; } @@ -62,16 +62,22 @@ export class WorkspaceUnitCollection { const workspaceUnits = Array.isArray(workspaceUnit) ? workspaceUnit : [workspaceUnit]; + let added = false; workspaceUnits.forEach(workspaceUnit => { if (this._workspaceUnitMap.has(workspaceUnit.id)) { // FIXME: multiple add same workspace return; } + added = true; this._workspaceUnitMap.set(workspaceUnit.id, workspaceUnit); scopedWorkspaceIds.add(workspaceUnit.id); }); + if (!added) { + return; + } + this._events.emit('change', [ { added: workspaceUnits, @@ -79,27 +85,39 @@ export class WorkspaceUnitCollection { ]); }; - const remove = (workspaceId: string) => { - if (!scopedWorkspaceIds.has(workspaceId)) { - return true; - } + const remove = (workspaceId: string | string[]) => { + const workspaceIds = Array.isArray(workspaceId) + ? workspaceId + : [workspaceId]; + const workspaceUnits: WorkspaceUnit[] = []; - const workspaceUnit = this._workspaceUnitMap.get(workspaceId); - if (workspaceUnit) { - const ret = this._workspaceUnitMap.delete(workspaceId); - // If deletion failed, return. - if (!ret) { - return ret; + workspaceIds.forEach(workspaceId => { + if (!scopedWorkspaceIds.has(workspaceId)) { + return; } + const workspaceUnit = this._workspaceUnitMap.get(workspaceId); + if (workspaceUnit) { + const ret = this._workspaceUnitMap.delete(workspaceId); + // If deletion failed, return. + if (!ret) { + return; + } - scopedWorkspaceIds.delete(workspaceId); + workspaceUnits.push(workspaceUnit); + scopedWorkspaceIds.delete(workspaceId); + } + }); - this._events.emit('change', [ - { - deleted: workspaceUnit, - } as WorkspaceUnitCollectionChangeEvent, - ]); + if (!workspaceUnits.length) { + return false; } + + this._events.emit('change', [ + { + deleted: workspaceUnits, + } as WorkspaceUnitCollectionChangeEvent, + ]); + return true; };