@univerjs-pro/collaboration-client 0.1.9
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/README.md +18 -0
- package/lib/cjs/index.js +4 -0
- package/lib/es/index.js +3626 -0
- package/lib/index.css +1 -0
- package/lib/types/controllers/collab-cursor/__tests__/doc-collab-cursor.controller.spec.d.ts +1 -0
- package/lib/types/controllers/collab-cursor/__tests__/serialize-text-ranges.spec.d.ts +1 -0
- package/lib/types/controllers/collab-cursor/__tests__/sheet-collab-cursor.controller.spec.d.ts +1 -0
- package/lib/types/controllers/collab-cursor/collab-cursor.controller.d.ts +24 -0
- package/lib/types/controllers/collab-cursor/doc-collab-cursor-entity.d.ts +40 -0
- package/lib/types/controllers/collab-cursor/doc-collab-cursor-render.controller.d.ts +22 -0
- package/lib/types/controllers/collab-cursor/serialize-text-ranges.d.ts +4 -0
- package/lib/types/controllers/collab-cursor/sheet-collab-cursor-entity.d.ts +41 -0
- package/lib/types/controllers/collab-cursor/sheet-collab-cursor-render.controller.d.ts +23 -0
- package/lib/types/controllers/collab-status/collab-status.controller.d.ts +18 -0
- package/lib/types/controllers/collaboration/__tests__/collaboration.controller.spec.d.ts +5 -0
- package/lib/types/controllers/collaboration/__tests__/mock-text-selection-render-manager.service.d.ts +10 -0
- package/lib/types/controllers/collaboration/__tests__/mocks.d.ts +55 -0
- package/lib/types/controllers/collaboration/collaboration-state.d.ts +266 -0
- package/lib/types/controllers/collaboration/collaboration.controller.d.ts +110 -0
- package/lib/types/controllers/collaboration/utils/changeset-utils.d.ts +17 -0
- package/lib/types/controllers/data-loader/__tests__/data-loader.controller.spec.d.ts +1 -0
- package/lib/types/controllers/data-loader/data-loader.controller.d.ts +23 -0
- package/lib/types/controllers/file-name/file-name.controller.d.ts +13 -0
- package/lib/types/index.d.ts +11 -0
- package/lib/types/locale/en-US.d.ts +4 -0
- package/lib/types/locale/index.d.ts +2 -0
- package/lib/types/locale/zh-CN.d.ts +29 -0
- package/lib/types/models/cursor.d.ts +29 -0
- package/lib/types/plugin.d.ts +20 -0
- package/lib/types/services/auth-server/auth-server.service.d.ts +15 -0
- package/lib/types/services/collaboration-session/collaboration-session.service.d.ts +107 -0
- package/lib/types/services/color-assign/color-assign.service.d.ts +11 -0
- package/lib/types/services/ime-cache-transform/doc-transform-ime-cache.service.d.ts +12 -0
- package/lib/types/services/local-cache/local-cache.service.d.ts +43 -0
- package/lib/types/services/member/member.service.d.ts +33 -0
- package/lib/types/services/range-selection/sheet-transform-selections.service.d.ts +9 -0
- package/lib/types/services/single-active-unit/single-active-unit.service.d.ts +40 -0
- package/lib/types/services/snapshot-server/snapshot-server.service.d.ts +22 -0
- package/lib/types/services/socket/collaboration-socket.service.d.ts +36 -0
- package/lib/types/services/socket/serialize.d.ts +4 -0
- package/lib/types/services/sync-editing-collab-cursor/doc-sync-editing-collab-cursor.service.d.ts +14 -0
- package/lib/types/services/text-selection/doc-transform-selections.service.d.ts +9 -0
- package/lib/types/services/undoredo/collaborative-undoredo.service.d.ts +20 -0
- package/lib/types/services/url/url.service.d.ts +13 -0
- package/lib/types/services/url/web-url.service.d.ts +11 -0
- package/lib/types/views/components/CollabStatus.d.ts +14 -0
- package/lib/types/views/components/CollabStatus.stories.d.ts +9 -0
- package/lib/types/views/shapes/doc-collab-cursor.d.ts +27 -0
- package/lib/types/views/shapes/sheet-collab-cursor.shape.d.ts +27 -0
- package/lib/types/views/shapes/text-bubble.shape.d.ts +20 -0
- package/lib/umd/index.js +4 -0
- package/package.json +102 -0
package/README.md
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
# @univerjs-pro/collaboration-client
|
2
|
+
|
3
|
+
## Introduction
|
4
|
+
|
5
|
+
Univer collaboration plugin on the client side. It brings online collaboration to your Univer application.
|
6
|
+
|
7
|
+
## Usage
|
8
|
+
|
9
|
+
### Installation
|
10
|
+
|
11
|
+
```shell
|
12
|
+
npm i @univerjs-pro/collaboration-client
|
13
|
+
```
|
14
|
+
|
15
|
+
### API
|
16
|
+
|
17
|
+
Check [Univer](https://github.com/dream-num/univer/)
|
18
|
+
|
package/lib/cjs/index.js
ADDED
@@ -0,0 +1,4 @@
|
|
1
|
+
"use strict";var wt=Object.defineProperty;var Ut=(n,t,e)=>t in n?wt(n,t,{enumerable:!0,configurable:!0,writable:!0,value:e}):n[t]=e;var d=(n,t,e)=>(Ut(n,typeof t!="symbol"?t+"":t,e),e);Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const a=require("@univerjs/core"),le=require("@univerjs/design"),A=require("@univerjs/ui"),_=require("@univerjs-pro/collaboration"),h=require("@wendellhu/redi"),v=require("rxjs"),T=require("rxjs/operators"),N=require("@univerjs/docs"),k=require("@univerjs/network"),p=require("@univerjs/sheets"),Ke=require("@univerjs/engine-formula"),He=require("lodash/debounce"),R=require("@univerjs/engine-render"),ae=require("@univerjs/sheets-ui"),rt=require("@wendellhu/redi/react-bindings"),w=require("react"),Lt=require("clsx"),Nt=require("@univerjs/rpc");var $=(n=>(n[n.UNIVER_UNKNOWN=0]="UNIVER_UNKNOWN",n[n.UNIVER_DOC=1]="UNIVER_DOC",n[n.UNIVER_SHEET=2]="UNIVER_SHEET",n[n.UNIVER_SLIDE=3]="UNIVER_SLIDE",n[n.UNRECOGNIZED=-1]="UNRECOGNIZED",n))($||{}),b=(n=>(n[n.UNKNOWN_CMD=0]="UNKNOWN_CMD",n[n.HELLO=1]="HELLO",n[n.JOIN=2]="JOIN",n[n.LEAVE=3]="LEAVE",n[n.INGEST=4]="INGEST",n[n.HEARTBEAT=5]="HEARTBEAT",n[n.RECV=6]="RECV",n[n.UNRECOGNIZED=-1]="UNRECOGNIZED",n))(b||{}),Be=(n=>(n[n.UNKNOWN_CODE=0]="UNKNOWN_CODE",n[n.OK=1]="OK",n[n.FAIL=2]="FAIL",n[n.UNRECOGNIZED=-1]="UNRECOGNIZED",n))(Be||{}),At=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},kt=(n,t)=>(e,s)=>t(e,s,n);let G=class extends a.Disposable{constructor(t){super();d(this,"_roomMembers",new Map);d(this,"_currentUser",null);this._univerInstanceService=t,this.disposeWithMe(a.toDisposable(v.merge(this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_SHEET).pipe(T.map(e=>e.getUnitId())),this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_DOC).pipe(T.map(e=>e.getUnitId())),this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_SLIDE).pipe(T.map(e=>e.getUnitId()))).subscribe(e=>this._removeRoom(e))))}setCurrentUser(t){this._currentUser=t}getCurrentUser(){return this._currentUser}updateMember(t,e){let s=this._roomMembers.get(t);s||(s=new $t,this._roomMembers.set(t,s)),s.updateMember(e)}removeMember(t,e){const s=this._roomMembers.get(t);s&&s.removeMember(e)}getRoom(t){return this._roomMembers.get(t)}getMember(t,e){const s=this._roomMembers.get(t);if(s)return s.getMember(e)}_removeRoom(t){const e=this._roomMembers.get(t);e&&(e.dispose(),this._roomMembers.delete(t))}dispose(){this._roomMembers.forEach(t=>t.dispose()),this._roomMembers.clear()}};G=At([kt(0,a.IUniverInstanceService)],G);class $t extends a.Disposable{constructor(){super(...arguments);d(this,"_members",new Map)}dispose(){this._members.clear()}updateMember(e){this._members.set(e.memberID,e)}removeMember(e){this._members.delete(e)}getMember(e){return this._members.get(e)}}function ot(n){var s,i,r;const t=n.data,e=JSON.parse(t);switch(e.cmd){case b.HEARTBEAT:case b.HELLO:{const o=e.infoRsp;return{...e,data:o,cmd:e.cmd}}case b.JOIN:{const o=e.joinRsp;return{...e,data:o,cmd:e.cmd}}case b.RECV:{const o=e.collaMsg;switch(o.eventID){case _.CollaborationEvent.CHANGESET_ACK:return{...e,data:{...o,data:(s=o.csAckEvent)==null?void 0:s.cs},cmd:e.cmd};case _.CollaborationEvent.NEW_CHANGESETS:return{...e,data:{...o,data:(i=o.newCsEvent)==null?void 0:i.cs},cmd:e.cmd};case _.CollaborationEvent.CHANGESET_REJ:return{...e,data:{...o,data:(r=o.csRejEvent)==null?void 0:r.cs},cmd:e.cmd};case _.CollaborationEvent.UPDATE_CURSOR:return{...e,data:{...o,data:o.updateCursorEvent},cmd:e.cmd};case _.CollaborationEvent.USERS_ENTER:return{...e,data:{...o,data:o.joinEvent},cmd:e.cmd};case _.CollaborationEvent.USERS_LEAVE:return{...e,data:{...o,data:o.leaveEvent},cmd:e.cmd};case _.CollaborationEvent.LIVESHARE_NEW_HOST:return{...e,data:{...o,data:o.liveShareNewHost},cmd:e.cmd};case _.CollaborationEvent.LIVESHARE_FETCH_OPERATIONS:case _.CollaborationEvent.LIVESHARE_OPERATION:return{...e,data:{...o,data:o.liveShareOperation},cmd:e.cmd};case _.CollaborationEvent.LIVESHARE_TERMINATE:return{...e,data:{...o,data:o.liveShareNewHost},cmd:e.cmd};case _.CollaborationEvent.MSG_FOR_ERROR:return{...e,data:o,cmd:e.cmd};default:return e}}default:return e}}function at(n){switch(n.cmd){case b.HEARTBEAT:case b.HELLO:return JSON.stringify({cmd:n.cmd,routeKey:n.routeKey});case b.INGEST:{let t;switch(n.data.eventID){case _.CollaborationEvent.UPDATE_CURSOR:{t={eventID:_.CollaborationEvent.UPDATE_CURSOR,updateCursorEvent:n.data.data};break}case _.CollaborationEvent.USERS_LEAVE:{t={eventID:_.CollaborationEvent.USERS_LEAVE,leaveEvent:n.data.data};break}case _.CollaborationEvent.USERS_ENTER:{t={eventID:_.CollaborationEvent.USERS_ENTER,joinEvent:n.data.data};break}case _.CollaborationEvent.LIVESHARE_NEW_HOST:{t={eventID:_.CollaborationEvent.LIVESHARE_NEW_HOST,liveShareNewHost:n.data.data};break}case _.CollaborationEvent.LIVESHARE_OPERATION:{t={eventID:_.CollaborationEvent.LIVESHARE_OPERATION,liveShareOperation:n.data.data};break}case _.CollaborationEvent.LIVESHARE_TERMINATE:{t={eventID:_.CollaborationEvent.LIVESHARE_TERMINATE,liveShareTerminate:n.data.data};break}case _.CollaborationEvent.LIVESHARE_REQUEST_HOST:{t={eventID:_.CollaborationEvent.LIVESHARE_REQUEST_HOST,liveShareRequestHost:n.data.data};break}case _.CollaborationEvent.LIVESHARE_FETCH_OPERATIONS:{t={eventID:_.CollaborationEvent.LIVESHARE_FETCH_OPERATIONS};break}default:t={eventID:n.data.eventID}}return JSON.stringify({cmd:n.cmd,routeKey:n.routeKey,collaMsg:t})}case b.JOIN:return JSON.stringify({cmd:n.cmd,routeKey:n.routeKey,joinReq:n.data});case b.LEAVE:return JSON.stringify({cmd:n.cmd,routeKey:n.routeKey,leaveReq:n.data});default:throw new Error("[serializeCombRequest]: should not fall into default branch!")}}var jt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},te=(n,t)=>(e,s)=>t(e,s,n);const Ve=h.createIdentifier("univer-pro.collaboration-client-socket-service"),ct="COLLAB_SUBMIT_CHANGESET_URL",Pt="/universer-api/comb";function xt(n,t,e){return`${n}/${t}/unit/${e}/new_changes`}exports.CollaborationSocketService=class{constructor(t,e,s,i,r){this._http=t,this._ws=e,this._configService=s,this._logService=i,this._snapshotServerService=r}createSocket(t){const e=this._ws.createSocket(t);if(!e)throw new Error("[CollaborationSocketService]: failed to create socket!");const s=new a.DisposableCollection,i=new v.Subject;s.add(a.toDisposable(e.close$.subscribe(u=>i.next(u)))),s.add(a.toDisposable(()=>i.complete()));const r=new v.Subject;s.add(a.toDisposable(e.error$.subscribe(u=>r.next(u)))),s.add(a.toDisposable(()=>r.complete()));const o=new v.Subject;s.add(a.toDisposable(e.message$.subscribe(u=>{const g=ot(u);o.next(g)}))),s.add(a.toDisposable(()=>o.complete()));const c=()=>{r.next(new Event("connection error")),i.next(new CloseEvent("connection error")),l.close()},l={memberID:"",close$:i.asObservable(),error$:r.asObservable(),open$:e.open$,message$:o.asObservable(),send:u=>{if(u.cmd===b.INGEST){if(u.data.eventID===_.CollaborationEvent.SUBMIT_CHANGESET){this._submitChangeset(l,u.data).catch(g=>{this._logService.error(g),c()});return}if(u.data.eventID===_.CollaborationEvent.FETCH_MISSING){const g=u.data;this._fetchMissChangesets(g).then(S=>{o.next({cmd:b.RECV,code:Be.OK,routeKey:g.data.unitID,routeType:"",data:{eventID:_.CollaborationEvent.PSEUDO_FETCH_MISSING_RESULT,data:{changesets:S}}})}).catch(S=>{this._logService.error(S),c()});return}}e.send(at(u))},close:()=>{e.close(),s.dispose()}};return l}async _submitChangeset(t,e){var l;const{unitType:s,unitID:i,changeset:r}=e.data,o={unitID:i,memberID:t.memberID,type:s,changeset:_.parseChangesetToProtocol(r)},c=xt((l=this._configService.getConfig(ct))!=null?l:Pt,s,i);try{await this._http.post(c,{body:o})}catch(u){throw this._logService.error("[CollaborationSession]","submit changeset error!"),u}}async _fetchMissChangesets(t){const{unitID:e,from:s,to:i,unitType:r}=t.data;return(await this._snapshotServerService.fetchMissingChangesets({metadata:void 0},{unitID:e,type:r,from:s,to:i})).changesets}};exports.CollaborationSocketService=jt([te(0,h.Inject(k.HTTPService)),te(1,h.Inject(k.WebSocketService)),te(2,a.IConfigService),te(3,a.ILogService),te(4,a.ISnapshotServerService)],exports.CollaborationSocketService);var lt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},U=(n,t)=>(e,s)=>t(e,s,n),W=(n=>(n[n.IDLE=0]="IDLE",n[n.JOINING=1]="JOINING",n[n.OFFLINE=2]="OFFLINE",n[n.ONLINE=3]="ONLINE",n))(W||{});const ht="COLLAB_WEB_SOCKET_URL",Ht="ws://127.0.0.1:8000/universer-api/comb/connect",ut="HEARTBEAT_INTERVAL",Bt=3e4,Fe="HEARTBEAT_TIMEOUT",_t=1e4,Vt="RETRY_CONNECTING_INTERVAL",Ft=2e4,Wt="RETRY_CONNECTING_MAX_COUNT",Gt=3;exports.CollaborationSession=class extends a.RxDisposable{constructor(e,s,i,r,o,c,l,u){super();d(this,"_sessionStatus$",new v.BehaviorSubject(0));d(this,"sessionStatus$",this._sessionStatus$.asObservable());d(this,"_event$",new v.Subject);d(this,"event$",this._event$.asObservable());d(this,"_socket");d(this,"_socketMessageSubscription");d(this,"_collaborationTimeoutTimer");this._unitID=e,this._logService=i,this._beforeCloseService=r,this._messageService=o,this._configService=c,this._localeService=l,this._memberService=u,s.pipe(T.takeUntil(this.dispose$)).subscribe(g=>{var S;typeof g>"u"||(this._socket=g,g?(this._joinRoom(g),this._socketMessageSubscription=this._socket.message$.subscribe(f=>{f.routeKey===this._unitID&&this._onCombEvent(f)})):(this._sessionStatus$.next(2),(S=this._socketMessageSubscription)==null||S.unsubscribe(),this._socketMessageSubscription=null))}),this.disposeWithMe(this._beforeCloseService.registerOnClose(()=>{var g;(g=this._socket)==null||g.send({cmd:b.LEAVE,data:{roomID:this._unitID}})}))}get sessionStatus(){return this._sessionStatus$.getValue()}getMemberID(){var e,s;return(s=(e=this._socket)==null?void 0:e.memberID)!=null?s:null}dispose(){super.dispose(),this.dispose$.next(),this.dispose$.complete()}_onCombEvent(e){e.cmd===b.JOIN?this._onJoinRoomEvent(e):e.cmd===b.RECV&&this._onRecvEvent(e)}_joinRoom(e){this._sessionStatus$.next(1),e.send({cmd:b.JOIN,routeKey:this._unitID,routeType:"",data:{rooms:[{roomID:this._unitID}]}})}_onJoinRoomEvent(e){var i;if(e.code===Be.FAIL){this._messageService.show({type:le.MessageType.Warning,content:this._localeService.t("session.room-full")}),this._sessionStatus$.next(2);return}this._sessionStatus$.next(3);const s=(i=e.data.roomInfos[this._unitID])==null?void 0:i.members;s&&s.forEach(r=>this._memberService.updateMember(this._unitID,r))}_onRecvEvent(e){try{const s=e.data;switch(s.eventID){case _.CollaborationEvent.USERS_ENTER:this._onUserJoin(s),this._event$.next(s);break;case _.CollaborationEvent.USERS_LEAVE:this._onUserLeave(s),this._event$.next(s);break;case _.CollaborationEvent.CHANGESET_ACK:this._clearCollaborationTimeoutTimer(),this._event$.next(s);break;case _.CollaborationEvent.MSG_FOR_ERROR:this._logService.error(`save fail reason is ${JSON.stringify(s)}`),this._event$.next(s);break;default:this._event$.next(s)}}catch(s){this._logService.error(s,e)}}_onUserJoin(e){this._memberService.updateMember(this._unitID,e.data)}_onUserLeave(e){this._memberService.removeMember(this._unitID,e.data.memberID)}async send(e,s){if(this.sessionStatus!==3||!this._socket)throw new Error("[CollaborationSession]: should not send message when the session is offline!");try{e.eventID===_.CollaborationEvent.NEW_CHANGESETS&&this._scheduleCollaborationTimeoutTimer(),this._socket.send({cmd:b.INGEST,routeKey:s,routeType:"",data:e})}catch(i){this._logService.error(i)}}_scheduleCollaborationTimeoutTimer(){var e;this._collaborationTimeoutTimer=window.setTimeout(()=>{this._collaborationTimeoutTimer=null,this._messageService.show({type:le.MessageType.Error,content:this._localeService.t("session.collaboration-timeout")})},(e=this._configService.getConfig(Fe))!=null?e:_t)}_clearCollaborationTimeoutTimer(){this._collaborationTimeoutTimer&&(clearTimeout(this._collaborationTimeoutTimer),this._collaborationTimeoutTimer=null)}};exports.CollaborationSession=lt([U(2,a.ILogService),U(3,A.IBeforeCloseService),U(4,A.IMessageService),U(5,a.IConfigService),U(6,h.Inject(a.LocaleService)),U(7,h.Inject(G))],exports.CollaborationSession);exports.CollaborationSessionService=class extends a.Disposable{constructor(e,s,i,r,o,c){super();d(this,"_socket$",new v.BehaviorSubject(void 0));d(this,"_sessions",new Map);d(this,"_status$",new v.BehaviorSubject(0));d(this,"status$",this._status$.asObservable());d(this,"_socketReady",!1);d(this,"_sendHeartbeatTimer");d(this,"_timeoutTimer");d(this,"_retryConnectingTimer");d(this,"_retryCount",0);this._injector=e,this._localeService=s,this._messageService=i,this._logService=r,this._configService=o,this._socketService=c}get _socket(){return this._socket$.getValue()}dispose(){super.dispose(),this._sessions.forEach(e=>e.dispose()),this._sessions.clear(),this._status$.complete()}async requireSession(e){if(this._sessions.has(e))return this._sessions.get(e);this._tryEnsureSocket();const s=this._injector.createInstance(exports.CollaborationSession,e,this._socket$.asObservable());return this._sessions.set(e,s),s}_createSocket(){var i;const e=(i=this._configService.getConfig(ht))!=null?i:Ht;return this._socketService.createSocket(e)}_tryEnsureSocket(){try{const e=this._createSocket();if(e){const s=e.send;e.send=i=>(this._rescheduleHeartbeatEvent(),s.apply(e,[i])),e.message$.subscribe(i=>this._onMessage(e,i)),e.error$.pipe(T.take(1)).subscribe(i=>this._logService.error("[CollaborationSessionService]: socket error",i)),e.open$.pipe(T.take(1)).subscribe(()=>{this._onConnectionOpen(e)}),e.close$.pipe(T.take(1)).subscribe(i=>{this._logService.debug("[CollaborationSessionService]","socket close",i),this._onConnectionFailed()})}}catch(e){this._logService.error(e),this._onConnectionFailed()}}_onConnectionOpen(e){this._logService.debug("[CollaborationSessionService]","socket open."),e.send({cmd:b.HELLO}),this._rescheduleHeartbeatEvent()}_onConnectionFailed(){var e;this._status$.next(2),this._socket$.next(null),this._clearTimeoutTimer(),this._clearHeartbeatTimer(),this._socketReady=!1,this._retryCount<((e=this._configService.getConfig(Wt))!=null?e:Gt)?(this._scheduleReconnection(this._retryCount),this._retryCount+=1):this._messageService.show({type:le.MessageType.Error,content:this._localeService.t("session.connection-failed")})}_scheduleReconnection(e){var i;const s=((i=this._configService.getConfig(Vt))!=null?i:Ft)*2**e;this._messageService.show({type:le.MessageType.Warning,content:this._localeService.t("session.will-retry")}),this._retryConnectingTimer=setTimeout(()=>{this._tryEnsureSocket(),clearTimeout(this._retryConnectingTimer),this._retryConnectingTimer=null},s)}_rescheduleHeartbeatEvent(){var e;this._clearHeartbeatTimer(),this._sendHeartbeatTimer=setTimeout(()=>this._sendHeartbeat(),(e=this._configService.getConfig(ut))!=null?e:Bt)}_sendHeartbeat(){this._socket.send({cmd:b.HEARTBEAT}),this._waitForHeartbeatResponse()}_waitForHeartbeatResponse(){var e;this._timeoutTimer=setTimeout(()=>this._onConnectionFailed(),(e=this._configService.getConfig(Fe))!=null?e:_t)}_onMessage(e,s){const{cmd:i}=s;i===b.HELLO&&!this._socketReady&&(e.memberID=s.data.memberID,this._socket$.next(e),this._status$.next(3),this._socketReady=!0),i===b.HEARTBEAT&&this._clearTimeoutTimer(),this._rescheduleHeartbeatEvent()}_clearHeartbeatTimer(){this._sendHeartbeatTimer!=null&&(clearTimeout(this._sendHeartbeatTimer),this._sendHeartbeatTimer=null)}_clearTimeoutTimer(){this._timeoutTimer!=null&&(clearTimeout(this._timeoutTimer),this._timeoutTimer=null)}};exports.CollaborationSessionService=lt([U(0,h.Inject(h.Injector)),U(1,h.Inject(a.LocaleService)),U(2,A.IMessageService),U(3,a.ILogService),U(4,a.IConfigService),U(5,Ve)],exports.CollaborationSessionService);var Yt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},se=(n,t)=>(e,s)=>t(e,s,n);const dt="LOCAL_CACHE_INTERVAL",Kt=1e3;let M=class extends a.Disposable{constructor(t,e,s,i,r){super();d(this,"_cachedData",new Map);d(this,"_saveTaskMap",new Map);d(this,"_disabled",!1);this._configService=t,this._localStorageService=e,this._beforeCloseService=s,this._localeService=i,this._revisionService=r,this._setupBeforeClosingHandler()}disableLocalCache(){this._disabled=!0}enableLocalCache(){this._disabled=!1}dispose(){this._exhaustSavingTask().then(()=>super.dispose())}async loadOfflineData(t){return this._disabled?null:this._localStorageService.getItem(qe(t))}async saveOfflineData(t,e){return!!this._localStorageService.setItem(t,e)}updateOfflineData(t,e,s,i){const r=this._revisionService.getCurrentRevForDocument(t);this._cachedData.set(t,{unitID:t,type:e,awaitingChangeset:s,mutations:i,rev:r}),this._saveTaskMap.has(t)||this._scheduleSaving(t)}_scheduleSaving(t){const e=this._getSaveTimeout();e===0?this._saveCache(t):this._saveTaskMap.set(t,setTimeout(()=>this._saveCache(t),e))}_getSaveTimeout(){var t;return(t=this._configService.getConfig(dt))!=null?t:Kt}_saveCache(t){const e=this._saveTaskMap.get(t);return e!==void 0&&window.clearTimeout(e),this._localStorageService.setItem(qe(t),this._cachedData.get(t)).then(()=>this._saveTaskMap.delete(t))}async _exhaustSavingTask(){const t=[];this._saveTaskMap.forEach((e,s)=>{window.clearTimeout(e),t.push(this._saveCache(s).then(()=>{this._saveTaskMap.delete(s)}))}),await Promise.all(t)}_setupBeforeClosingHandler(){this.disposeWithMe(this._beforeCloseService.registerBeforeClose(()=>{if(this._saveTaskMap.size)return this._localeService.t("collaboration-client.offline-data-not-saved")}))}};M=Yt([se(0,a.IConfigService),se(1,a.ILocalStorageService),se(2,A.IBeforeCloseService),se(3,h.Inject(a.LocaleService)),se(4,h.Inject(_.RevisionService))],M);function qe(n){return`unit-cache-${n}`}const be=h.createIdentifier("univer-pro.collaboration-client.single-active-unit-service");var gt=(n=>(n[n.NO_OTHER_CLIENTS_EDITING=0]="NO_OTHER_CLIENTS_EDITING",n[n.OTHER_CLIENTS_EDITING=1]="OTHER_CLIENTS_EDITING",n))(gt||{});const Xe=3e4,ze="ACTIVE_UNIT_EVENT_CHANNEL";class qt extends a.Disposable{constructor(){super();d(this,"_id",a.Tools.generateRandomId());d(this,"_selfUnitIDs",new Set);d(this,"_unitOnClients",new Map);d(this,"_heartbeatTimer",null);d(this,"_clearOtherTimers",new Map);d(this,"_unitStatus",new Map);this._init()}dispose(){super.dispose(),this._clearOtherTimers.forEach((e,s)=>this._removeClearOtherTimer(s)),this._heartbeatTimer&&window.clearInterval(this._heartbeatTimer)}getUnitStatus$(e){return this._ensureSubject(e).pipe(v.distinctUntilChanged())}editingUnit(e){this._selfUnitIDs.size===0&&this._scheduleHeartbeat(),this._selfUnitIDs.add(e),this._send({type:0,memberID:this._id,unitID:e})}disposeUnit(e){this._selfUnitIDs.delete(e),this._selfUnitIDs.size===0&&this._heartbeatTimer&&window.clearInterval(this._heartbeatTimer)}_init(){this.disposeWithMe(a.toDisposable(v.fromEvent(window,"storage").subscribe(e=>{if(e.key!==ze||!e.newValue)return;const s=JSON.parse(e.newValue);this._handleEvent(s)}))),window.addEventListener("unload",()=>this._send({type:1,memberID:this._id,unitIDs:Array.from(this._selfUnitIDs)}))}_handleEvent(e){switch(e.type){case 0:this._handleJoinEvent(e);break;case 1:this._handleLeaveEvent(e);break;case 2:this._handleHeartbeatEvent(e);break}}_handleJoinEvent(e){const{unitID:s,memberID:i}=e;if(!this._unitOnClients.has(s)||!this._unitOnClients.get(s).has(i)){const r=this._unitOnClients.get(s)||new Set;r.add(i),this._unitOnClients.set(s,r),this._scheduleClearOtherTimer(i),this._send({type:0,memberID:this._id,unitID:s})}else this._ensureSubject(s).next(1)}_scheduleClearOtherTimer(e){this._removeClearOtherTimer(e);const s=window.setTimeout(()=>{this._unitOnClients.forEach(i=>{i.delete(e)})},Xe*2);this._clearOtherTimers.set(e,s)}_removeClearOtherTimer(e){if(this._clearOtherTimers.has(e)){const s=this._clearOtherTimers.get(e);s&&window.clearTimeout(s),this._clearOtherTimers.set(e,null)}}_handleLeaveEvent(e){const{memberID:s,unitIDs:i}=e;i.forEach(r=>{var c;const o=this._unitOnClients.get(r);o&&(o.delete(s),(c=this._ensureSubject(r))==null||c.next(o.size===0?0:1))}),this._removeClearOtherTimer(s)}_handleHeartbeatEvent(e){this._scheduleClearOtherTimer(e.memberID)}_send(e){localStorage.setItem(ze,JSON.stringify(e))}_scheduleHeartbeat(){this._heartbeatTimer=window.setInterval(()=>{this._send({type:2,memberID:this._id})},Xe)}_ensureSubject(e){return this._unitStatus.has(e)||this._unitStatus.set(e,new v.BehaviorSubject(0)),this._unitStatus.get(e)}}var Xt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},Je=(n,t)=>(e,s)=>t(e,s,n);let fe=class{constructor(n,t){this._injector=n,this._transformService=t}transformIMECache(n){this._transformUndoRedoStack(n),this._transformPreviousActiveRange(n)}transformRemoteChangeset(n){const t=this._injector.get(N.IMEInputManagerService),{redoCache:e}=t.getUndoRedoMutationParamsCache();if(e.length===0)return n;let s=a.Tools.deepClone(n.mutations[0]);for(let i=0;i<e.length;i++){const r={id:"doc.mutation.rich-text-editing",params:{...e[i]}},o=this._transformService.transformMutation(s,r,!1);if(_.isTransformMutationFailure(o))throw o.error;s=o.m1Prime}return{...a.Tools.deepClone(n),mutations:[s]}}_transformUndoRedoStack(n){const t=this._injector.get(N.IMEInputManagerService),{undoCache:e,redoCache:s}=t.getUndoRedoMutationParamsCache();if(e.length===0||s.length===0)return;const i=[],r=[];let o=a.Tools.deepClone(n.mutations[0]),c=a.Tools.deepClone(n.mutations[0]);for(let l=e.length-1;l>=0;l--){const u={id:"doc.mutation.rich-text-editing",params:{...e[l]}},g={id:"doc.mutation.rich-text-editing",params:{...s[l]}},S=this._transformService.transformMutation(o,u,!1),f=this._transformService.transformMutation(c,g,!1);if(_.isTransformMutationFailure(S))throw S.error;if(_.isTransformMutationFailure(f))throw f.error;i.unshift(S.m2Prime.params),r.unshift(f.m2Prime.params),o=S.m1Prime,c=f.m1Prime}t.setUndoRedoMutationParamsCache({undoCache:i,redoCache:r})}_transformPreviousActiveRange(n){const t=this._injector.get(N.IMEInputManagerService),e=t.getActiveRange();if(e==null)return;const s=[{id:"doc.mutation.rich-text-editing",params:{unitId:n.unitID,actions:[],textRanges:[e]}}],i=this._transformService.transformMutationsWithChangeset(n,s);if(!_.isTransformMutationsWithChangesetSuccess(i))throw i.error;const r=i.m2Prime[0].params.textRanges;Array.isArray(r)&&r.length&&t.setActiveRange(r[0])}};fe=Xt([Je(0,h.Inject(h.Injector)),Je(1,_.ITransformService)],fe);var zt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},Ze=(n,t)=>(e,s)=>t(e,s,n);let Ie=class{constructor(n,t){this._injector=n,this._transformService=t}transformSelections(n){var c;const t=this._injector.get(N.TextSelectionManagerService),e=(c=t.getSelections())!=null?c:[],s=e==null?void 0:e.map(N.serializeTextRange);if(s.length===0)return;const i=[{id:"doc.mutation.rich-text-editing",params:{unitId:n.unitID,actions:[],textRanges:s}}],r=this._transformService.transformMutationsWithChangeset(n,i);if(!_.isTransformMutationsWithChangesetSuccess(r))throw r.error;const o=r.m2Prime[0].params.textRanges;Array.isArray(o)&&o.length&&t.replaceTextRanges(o,!1)}};Ie=zt([Ze(0,h.Inject(h.Injector)),Ze(1,_.ITransformService)],Ie);function St(n){let t="";for(const e of n){const{startOffset:s,endOffset:i,isActive:r}=e;t.length&&(t+=","),t+=`${s}:${i}:${r?"1":"0"}`}return t}function Jt(n){const t=n.split(","),e=[];for(const s of t){const[i,r,o]=s.split(":");e.push({startOffset:Number(i),endOffset:Number(r),collapsed:i===r,isActive:o==="1"})}return e.some(s=>s.isActive)||(e[0].isActive=!0),e}class We extends a.RxDisposable{constructor(){super(...arguments);d(this,"_collabCursorState$",new v.BehaviorSubject(null));d(this,"collabCursorState$",this._collabCursorState$.asObservable())}syncEditingCollabCursor(e){const{unitID:s,memberID:i,textRanges:r}=e,o=St(r),c={unitID:s,memberID:i,selection:o};this._collabCursorState$.next(c)}}var Zt=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},Qe=(n,t)=>(e,s)=>t(e,s,n);let Ce=class{constructor(n,t){this._injector=n,this._transformService=t}transformSelections(n){var u,g,S,f;const t=this._injector.get(p.SelectionManagerService),{pluginName:e,unitId:s,sheetId:i}=t.getCurrent()||{},r=(u=t.getSelections())!=null?u:[];if(r.length===0||!e||!s||!i)return;const o=[{id:p.SetSelectionsOperation.id,params:{unitId:s,subUnitId:i,pluginName:e,selections:a.Tools.deepClone(r)}}],c=this._transformService.transformMutationsWithChangeset(n,o);if(!_.isTransformMutationsWithChangesetSuccess(c))throw c.error;const l=(f=(S=(g=c.m2Prime[0])==null?void 0:g.params)==null?void 0:S.selections)!=null?f:r;Array.isArray(l)&&l.length&&this._injector.get(a.ICommandService).executeCommand(p.SetSelectionsOperation.id,{unitId:s,subUnitId:i,pluginName:e,selections:l})}};Ce=Zt([Qe(0,h.Inject(h.Injector)),Qe(1,_.ITransformService)],Ce);const Qt=new Set([p.InsertSheetMutation.id]);function es(n,t,e,s,i){var u,g,S,f;const r=[];for(const C of n)if(Qt.has(C.id)){if(r.length>0)break;r.push(C);break}else r.push(C);const o=(g=(u=i.getCurrentUser())==null?void 0:u.userID)!=null?g:"unknown",c=(f=(S=i.getCurrentUser())==null?void 0:S.memberID)!=null?f:"unknown";return{changeset:{unitID:t,type:_.mapDocumentTypeToUniverType(e.getUnitType(t)),baseRev:s.getCurrentRevForDocument(t),revision:0,userID:o,memberID:c,mutations:r},pendingMutations:n.slice(r.length)}}function ts(n,t,e,s,i){var g,S,f,C;const o=[n.reduce((E,y)=>{var ee;const{id:O}=E,{id:H,type:Z}=y,ye=(ee=E.params)!=null?ee:{actions:[]},Q=y.params;if(O&&O!==H)throw new Error(`Cannot assemble a changeset from multiple mutations of different types: ${O} - ${H}.`);return{...E,id:H,type:Z,params:{unitId:Q.unitId,textRanges:Q.textRanges,actions:a.TextX.compose(ye.actions,Q.actions)}}},{})],c=(S=(g=i.getCurrentUser())==null?void 0:g.userID)!=null?S:"unknown",l=(C=(f=i.getCurrentUser())==null?void 0:f.memberID)!=null?C:"unknown";return{changeset:{unitID:t,type:_.mapDocumentTypeToUniverType(e.getUnitType(t)),baseRev:s.getCurrentRevForDocument(t),revision:0,userID:c,memberID:l,mutations:o},pendingMutations:[]}}var K=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},m=(n,t)=>(e,s)=>t(e,s,n);const vt="SEND_CHANGESET_TIMEOUT",ss=2e3;var D=(n=>(n.NOT_COLLAB="not_collab",n.SYNCED="synced",n.PENDING="pending",n.AWAITING="awaiting",n.AWAITING_WITH_PENDING="awaiting_with_pending",n.FETCH_MISS="fetch_missing",n.CONFLICT="conflict",n.OFFLINE="offline",n))(D||{});class q{constructor(t,e,s,i,r,o,c,l,u){d(this,"_awaitingChangeset",null);d(this,"_pendingMutations",[]);this.unitID=t,this.type=e,this._handler=r,this._commandService=o,this._undoRedoService=c,this._revisionService=l,this._localCacheService=u,this._awaitingChangeset=s,this._pendingMutations=i}_checkMissing(t){const e=this._revisionService.getCurrentRevForDocument(this.unitID);return t.revision>e+1?(this._handler.onMissingChangesets({from:e,to:t.revision-1}),!0):!1}_transformUndoredo(t){this._undoRedoService.transformUndoRedo(this.unitID,t)}_transformSelections(t){var e,s;(s=(e=this._handler).onTransformSelections)==null||s.call(e,t)}_transformIMECache(t){var e,s;return(s=(e=this._handler).onTransformIME)==null?void 0:s.call(e,t)}_transformRemoteChangesetByIMECache(t){var e,s,i;return(i=(s=(e=this._handler).onTransformRemoteChangesetByIMECache)==null?void 0:s.call(e,t))!=null?i:t}_syncEditingCollabCursor(t){var e,s;if(this.type===$.UNIVER_DOC){const{unitID:i,mutations:r,memberID:o}=t,c=r[0].params.textRanges;Array.isArray(c)&&c.length>0&&((s=(e=this._handler).onSyncEditingCollabCursor)==null||s.call(e,{unitID:i,memberID:o,textRanges:c}))}}_updateLocalCache(){this._localCacheService.updateOfflineData(this.unitID,this.type,this._awaitingChangeset,this._pendingMutations)}_getCurrentRevision(){return this._revisionService.getCurrentRevForDocument(this.unitID)}_incrementRevisionNumber(){this._revisionService.incrementRevForDocument(this.unitID)}_executeRemoteChangeset(t){var i;const e=this._transformRemoteChangesetByIMECache(t),s=a.sequenceExecute(e.mutations,this._commandService,{fromCollab:!0});if(!s.result)throw s.error instanceof Error?s.error:new Error((i=s.error)!=null?i:"[CollaborationState]: apply error!");this._transformIMECache(e),this._transformUndoredo(t),this._transformSelections(e),this._syncEditingCollabCursor(e),this._incrementRevisionNumber()}}let he=class extends q{constructor(t,e,s,i,r,o,c,l,u){super(t,e,null,[],s,l,c,i,r);d(this,"status","synced");this._injector=o,this._logService=u}appendMutation(t){const e=this._injector.createInstance(j,this.unitID,this.type,[t],this._handler);return e._schedule(),e._updateLocalCache(),e}onRemoteChangeset(t){if(this._checkMissing(t))return this._injector.createInstance(x,this.unitID,this.type,null,[],null,[t],this._handler);try{return this._executeRemoteChangeset(t),this}catch(s){return this._logService.error("[CollaborationController]: remote changeset applied error.",s),this}}onRemoteAck(){throw new Error("[SyncedState]: received acknowledgement.")}onRemoteRej(){throw new Error("[SyncedState]: received rejection.")}toggleOffline(){return this._injector.createInstance(V,this.unitID,this.type,null,[],this._handler)}toggleOnline(){return this}resend(){throw new Error("[SyncedState]: invalid calling to `resend`.")}};he=K([m(3,h.Inject(_.RevisionService)),m(4,h.Inject(M)),m(5,h.Inject(h.Injector)),m(6,a.IUndoRedoService),m(7,a.ICommandService),m(8,a.ILogService)],he);let j=class extends q{constructor(t,e,s,i,r,o,c,l,u,g,S,f,C,E){super(t,e,null,s,i,g,E,o,c);d(this,"status","pending");d(this,"_scheduleTimestamp",null);d(this,"_sendingTimer",null);this._injector=r,this._memberService=l,this._logService=u,this._configService=S,this._transformService=f,this._univerInstanceService=C}appendMutation(t){return this._pendingMutations.push(t),this._updateLocalCache(),this}onRemoteChangeset(t){if(this._checkMissing(t))return this._clearScheduledTask(),this._injector.createInstance(x,this.unitID,this.type,null,this._pendingMutations,null,[t],this._handler);try{const s=this._transformService.transformMutationsWithChangeset(t,this._pendingMutations);if(_.isTransformMutationsWithChangesetSuccess(s)){const{c1Prime:i,m2Prime:r}=s;this._executeRemoteChangeset(i);const o=this._injector.createInstance(j,this.unitID,this.type,r,this._handler);return this._clearScheduledTask(),o._schedule(this._scheduleTimestamp?Math.max(0,new Date().getTime()-this._scheduleTimestamp):this._getSendChangesetTimeout()),o}throw s.error}catch(s){return this._logService.error(s),this._onConflict()}}onRemoteAck(){throw new Error("[PendingState]: received acknowledgement.")}onRemoteRej(){throw new Error("[PendingState]: received rejection.")}toggleOffline(){return this._clearScheduledTask(),this._injector.createInstance(V,this.unitID,this.type,null,this._pendingMutations,this._handler)}toggleOnline(){return this}_schedule(t){t=t!=null?t:this._getSendChangesetTimeout(),this._scheduleTimestamp=new Date().getTime(),this._sendingTimer=setTimeout(()=>{this._clearScheduledTask();let e=null;switch(this.type){case $.UNIVER_SHEET:{e=es(this._pendingMutations,this.unitID,this._univerInstanceService,this._revisionService,this._memberService);break}case $.UNIVER_DOC:{e=ts(this._pendingMutations,this.unitID,this._univerInstanceService,this._revisionService,this._memberService);break}default:throw new Error(`[PendingState]: unhandled univer type: ${this.type} in _schedule.`)}const{changeset:s,pendingMutations:i}=e;this._handler.onSendChangeset(s);const r=i.length?this._injector.createInstance(P,this.unitID,this.type,s,i,this._handler):this._injector.createInstance(B,this.unitID,this.type,s,this._handler);r._updateLocalCache(),this._handler.onStateChange(this,r)},t)}_getSendChangesetTimeout(){var t;return(t=this._configService.getConfig(vt))!=null?t:ss}resend(){throw new Error("[PendingState]: invalid calling to `resend`.")}_clearScheduledTask(){this._sendingTimer!=null&&(clearTimeout(this._sendingTimer),this._sendingTimer=null)}_onConflict(){return this._clearScheduledTask(),this._injector.createInstance(Y,this.unitID,this.type,null,this._pendingMutations,this._handler)}};j=K([m(4,h.Inject(h.Injector)),m(5,h.Inject(_.RevisionService)),m(6,h.Inject(M)),m(7,h.Inject(G)),m(8,a.ILogService),m(9,a.ICommandService),m(10,a.IConfigService),m(11,_.ITransformService),m(12,a.IUniverInstanceService),m(13,a.IUndoRedoService)],j);let B=class extends q{constructor(t,e,s,i,r,o,c,l,u,g,S){super(t,e,s,[],i,l,S,o,c);d(this,"status","awaiting");this._injector=r,this._logService=u,this._transformService=g}appendMutation(t){const e=this._injector.createInstance(P,this.unitID,this.type,this._awaitingChangeset,[t],this._handler);return e._updateLocalCache(),e}onRemoteChangeset(t){if(this._checkMissing(t))return this._injector.createInstance(x,this.unitID,this.type,this._awaitingChangeset,[],null,[t],this._handler);try{const s=this._transformService.transformChangesets([t],[this._awaitingChangeset],!1);if(_.isTransformChangesetsSuccess(s)){const{c1Prime:i,c2Prime:r}=s;this._executeRemoteChangeset(i[0]),r[0].baseRev=this._getCurrentRevision();const o=this._injector.createInstance(B,this.unitID,this.type,r[0],this._handler);return o._updateLocalCache(),o}return this._onConflict()}catch(s){return this._logService.error(s),this._onConflict()}}onRemoteAck(t){const e=this._revisionService.getCurrentRevForDocument(this.unitID);if(t.revision<e-1)return this;if(this._checkMissing(t))return this._injector.createInstance(x,this.unitID,this.type,null,[],this._awaitingChangeset,[],this._handler);this._incrementRevisionNumber();const i=this._injector.createInstance(he,this.unitID,this.type,this._handler);return i._updateLocalCache(),i}onRemoteRej(){return this._onConflict()}toggleOffline(){return this._injector.createInstance(V,this.unitID,this.type,this._awaitingChangeset,[],this._handler)}toggleOnline(){return this}resend(){this._handler.onSendChangeset(this._awaitingChangeset)}_onConflict(){return this._injector.createInstance(Y,this.unitID,this.type,this._awaitingChangeset,[],this._handler)}};B=K([m(4,h.Inject(h.Injector)),m(5,h.Inject(_.RevisionService)),m(6,h.Inject(M)),m(7,a.ICommandService),m(8,a.ILogService),m(9,_.ITransformService),m(10,a.IUndoRedoService)],B);let P=class extends q{constructor(t,e,s,i,r,o,c,l,u,g,S,f){super(t,e,s,i,r,u,f,c,l);d(this,"status","awaiting_with_pending");this._injector=o,this._logService=g,this._transformService=S}appendMutation(t){return this._pendingMutations.push(t),this}onRemoteChangeset(t){if(this._checkMissing(t))return this._injector.createInstance(x,this.unitID,this.type,this._awaitingChangeset,this._pendingMutations,null,[t],this._handler);try{const s=this._transformService.transformChangesets([t],[this._awaitingChangeset],!1);if(_.isTransformChangesetsSuccess(s)){const{c1Prime:i,c2Prime:r}=s,o=this._transformService.transformMutationsWithChangeset(i[0],this._pendingMutations);if(_.isTransformMutationsWithChangesetSuccess(o)){const{c1Prime:c,m2Prime:l}=o;return this._executeRemoteChangeset(c),r[0].baseRev=this._getCurrentRevision(),this._injector.createInstance(P,this.unitID,this.type,r[0],l,this._handler)}throw o.error}throw s.error}catch(s){return this._logService.error(s),this._onConflict()}}onRemoteAck(t){if(this._checkMissing(t))return this._injector.createInstance(x,this.unitID,this.type,null,this._pendingMutations,this._awaitingChangeset,[],this._handler);this._incrementRevisionNumber();const s=this._injector.createInstance(j,this.unitID,this.type,this._pendingMutations,this._handler);return s._schedule(),s._updateLocalCache(),s}onRemoteRej(){return this._onConflict()}toggleOffline(){return this._injector.createInstance(V,this.unitID,this.type,this._awaitingChangeset,this._pendingMutations,this._handler)}toggleOnline(){return this}resend(){this._handler.onSendChangeset(this._awaitingChangeset)}_onConflict(){return this._injector.createInstance(Y,this.unitID,this.type,null,this._pendingMutations,this._handler)}};P=K([m(5,h.Inject(h.Injector)),m(6,h.Inject(_.RevisionService)),m(7,h.Inject(M)),m(8,a.ICommandService),m(9,a.ILogService),m(10,_.ITransformService),m(11,a.IUndoRedoService)],P);let Y=class extends q{constructor(t,e,s,i,r,o,c,l,u,g,S,f){super(t,e,s,i,r,c,l,g,u);d(this,"status","conflict");this._univerPermissionService=o,this._localeService=S,this._notificationService=f,this._showConflictNotification(),this._clearLocalCache(),this._disableEditing()}appendMutation(){return this}onRemoteChangeset(){return this}onRemoteAck(){return this}onRemoteRej(){return this}toggleOffline(){return this}toggleOnline(){return this}resend(){throw new Error("[ConflictState]: invalid calling to `resend`.")}_clearLocalCache(){this._localCacheService.updateOfflineData(this.unitID,this.type,null,[])}_showConflictNotification(){this._notificationService.show({title:this._localeService.t("conflict.title"),content:this._localeService.t("conflict.content"),type:"error",duration:0})}_disableEditing(){this._univerPermissionService.setEditable(this.unitID,!1)}};Y=K([m(5,h.Inject(a.UniverPermissionService)),m(6,a.ICommandService),m(7,a.IUndoRedoService),m(8,h.Inject(M)),m(9,h.Inject(_.RevisionService)),m(10,h.Inject(a.LocaleService)),m(11,A.INotificationService)],Y);let V=class extends q{constructor(t,e,s,i,r,o,c,l,u,g){super(t,e,s,i,r,u,g,c,l);d(this,"status","offline");this._injector=o}appendMutation(t){return this._pendingMutations.push(t),this._updateLocalCache(),this}onRemoteChangeset(t){throw new Error("[OfflineState]: received changeset.")}onRemoteAck(){throw new Error("[OfflineState]: received acknowledgement.")}onRemoteRej(){throw new Error("[OfflineState]: received rejection.")}toggleOffline(){return this}toggleOnline(){const{_injector:t,_pendingMutations:e,_awaitingChangeset:s,unitID:i,_handler:r,type:o}=this,c=mt(t,i,o,s,e,r);return c instanceof j?c._schedule():(c instanceof P||c instanceof B)&&c.resend(),c}resend(){throw new Error("[OfflineState]: invalid calling to `resend`.")}};V=K([m(5,h.Inject(h.Injector)),m(6,h.Inject(_.RevisionService)),m(7,h.Inject(M)),m(8,a.ICommandService),m(9,a.IUndoRedoService)],V);let x=class extends q{constructor(t,e,s,i,r,o,c,l,u,g,S,f,C,E){super(t,e,s,i,c,f,C,u,g);d(this,"status","fetch_missing");this._acknowledgedAwaitingChangeset=r,this._queuedRemoteChangesets=o,this._injector=l,this._logService=S,this._transformService=E}onMissedChangesetFetched(t){try{const e=[...t,...this._queuedRemoteChangesets],s=[this._awaitingChangeset||this._acknowledgedAwaitingChangeset].filter(l=>!!l);let i,r;if(s.length){const l=this._transformService.transformChangesets(e,s,!1);if(!_.isTransformChangesetsSuccess(l))throw l.error;i=l.c1Prime,r=l.c2Prime}else i=e,r=[];let o=this._pendingMutations;i.forEach(l=>{let u;if(o.length){const g=this._transformService.transformMutationsWithChangeset(l,o);if(!_.isTransformMutationsWithChangesetSuccess(g))throw g.error;u=g.c1Prime,o=g.m2Prime}else u=l;this._executeRemoteChangeset(u)}),this._acknowledgedAwaitingChangeset&&this._incrementRevisionNumber(),this._awaitingChangeset&&r.length&&(r[0].baseRev=this._getCurrentRevision());let c;if(this._awaitingChangeset&&o.length!==0)c=this._injector.createInstance(P,this.unitID,this.type,r[0],o,this._handler);else if(this._awaitingChangeset&&o.length===0)r[0].baseRev=this._getCurrentRevision(),c=this._injector.createInstance(B,this.unitID,this.type,r[0],this._handler);else if(o.length!==0){const l=this._injector.createInstance(j,this.unitID,this.type,o,this._handler);l._schedule(),c=l}else c=this._injector.createInstance(he,this.unitID,this.type,this._handler);return c._updateLocalCache(),c}catch(e){return this._logService.error("[FetchMissState]","failed to apply missed changesets!",e),this._injector.createInstance(Y,this.unitID,this.type,this._awaitingChangeset,this._pendingMutations,this._handler)}}resend(){throw new Error("[FetchingMissState]: invalid calling to `resend`.")}appendMutation(t){return this._pendingMutations.push(t),this}onRemoteChangeset(t){return this._queuedRemoteChangesets.push(t),this}onRemoteAck(t){if(this._awaitingChangeset)return this._acknowledgedAwaitingChangeset=this._awaitingChangeset,this._awaitingChangeset=null,this;throw new Error("[FetchingMissState]: not expected to receive ack when `this._awaitingChangeset` is null!")}onRemoteRej(){return this._onConflict()}toggleOffline(){return this._injector.createInstance(V,this.unitID,this.type,this._awaitingChangeset,this._pendingMutations,this._handler)}toggleOnline(){return this}_onConflict(){return this._injector.createInstance(Y,this.unitID,this.type,this._awaitingChangeset,this._pendingMutations,this._handler)}};x=K([m(7,h.Inject(h.Injector)),m(8,h.Inject(_.RevisionService)),m(9,h.Inject(M)),m(10,a.ILogService),m(11,a.ICommandService),m(12,a.IUndoRedoService),m(13,_.ITransformService)],x);function mt(n,t,e,s,i,r){return s&&i.length?n.createInstance(P,t,e,s,i,r):s?n.createInstance(B,t,e,s,r):i.length?n.createInstance(j,t,e,i,r):n.createInstance(he,t,e,r)}var Te=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},I=(n,t)=>(e,s)=>t(e,s,n);exports.CollaborationController=class extends a.RxDisposable{constructor(e,s,i){super();d(this,"_entities",new Map);d(this,"_entityInit$",new v.Subject);this._injector=e,this._collabSessionService=s,this._univerInstanceService=i,this._init()}dispose(){super.dispose(),this._entities.forEach(e=>e.dispose()),this._entities.clear()}getCollabEntity(e){var s;return(s=this._entities.get(e))!=null?s:null}getCollabEntity$(e){const s=this.getCollabEntity(e);return s?v.of(s):this._entityInit$.pipe(T.filter(i=>i.unitID===e))}_init(){this._univerInstanceService.getTypeOfUnitAdded$(a.UniverInstanceType.UNIVER_SHEET).pipe(v.takeUntil(this.dispose$),T.delay(16)).subscribe(async s=>{const i=s.getUnitId(),r=await this._startCollaboration(i,$.UNIVER_SHEET);this._entities.set(i,r)}),this._univerInstanceService.getTypeOfUnitAdded$(a.UniverInstanceType.UNIVER_DOC).pipe(v.takeUntil(this.dispose$),T.delay(16)).pipe(T.filter(s=>!s.getUnitId().startsWith("__"))).subscribe(async s=>{const i=s.getUnitId(),r=await this._startCollaboration(i,$.UNIVER_DOC);this._entities.set(i,r)}),v.merge(this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_SHEET),this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_DOC)).pipe(v.takeUntil(this.dispose$)).subscribe(s=>{const i=s.getUnitId(),r=this._entities.get(i);r&&(r.dispose(),this._entities.delete(i))})}async _startCollaboration(e,s){const i=await this._collabSessionService.requireSession(e),r=this._injector.createInstance(this._getCtorByUniverType(s),e,s,i);return await r.init(),this._entityInit$.next(r),r}_getCtorByUniverType(e){switch(e){case $.UNIVER_DOC:return Ae;case $.UNIVER_SHEET:return ke;default:throw new Error(`[CollaborationController]: invalid univer type: ${e}`)}}};exports.CollaborationController=Te([a.OnLifecycle(a.LifecycleStages.Starting,exports.CollaborationController),I(0,h.Inject(h.Injector)),I(1,h.Inject(exports.CollaborationSessionService)),I(2,a.IUniverInstanceService)],exports.CollaborationController);let pe=class extends a.RxDisposable{constructor(t,e,s,i,r,o,c,l,u,g,S,f,C){super();d(this,"_state$",new v.BehaviorSubject(null));d(this,"state$",this._state$.asObservable());d(this,"_state");d(this,"_collaborationPaused",!1);d(this,"status$",this.state$.pipe(T.map(t=>t?t.status:D.OFFLINE),T.shareReplay(1)));d(this,"_transitionLocked",!1);d(this,"_remoteChangesetQueue",[]);this.unitID=t,this._type=e,this._session=s,this._injector=i,this._localCacheService=r,this._univerPermissionService=o,this._compressMutationService=c,this._localeService=l,this._revisionService=u,this._logService=g,this._commandService=S,this._messageService=f,this._singleActiveUnitService=C}get state(){return this._state}async init(){if(this.state)throw new Error('[CollaborationEntity]: initial state has been created before. You should not call "init" twice.');await this._init()}pauseCollaboration(){return this._collaborationPaused=!0,a.toDisposable(()=>{this._collaborationPaused=!1,this._exhaustRemoteChangesetQueue()})}_updateState(t){this._state=t,this._state$.next(t)}async _init(){var t;return this._updateState(await this._createInitialState()),this._singleActiveUnitService&&((t=this._singleActiveUnitService)==null||t.editingUnit(this.unitID),this.disposeWithMe(a.toDisposable(this._singleActiveUnitService.getUnitStatus$(this.unitID).subscribe(e=>{this._logService.debug("[CollaborationEntity]","editing status changed to",e),e===gt.OTHER_CLIENTS_EDITING?(this._messageService.show({content:this._localeService.t("collaboration.single-unit.warning"),type:le.MessageType.Warning}),this._univerPermissionService.setEditable(this.unitID,!1)):this._univerPermissionService.setEditable(this.unitID,!0)})))),this.disposeWithMe(a.toDisposable(this._session.sessionStatus$.subscribe(e=>{e===W.ONLINE?this._toggleOnline():e===W.OFFLINE&&this._toggleOffline()}))),this.disposeWithMe(a.toDisposable(this._session.event$.subscribe(e=>{try{const s=e.eventID;s===_.CollaborationEvent.NEW_CHANGESETS?this._onRemoteChangeset(_.parseProtocolChangeset(e.data)):s===_.CollaborationEvent.CHANGESET_ACK?this._onRemoteACK(e.data):s===_.CollaborationEvent.CHANGESET_REJ?this._onRemoteRejected():s===_.CollaborationEvent.PSEUDO_FETCH_MISSING_RESULT&&this._onFetchMissResult(e.data.changesets.map(i=>_.parseProtocolChangeset(i)))}catch(s){throw console.error("Error on receiving event",s),s}}))),this._state}_unlockTransition(){this._transitionLocked=!1}_lockTransition(){if(this._transitionLocked)throw new Error("[CollaborationEntity]: cannot lock transition twice! This is an implementation error, meaning you transit the collaboration state again in the process of a previous transition. This should never happen.");this._transitionLocked=!0}_onLocalMutation(t){this._lockTransition(),this._updateState(this._state.appendMutation(t)),this._unlockTransition()}_onRemoteChangeset(t){if(!(t.revision<=this._revisionService.getCurrentRevForDocument(this.unitID))){if(this._collaborationPaused){this._remoteChangesetQueue.push(t);return}this._applyRemoteChangeset(t)}}_exhaustRemoteChangesetQueue(){this._remoteChangesetQueue.forEach(t=>this._applyRemoteChangeset(t)),this._remoteChangesetQueue=[]}_applyRemoteChangeset(t){const e=this._compressMutationService.interceptor.fetchThroughInterceptors(this._compressMutationService.interceptor.getInterceptPoints().COMPRESS_MUTATION_APPLY)(t.mutations,null)||t.mutations,s={...t,mutations:e};this._lockTransition(),this._updateState(this._state.onRemoteChangeset(s)),this._unlockTransition()}_onRemoteACK(t){this._lockTransition(),this._updateState(this._state.onRemoteAck(t)),this._unlockTransition()}_onRemoteRejected(){this._lockTransition(),this._updateState(this._state.onRemoteRej()),this._unlockTransition()}_onFetchMissResult(t){if(!(this._state instanceof x))throw new TypeError("[CollaborationEntity]: cannot apply missing results on other states!");const e=t.map(s=>{const i=this._compressMutationService.interceptor.fetchThroughInterceptors(this._compressMutationService.interceptor.getInterceptPoints().COMPRESS_MUTATION_APPLY)(s.mutations,null)||s.mutations;return{...s,mutations:i}});this._lockTransition(),this._updateState(this._state.onMissedChangesetFetched(e)),this._unlockTransition()}_toggleOffline(){this._lockTransition(),this._updateState(this._state.toggleOffline()),this._unlockTransition()}_toggleOnline(){this._lockTransition(),this._updateState(this._state.toggleOnline()),this._unlockTransition()}async _createInitialState(){return new Promise(t=>{this._session.sessionStatus$.pipe(T.take(1)).subscribe(async e=>{t(await this._createInitialStateImpl(e===W.ONLINE))})})}_createHandler(){const t=this.unitID;return{onStateChange:(s,i)=>{if(s!==this._state)throw new Error(`[ClientCollaborationController]: invalid state transition! State transferred from is not the current state.
|
2
|
+
Before: ${s.status}
|
3
|
+
After: ${i.status}
|
4
|
+
Current: ${this._state.status}`);this._updateState(i)},onSendChangeset:s=>{const i={eventID:_.CollaborationEvent.SUBMIT_CHANGESET,data:{unitID:s.unitID,unitType:this._type,changeset:s,memberID:this._session.getMemberID()}};this._session.send(i,this.unitID)},onMissingChangesets:({from:s,to:i})=>{this._logService.debug("[CollaborationEntity]",`fetching missing changesets from ${s} to ${i}`);const r={eventID:_.CollaborationEvent.FETCH_MISSING,data:{unitID:t,unitType:this._type,from:s,to:i}};this._session.send(r,this.unitID)}}}async _createInitialStateImpl(t){var c,l;const e=await this._localCacheService.loadOfflineData(this.unitID),s=(c=e==null?void 0:e.mutations)!=null?c:[],i=(l=e==null?void 0:e.awaitingChangeset)!=null?l:null,r=this.unitID;try{this._replayCachedMutations(i,s)}catch(u){this._logService.error(u)}const o=this._createHandler();if(t){const u=mt(this._injector,r,this._type,i,s,o);return u instanceof j?u._schedule():(u instanceof P||u instanceof B)&&u.resend(),u}return this._injector.createInstance(V,r,this._type,i,s,o)}_replayCachedMutations(t,e){var i,r;const s=this._compressMutationService.interceptor.fetchThroughInterceptors(this._compressMutationService.interceptor.getInterceptPoints().COMPRESS_MUTATION_APPLY);(i=s((t==null?void 0:t.mutations)||[],null))==null||i.forEach(o=>this._commandService.executeCommand(o.id,o.params)),(r=s(e||[],null))==null||r.forEach(o=>this._commandService.executeCommand(o.id,o.params))}};pe=Te([I(3,h.Inject(h.Injector)),I(4,h.Inject(M)),I(5,h.Inject(a.UniverPermissionService)),I(6,h.Inject(_.CompressMutationService)),I(7,h.Inject(a.LocaleService)),I(8,h.Inject(_.RevisionService)),I(9,a.ILogService),I(10,a.ICommandService),I(11,A.IMessageService),I(12,h.Optional(be))],pe);let Ae=class extends pe{constructor(n,t,e,s,i,r,o,c,l,u,g,S,f,C,E,y,O){super(n,t,e,s,i,r,o,c,l,C,E,y,O),this.unitID=n,this.type=t,this.session=e,this._docStateChangeManagerService=u,this._docTransformIMECacheService=g,this._docTransformSelectionsService=S,this._docSyncEditingCollabCursorService=f}_createHandler(){const n=super._createHandler();return n.onTransformIME=t=>this._docTransformIMECacheService.transformIMECache(t),n.onTransformSelections=t=>this._docTransformSelectionsService.transformSelections(t),n.onSyncEditingCollabCursor=t=>this._docSyncEditingCollabCursorService.syncEditingCollabCursor(t),n.onTransformRemoteChangesetByIMECache=t=>this._docTransformIMECacheService.transformRemoteChangeset(t),n}async _init(){const n=await super._init();return this._docStateChangeManagerService.docStateChange$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{if(t==null)return;const{unitId:e,redoState:s,commandId:i}=t;if(e!==this.unitID)return;const r={id:i,type:a.CommandType.MUTATION,params:{unitId:e,actions:s.actions,textRanges:null}};this._onLocalMutation(r)}),n}};Ae=Te([I(3,h.Inject(h.Injector)),I(4,h.Inject(M)),I(5,h.Inject(a.UniverPermissionService)),I(6,h.Inject(_.CompressMutationService)),I(7,h.Inject(a.LocaleService)),I(8,h.Inject(_.RevisionService)),I(9,h.Inject(N.DocStateChangeManagerService)),I(10,h.Inject(fe)),I(11,h.Inject(Ie)),I(12,h.Inject(We)),I(13,a.ILogService),I(14,a.ICommandService),I(15,A.IMessageService),I(16,h.Optional(be))],Ae);let ke=class extends pe{constructor(n,t,e,s,i,r,o,c,l,u,g,S,f,C){super(n,t,e,s,i,r,o,c,l,g,S,f,C),this.unitID=n,this.type=t,this.session=e,this._sheetTransformSelectionsService=u}_createHandler(){const n=super._createHandler();return n.onTransformSelections=t=>this._sheetTransformSelectionsService.transformSelections(t),n}async _init(){const n=await super._init();return this.disposeWithMe(this._commandService.onCommandExecuted((t,e)=>{if(t.type!==a.CommandType.MUTATION||e!=null&&e.fromCollab||e!=null&&e.onlyLocal)return;const s=t.params;if((s==null?void 0:s.unitId)!==this.unitID)return;const i=t,r=this._compressMutationService.interceptor.fetchThroughInterceptors(this._compressMutationService.interceptor.getInterceptPoints().COMPRESS_MUTATION_SEND)([i],null)||[i];this._onLocalMutation(r[0])})),n}};ke=Te([I(3,h.Inject(h.Injector)),I(4,h.Inject(M)),I(5,h.Inject(a.UniverPermissionService)),I(6,h.Inject(_.CompressMutationService)),I(7,h.Inject(a.LocaleService)),I(8,h.Inject(_.RevisionService)),I(9,h.Inject(Ce)),I(10,a.ILogService),I(11,a.ICommandService),I(12,A.IMessageService),I(13,h.Optional(be))],ke);const et=["purple300","jiqing500","verdancy600","red300","blue400","gold400"];class Ge extends a.Disposable{constructor(){super(...arguments);d(this,"_assignedColors",new Map);d(this,"_colorIndex",0)}assignAColorForMemberID(e){if(this._assignedColors.has(e))return this._assignedColors.get(e);const s=et[this._colorIndex];return this._colorIndex=(this._colorIndex+1)%et.length,this._assignedColors.set(e,s),s}}var is=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},X=(n,t)=>(e,s)=>t(e,s,n);const ns=300,rs=100,os=()=>{let n=[],t=!1;return e=>{n.push(e),t||(t=!0,setTimeout(()=>{n.forEach(s=>s()),n=[],t=!1}))}};let $e=class extends a.RxDisposable{constructor(t,e,s,i,r,o,c,l){super();d(this,"_online",!1);d(this,"_init",!1);d(this,"_cursorInfo$",new v.BehaviorSubject(new Map));d(this,"cursorInfo$",this._cursorInfo$.asObservable());d(this,"_roomMembers$",new v.BehaviorSubject([]));d(this,"roomMembers$",this._roomMembers$.pipe(v.debounceTime(ns)));d(this,"_updateLocalCursor",He((t,e)=>{const s={eventID:_.CollaborationEvent.UPDATE_CURSOR,data:{unitID:this.unitID,memberID:this._session.getMemberID(),selection:Ke.serializeRangeWithSheet(t,e.range)}};this._session.send(s,this.unitID)},rs));this.unitID=t,this._session=e,this._injector=s,this._colorAssignService=i,this._memberService=r,this._univerInstanceService=o,this._commandService=c,this._refRangeService=l}get cursorInfo(){return this._cursorInfo$.getValue()}get roomMembers(){return this._roomMembers$.getValue()}dispose(){super.dispose(),this._cursorInfo$.next(new Map),this._cursorInfo$.complete(),this._roomMembers$.next([]),this._roomMembers$.complete()}init(){this._init||(this._init=!0,this._session.sessionStatus$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{t===W.ONLINE?this._toggleOnline():this._toggleOffline()}),this._session.event$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{const e=t.eventID;e===_.CollaborationEvent.UPDATE_CURSOR&&this._onCursorUpdate(t),e===_.CollaborationEvent.USERS_LEAVE&&this._onCursorDelete(t)}),this._onRefRangeChange(),this.disposeWithMe(this._commandService.onCommandExecuted(t=>{if(this._online&&t.id===p.SetSelectionsOperation.id&&t.params.unitId===this.unitID){const e=t.params;this._updateLocalCursor(e.subUnitId,e.selections[0])}})))}_onCursorUpdate(t){var u,g;const{memberID:e,selection:s}=t.data,{sheetName:i,range:r}=Ke.deserializeRangeWithSheet(s),c={name:(g=(u=this._memberService.getMember(this.unitID,e))==null?void 0:u.name)!=null?g:"Unknown user",range:this._getMergeRange(i,r),sheetID:i,color:this._colorAssignService.assignAColorForMemberID(e),selection:s},l=this.cursorInfo;l.set(e,c),this._cursorInfo$.next(l)}_onCursorDelete(t){const{memberID:e}=t.data,s=this.cursorInfo;s.delete(e),this._cursorInfo$.next(s)}_getMergeRange(t,e){var i,r;const s=(r=(i=this._univerInstanceService.getUniverSheetInstance(this.unitID))==null?void 0:i.getSheetBySheetId(t))==null?void 0:r.getMergeData();return(s==null?void 0:s.find(o=>a.Rectangle.contains(o,e)))||e}_onRefRangeChange(){const t=new a.DisposableCollection,e=os(),s=()=>{t.dispose();const i=(r,o,c,l)=>{let u=[];switch(r.id){case p.EffectRefRangId.DeleteRangeMoveLeftCommandId:{u=p.handleDeleteRangeMoveLeft(r,l);break}case p.EffectRefRangId.DeleteRangeMoveUpCommandId:{u=p.handleDeleteRangeMoveUp(r,l);break}case p.EffectRefRangId.InsertColCommandId:{u=p.handleInsertCol(r,l);break}case p.EffectRefRangId.InsertRangeMoveDownCommandId:{u=p.handleInsertRangeMoveDown(r,l);break}case p.EffectRefRangId.InsertRangeMoveRightCommandId:{u=p.handleInsertRangeMoveRight(r,l);break}case p.EffectRefRangId.InsertRowCommandId:{u=p.handleInsertRow(r,l);break}case p.EffectRefRangId.MoveRangeCommandId:{u=p.handleMoveRange(r,l);break}case p.EffectRefRangId.RemoveColCommandId:{u=p.handleIRemoveCol(r,l);break}case p.EffectRefRangId.RemoveRowCommandId:{u=p.handleIRemoveRow(r,l);break}}const g=p.runRefRangeMutations(u,l),S=this.cursorInfo.get(o);if(S&&g){const f={...S,range:g};this.cursorInfo.set(o,f),e(()=>{const C=this._refRangeService.registerRefRange(g,E=>(C.dispose(),i(E,o,c,g)));t.add(C)})}return{redos:[],undos:[]}};this.cursorInfo.forEach((r,o)=>{const{range:c,sheetID:l}=r,u=this._refRangeService.registerRefRange(c,g=>(u.dispose(),i(g,o,l,c)));t.add(u)})};this.disposeWithMe(a.toDisposable(this._cursorInfo$.subscribe(()=>{s()})))}_toggleOnline(){var s,i;if(this._online=!0,((s=this._univerInstanceService.getFocusedUnit())==null?void 0:s.getUnitId())!==this.unitID)return;const e=(i=this._injector.get(p.SelectionManagerService).getSelections())==null?void 0:i[0];e&&this._updateLocalCursor(this._univerInstanceService.getCurrentUnitForType(a.UniverInstanceType.UNIVER_SHEET).getActiveSheet().getSheetId(),e)}_toggleOffline(){this._online=!1}};$e=is([X(2,h.Inject(h.Injector)),X(3,h.Inject(Ge)),X(4,h.Inject(G)),X(5,a.IUniverInstanceService),X(6,a.ICommandService),X(7,h.Inject(p.RefRangeService))],$e);var as=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},F=(n,t)=>(e,s)=>t(e,s,n);const cs=300,ls=100;let je=class extends a.RxDisposable{constructor(t,e,s,i,r,o,c,l,u){super();d(this,"_online",!1);d(this,"_init",!1);d(this,"_cursorInfo$",new v.BehaviorSubject(new Map));d(this,"cursorInfo$",this._cursorInfo$.asObservable());d(this,"_roomMembers$",new v.BehaviorSubject([]));d(this,"roomMembers$",this._roomMembers$.pipe(v.debounceTime(cs)));d(this,"_updateLocalCursor",He(t=>{const e={eventID:_.CollaborationEvent.UPDATE_CURSOR,data:{unitID:this.unitID,memberID:this._session.getMemberID(),selection:St(t)}};this._session.send(e,this.unitID)},ls));this.unitID=t,this._session=e,this._injector=s,this._colorAssignService=i,this._memberService=r,this._syncEditingCollabCursorService=o,this._transformService=c,this._univerInstanceService=l,this._commandService=u}get cursorInfo(){return this._cursorInfo$.getValue()}get roomMembers(){return this._roomMembers$.getValue()}dispose(){super.dispose(),this._cursorInfo$.next(new Map),this._cursorInfo$.complete(),this._roomMembers$.next([]),this._roomMembers$.complete()}init(){this._init||(this._init=!0,this._session.sessionStatus$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{t===W.ONLINE?this._toggleOnline():this._toggleOffline()}),this._session.event$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{const e=t.eventID;e===_.CollaborationEvent.UPDATE_CURSOR&&this._onCursorUpdate(t),e===_.CollaborationEvent.USERS_LEAVE&&this._onCursorDelete(t)}),this.disposeWithMe(this._commandService.onCommandExecuted(t=>{const e=t.params;e!=null&&this._online&&t.id===N.SetTextSelectionsOperation.id&&e.unitId===this.unitID&&e.isEditing===!1&&this._updateLocalCursor(e.ranges)})),this._syncEditingCollabCursorService.collabCursorState$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{if((t==null?void 0:t.unitID)!==this.unitID)return;const e={eventID:_.CollaborationEvent.UPDATE_CURSOR,data:t};this._onCursorUpdate(e)}),this.disposeWithMe(this._commandService.onCommandExecuted(t=>{if(t.params==null)return;const e=t.params;if(t.id!==N.RichTextEditingMutation.id||e.unitId!==this.unitID)return;const s={id:"doc.mutation.rich-text-editing",params:e},i=this.cursorInfo;for(const[r,o]of i){const c={id:"doc.mutation.rich-text-editing",params:{unitId:this.unitID,actions:[],textRanges:o.ranges}},l=this._transformService.transformMutation(s,c,!1);if(_.isTransformMutationFailure(l))throw l.error;i.set(r,{...o,ranges:l.m2Prime.params.textRanges})}queueMicrotask(()=>{this._cursorInfo$.next(i)})})))}_onCursorUpdate(t){var l,u;const{memberID:e,selection:s}=t.data,i=Jt(s),r=(u=(l=this._memberService.getMember(this.unitID,e))==null?void 0:l.name)!=null?u:"Unknown user",o={color:this._colorAssignService.assignAColorForMemberID(e),name:r,ranges:i},c=this.cursorInfo;c.set(e,o),this._cursorInfo$.next(c)}_onCursorDelete(t){const{memberID:e}=t.data,s=this.cursorInfo;s.delete(e),this._cursorInfo$.next(s)}_toggleOnline(){var i;if(this._online=!0,((i=this._univerInstanceService.getFocusedUnit())==null?void 0:i.getUnitId())!==this.unitID)return;const e=this._injector.get(N.TextSelectionManagerService).getSelections(),s=e==null?void 0:e.map(N.serializeTextRange);Array.isArray(s)&&s.length>0&&this._updateLocalCursor(s)}_toggleOffline(){this._online=!1}};je=as([F(2,h.Inject(h.Injector)),F(3,h.Inject(Ge)),F(4,h.Inject(G)),F(5,h.Inject(We)),F(6,_.ITransformService),F(7,a.IUniverInstanceService),F(8,a.ICommandService)],je);var hs=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},Me=(n,t)=>(e,s)=>t(e,s,n);let J=class extends a.RxDisposable{constructor(t,e,s){super();d(this,"_entities",new Map);d(this,"_entityInit$",new v.Subject);this._univerInstanceService=t,this._injector=e,this._collabSessionService=s,this._init()}dispose(){super.dispose(),this._entityInit$.complete(),this._entities.forEach(t=>t.dispose())}getCollabCursors$(t){return this._entities.has(t)?this._entities.get(t).cursorInfo$:this._entityInit$.pipe(v.filter(e=>e.unitID===t),v.switchMap(e=>e.cursorInfo$))}_init(){this._univerInstanceService.getTypeOfUnitAdded$(a.UniverInstanceType.UNIVER_SHEET).pipe(v.takeUntil(this.dispose$)).subscribe(async t=>{const e=t.getUnitId(),s=await this._startSheetCollabCursor(e);this._entityInit$.next(s),this._entities.set(e,s)}),this._univerInstanceService.getTypeOfUnitAdded$(a.UniverInstanceType.UNIVER_DOC).pipe(v.takeUntil(this.dispose$)).pipe(v.filter(t=>!t.getUnitId().startsWith("__"))).subscribe(async t=>{const e=t.getUnitId(),s=await this._startDocCollabCursor(e);this._entityInit$.next(s),this._entities.set(e,s)}),v.merge(this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_DOC),this._univerInstanceService.getTypeOfUnitDisposed$(a.UniverInstanceType.UNIVER_SHEET)).pipe(v.takeUntil(this.dispose$)).subscribe(t=>{const e=t.getUnitId(),s=this._entities.get(e);s&&(s.dispose(),this._entities.delete(e))})}async _startSheetCollabCursor(t){const e=await this._collabSessionService.requireSession(t),s=this._injector.createInstance($e,t,e);return s.init(),s}async _startDocCollabCursor(t){const e=await this._collabSessionService.requireSession(t),s=this._injector.createInstance(je,t,e);return s.init(),s}};J=hs([a.OnLifecycle(a.LifecycleStages.Starting,J),Me(0,a.IUniverInstanceService),Me(1,h.Inject(h.Injector)),Me(2,h.Inject(exports.CollaborationSessionService))],J);const ue=20,tt=200,De=4,us=5;function _s(n,t){let{radius:e,width:s,height:i}=t;e=e!=null?e:0,s=s!=null?s:30,i=i!=null?i:30;let r=0,o=0,c=0;r=o=c=Math.min(e,s/2,i/2),n.beginPath(),n.moveTo(r,0),n.lineTo(s-o,0),n.arc(s-o,o,o,Math.PI*3/2,0,!1),n.lineTo(s,i-c),n.arc(s-c,i-c,c,0,Math.PI/2,!1),n.lineTo(0,i),n.lineTo(0,r),n.arc(r,r,r,Math.PI,Math.PI*3/2,!1),n.closePath(),t.fill&&(n.save(),n.fillStyle=t.fill,t.fillRule==="evenodd"?n.fill("evenodd"):n.fill(),n.restore())}class Re extends R.Shape{constructor(e,s){super(e,s);d(this,"color");d(this,"text");this.color=s==null?void 0:s.color,this.text=s==null?void 0:s.text}static drawWith(e,s){const{text:i,color:r}=s;e.save(),e.font="bold 13px Source Han Sans CN";const o=e.measureText(i).width,c=Math.min(o+2*De,tt);_s(e,{height:ue,radius:4,width:c,fill:r,evented:!1}),e.fillStyle="#FFF";const l=De,u=ue-us,g=tt-2*De;if(o>g){let S="",f=0;for(const C of i){const E=e.measureText(C).width;if(f+E<=g-e.measureText("...").width)S+=C,f+=E;else{S+="...";break}}e.fillText(S,l,u)}else e.fillText(i,l,u);e.restore()}_draw(e){Re.drawWith(e,this)}}const ds=1,gs=1.5;class Ss extends R.Shape{constructor(e,s){super(e,s);d(this,"_color");d(this,"_hovered",!1);d(this,"_range");d(this,"_name","");d(this,"_labelPosition","top");s&&this.setShapeProps(s),this.onPointerEnterObserver.add(()=>this.setShapeProps({hovered:!0})),this.onPointerLeaveObserver.add(()=>this.setShapeProps({hovered:!1}))}setShapeProps(e){var s,i,r,o,c;this._color=(s=e.color)!=null?s:this._color,this._hovered=(i=e.hovered)!=null?i:this._hovered,this._range=(r=e.range)!=null?r:this._range,this._name=(o=e.name)!=null?o:this._name,this._labelPosition=(c=e.labelPosition)!=null?c:this._labelPosition,this.transformByState({width:e.width,height:e.height})}onMouseMove(e){const{row:s,column:i}=e;if(s>=this._range.startRow&&s<=this._range.endRow&&i>=this._range.startColumn&&i<=this._range.endColumn){this.setShapeProps({hovered:!0});return}this.setShapeProps({hovered:!1})}triggerDblclick(e){return!1}_draw(e){R.Rect.drawWith(e,{width:this.width,height:this.height,strokeWidth:gs,stroke:this._color,evented:!1}),this._hovered&&(e.save(),e.transform(1,0,0,1,this.width,this._labelPosition==="bottom"?0:-ue),Re.drawWith(e,{text:this._name,color:this._color}),e.restore())}}var vs=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},ie=(n,t)=>(e,s)=>t(e,s,n);let ge=class extends a.RxDisposable{constructor(t,e,s,i,r){super();d(this,"_cursors",new Set);d(this,"_lastPointer",null);this._collabCursorController=t,this._univerInstanceService=e,this._renderManagerService=s,this._sheetSkeletonManagerService=i,this._themeService=r,this._init()}_init(){this._sheetSkeletonManagerService.currentSkeleton$.pipe(T.takeUntil(this.dispose$),T.switchMap(t=>{if(t){const e=t.sheetId;return v.combineLatest(this._collabCursorController.getCollabCursors$(t.unitId),this._themeService.currentTheme$).pipe(T.map(([s,i])=>{const r=new Map;return s.forEach((o,c)=>{if(o.sheetID===e){const l={...o};l.color=i[o.color],r.set(c,l)}}),{skeleton:t,cursors:r}}))}return v.of({skeleton:null,cursors:new Map})})).subscribe(({skeleton:t,cursors:e})=>{this._removeCollabCursors(),t&&this._updateCollabCursors(t,e)}),this._sheetSkeletonManagerService.currentSkeleton$.subscribe(t=>{if(t==null)return;const{unitId:e,skeleton:s}=t,i=this._renderManagerService.getRenderById(e);if(i==null)return;const{scene:r}=i;r.onPointerMoveObserver.add(He(o=>{var O,H;const{offsetX:c,offsetY:l}=o,{x:u,y:g}=r.getRelativeCoord(R.Vector2.FromArray([c,l])),{scaleX:S,scaleY:f}=r.getAncestorScale(),C=r.getViewport(ae.VIEWPORT_KEY.VIEW_MAIN),E=r.getScrollXYByRelativeCoords(R.Vector2.FromArray([u,g]),C),y=s.getCellPositionByOffset(c,l,S,f,E);((O=this._lastPointer)==null?void 0:O.column)===y.column&&((H=this._lastPointer)==null?void 0:H.row)===y.row||this._cursors.forEach(Z=>{Z.onMouseMove(y)})},100))})}_updateCollabCursors(t,e){var c;const s=(c=this._sheetSkeletonManagerService.getCurrent())==null?void 0:c.skeleton;if(!s)return;const i=this._getSheetObject();if(!i)return;this._cursors.forEach(l=>{l.makeDirty()});const{scene:r}=i,o=ms(Array.from(e.values())).map(l=>{const{color:u,range:g,name:S,selection:f,sheetID:C}=l,{startColumn:E,startRow:y,endColumn:O,endRow:H}=g,Z=ae.getCoordByCell(y,E,r,s),ye=ae.getCoordByCell(H,O,r,s),{columnHeaderHeightAndMarginTop:Q}=s,{startX:ee,startY:Oe}=Z,{endX:Rt,endY:yt}=ye,Ot=Rt-ee,Mt=yt-Oe,Dt={labelPosition:Oe-Q>=ue?"top":"bottom",sheetID:C,range:g,color:u,name:S,selection:f,left:ee,top:Oe,width:Ot,height:Mt,evented:!1};return new Ss(S,Dt)});r.addObjects(o,ds),this._cursors=new Set(o)}_removeCollabCursors(){var t;(t=this._cursors)==null||t.forEach(e=>e.dispose())}_getSheetObject(){return ae.getSheetObject(this._univerInstanceService,this._renderManagerService)}};ge=vs([a.OnLifecycle(a.LifecycleStages.Steady,ge),ie(0,h.Inject(J)),ie(1,a.IUniverInstanceService),ie(2,R.IRenderManagerService),ie(3,h.Inject(ae.SheetSkeletonManagerService)),ie(4,h.Inject(a.ThemeService))],ge);function ms(n){const t=new Map;return n.forEach(e=>{if(t.has(e.selection)){const s=t.get(e.selection);s.name+=`, ${e.name}`}else t.set(e.selection,e)}),Array.from(t.values())}var L=function(){return L=Object.assign||function(n){for(var t,e=1,s=arguments.length;e<s;e++){t=arguments[e];for(var i in t)Object.prototype.hasOwnProperty.call(t,i)&&(n[i]=t[i])}return n},L.apply(this,arguments)},fs=function(n,t){var e={};for(var s in n)Object.prototype.hasOwnProperty.call(n,s)&&t.indexOf(s)<0&&(e[s]=n[s]);if(n!=null&&typeof Object.getOwnPropertySymbols=="function")for(var i=0,s=Object.getOwnPropertySymbols(n);i<s.length;i++)t.indexOf(s[i])<0&&Object.prototype.propertyIsEnumerable.call(n,s[i])&&(e[s[i]]=n[s[i]]);return e},Ye=w.forwardRef(function(n,t){var e=n.icon,s=n.id,i=n.className,r=n.extend,o=fs(n,["icon","id","className","extend"]),c="univerjs-icon univerjs-icon-".concat(s," ").concat(i||"").trim(),l=w.useRef("_".concat(ps()));return ft(e,"".concat(s),{defIds:e.defIds,idSuffix:l.current},L({ref:t,className:c},o),r)});function ft(n,t,e,s,i){return w.createElement(n.tag,L(L({key:t},Is(n,e,i)),s),(Cs(n,e).children||[]).map(function(r,o){return ft(r,"".concat(t,"-").concat(n.tag,"-").concat(o),e,void 0,i)}))}function Is(n,t,e){var s=L({},n.attrs);e!=null&&e.colorChannel1&&s.fill==="colorChannel1"&&(s.fill=e.colorChannel1);var i=t.defIds;return!i||i.length===0||(n.tag==="use"&&s["xlink:href"]&&(s["xlink:href"]=s["xlink:href"]+t.idSuffix),Object.entries(s).forEach(function(r){var o=r[0],c=r[1];typeof c=="string"&&(s[o]=c.replace(/url\(#(.*)\)/,"url(#$1".concat(t.idSuffix,")")))})),s}function Cs(n,t){var e,s=t.defIds;return!s||s.length===0?n:n.tag==="defs"&&(!((e=n.children)===null||e===void 0)&&e.length)?L(L({},n),{children:n.children.map(function(i){return typeof i.attrs.id=="string"&&s&&s.indexOf(i.attrs.id)>-1?L(L({},i),{attrs:L(L({},i.attrs),{id:i.attrs.id+t.idSuffix})}):i})}):n}function ps(){return Math.random().toString(36).substring(2,8)}Ye.displayName="UniverIcon";var Es={tag:"svg",attrs:{fill:"none",viewBox:"0 0 16 16",width:"1em",height:"1em"},children:[{tag:"mask",attrs:{id:"mask0_102_585",style:{maskType:"alpha"},width:16,height:16,x:0,y:0,maskUnits:"userSpaceOnUse"},children:[{tag:"path",attrs:{fill:"#D9D9D9",d:"M0 0H16V16H0z"}}]},{tag:"g",attrs:{fill:"currentColor",mask:"url(#mask0_102_585)"},children:[{tag:"path",attrs:{d:"M8.00011 11.7216C7.64665 11.7216 7.36011 11.435 7.36011 11.0816V2.76158C7.36011 2.40812 7.64665 2.12158 8.00011 2.12158 8.35357 2.12158 8.64011 2.40812 8.64011 2.76158V11.0816C8.64011 11.435 8.35357 11.7216 8.00011 11.7216zM8.00008 13.8783C8.46032 13.8783 8.83342 13.5052 8.83342 13.045 8.83342 12.5847 8.46032 12.2116 8.00008 12.2116 7.53985 12.2116 7.16675 12.5847 7.16675 13.045 7.16675 13.5052 7.53985 13.8783 8.00008 13.8783zM9.43991 3.3083V4.6566C11.1747 4.93531 12.8439 5.72115 14.2082 7.01405 14.4754 7.26731 14.8974 7.25598 15.1506 6.98873 15.4039 6.72149 15.3926 6.29953 15.1253 6.04626 13.5035 4.50928 11.5069 3.59665 9.43991 3.3083zM2.3565 6.52137C3.60481 5.51948 5.05771 4.89789 6.55991 4.65657V3.30842C4.7603 3.55961 3.014 4.284 1.52191 5.48155 1.3003 5.65943 1.08439 5.84768.874838 6.04627.607592 6.29953.59626 6.72149.849526 6.98873 1.10279 7.25598 1.52475 7.26731 1.79199 7.01405 1.97498 6.84063 2.16333 6.67643 2.3565 6.52137zM2.86201 8.33667C3.91262 7.28606 5.2049 6.62442 6.55991 6.35175V7.71826C5.55037 7.96981 4.59408 8.49022 3.80482 9.27947 3.54447 9.53982 3.12236 9.53982 2.86201 9.27947 2.60166 9.01912 2.60166 8.59701 2.86201 8.33667zM9.43991 7.71818V6.35169C10.795 6.62431 12.0875 7.28597 13.1382 8.33667 13.3985 8.59701 13.3985 9.01912 13.1382 9.27947 12.8778 9.53982 12.4557 9.53982 12.1953 9.27947 11.406 8.49013 10.4496 7.9697 9.43991 7.71818zM4.86201 10.5082C5.35689 10.0134 5.93957 9.65979 6.55991 9.44753V10.8951C6.28821 11.0374 6.03315 11.2227 5.80482 11.451 5.54447 11.7114 5.12236 11.7114 4.86201 11.451 4.60166 11.1907 4.60166 10.7686 4.86201 10.5082zM9.43991 10.8949V9.44741C10.0604 9.65966 10.6432 10.0133 11.1382 10.5082 11.3985 10.7686 11.3985 11.1907 11.1382 11.451 10.8778 11.7114 10.4557 11.7114 10.1953 11.451 9.96691 11.2226 9.71174 11.0372 9.43991 10.8949z"}}]}]},It=w.forwardRef(function(n,t){return w.createElement(Ye,Object.assign({},n,{id:"off-line-single",ref:t,icon:Es}))});It.displayName="OffLineSingle";var bs={tag:"svg",attrs:{fill:"none",viewBox:"0 0 16 16",width:"1em",height:"1em"},children:[{tag:"mask",attrs:{id:"mask0_102_580",style:{maskType:"alpha"},width:16,height:16,x:0,y:0,maskUnits:"userSpaceOnUse"},children:[{tag:"path",attrs:{fill:"#D9D9D9",d:"M0 0H16V16H0z"}}]},{tag:"g",attrs:{fill:"currentColor",mask:"url(#mask0_102_580)",fillRule:"evenodd",clipRule:"evenodd"},children:[{tag:"path",attrs:{d:"M5.82613 4.56746C5.40036 5.04236 5.18674 5.65314 5.02643 6.21425C4.94606 6.49553 4.68897 6.68945 4.39644 6.68945C4.17409 6.68945 3.56092 6.78651 3.0238 7.12221C2.52284 7.43531 2.10324 7.93892 2.10324 8.81885C2.10324 9.60442 2.39454 10.0131 2.72844 10.2503C3.09823 10.5131 3.60322 10.6206 4.06884 10.6206C4.43069 10.6206 4.72404 10.914 4.72404 11.2758C4.72404 11.6377 4.43069 11.931 4.06884 11.931C3.44246 11.931 2.63705 11.7929 1.96945 11.3185C1.26595 10.8187 0.792847 9.99887 0.792847 8.81885C0.792847 7.40558 1.51984 6.5169 2.32929 6.011C2.8676 5.67455 3.44845 5.50028 3.89776 5.42544C4.07573 4.89085 4.35413 4.2463 4.85044 3.69271C5.51609 2.95026 6.5174 2.43066 8.00003 2.43066C9.27898 2.43066 10.2502 2.7993 10.9548 3.3781C11.5184 3.84106 11.881 4.41324 12.1008 4.9709C12.1429 4.98097 12.1875 4.99222 12.2342 5.00477C12.549 5.08928 12.9754 5.23648 13.408 5.48878C14.2932 6.00515 15.2072 6.97409 15.2072 8.65505C15.2072 9.79541 14.8194 10.6501 14.1525 11.2059C13.5065 11.7442 12.6838 11.931 11.9312 11.931C11.5694 11.931 11.276 11.6377 11.276 11.2758C11.276 10.914 11.5694 10.6206 11.9312 10.6206C12.4891 10.6206 12.9767 10.4799 13.3136 10.1992C13.6294 9.93602 13.8968 9.48028 13.8968 8.65505C13.8968 7.55142 13.3367 6.96426 12.7477 6.62068C12.4431 6.443 12.1325 6.33426 11.8944 6.27034C11.7766 6.23871 11.6799 6.21893 11.6151 6.20737C11.5828 6.2016 11.5587 6.19792 11.5442 6.19585L11.53 6.19391L11.5302 6.19393L11.5307 6.19398C11.2667 6.16442 11.0466 5.97834 10.9736 5.72285C10.8382 5.24885 10.5726 4.75996 10.123 4.39067C9.68107 4.02762 9.01427 3.74106 8.00003 3.74106C6.86186 3.74106 6.22518 4.12236 5.82613 4.56746ZM11.53 6.19391L11.5294 6.19384L11.5286 6.19374C11.5284 6.19372 11.5288 6.19377 11.53 6.19391Z"}},{tag:"path",attrs:{d:"M11.0302 9.12626C11.3127 9.35231 11.3585 9.76463 11.1325 10.0472L8.51171 13.3232C8.40173 13.4606 8.24107 13.5481 8.06592 13.5658C7.89077 13.5835 7.71587 13.5299 7.58063 13.4172L5.61504 11.7792C5.33705 11.5476 5.2995 11.1344 5.53115 10.8564C5.7628 10.5785 6.17595 10.5409 6.45393 10.7725L7.90602 11.9826L10.1093 9.22859C10.3353 8.94603 10.7476 8.90021 11.0302 9.12626Z"}}]}]},Ct=w.forwardRef(function(n,t){return w.createElement(Ye,Object.assign({},n,{id:"on-line-single",ref:t,icon:bs}))});Ct.displayName="OnLineSingle";const Ts="univer-online-status-icon",Rs="univer-online-status-title",ys="univer-online-status",Os="univer-online",Ms="univer-offline",ne={onlineStatusIcon:Ts,onlineStatusTitle:Rs,onlineStatus:ys,online:Os,offline:Ms};function Ds(n){switch(n){case D.OFFLINE:return"collabStatus.offline";case D.CONFLICT:return"collabStatus.conflict";case D.FETCH_MISS:return"collabStatus.fetchMiss";case D.NOT_COLLAB:return"collabStatus.notCollab";case D.PENDING:case D.AWAITING:case D.AWAITING_WITH_PENDING:return"collabStatus.syncing";case D.SYNCED:return"collabStatus.synced"}}function ws(n){const t=A.useObservable(n.status$,D.NOT_COLLAB),e=rt.useDependency(a.LocaleService),s=t!==D.OFFLINE,i=e.t(Ds(t)),r=Lt(ne.onlineStatus,{[ne.online]:s,[ne.offline]:!s}),o=s?w.createElement(Ct,null):w.createElement(It,null);return w.createElement("div",{className:r},w.createElement("div",{className:ne.onlineStatusIcon},o),w.createElement("div",{className:ne.onlineStatusTitle},i))}var Us=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},_e=(n,t)=>(e,s)=>t(e,s,n);let Se=class extends a.Disposable{constructor(t,e,s,i){super();d(this,"_status$",new v.BehaviorSubject(D.NOT_COLLAB));this._uiController=t,this._univerInstanceService=e,this._injector=s,this._collaborationController=i,this._mountOnlineHint(),this._initStatusListener()}_mountOnlineHint(){this.disposeWithMe(this._uiController.registerComponent(A.DesktopUIPart.HEADER_MENU,()=>rt.connectInjector(Ls({status$:this._status$.asObservable()}),this._injector)))}_initStatusListener(){this.disposeWithMe(a.toDisposable(this._univerInstanceService.focused$.pipe(v.switchMap(()=>{const t=this._univerInstanceService.getFocusedUnit();return t?this._collaborationController.getCollabEntity$(t.getUnitId()):v.of(null)}),v.switchMap(t=>t?t.status$:v.of(D.NOT_COLLAB))).subscribe(t=>{this._status$.next(t)})))}};Se=Us([a.OnLifecycle(a.LifecycleStages.Starting,Se),_e(0,A.IUIController),_e(1,a.IUniverInstanceService),_e(2,h.Inject(h.Injector)),_e(3,h.Inject(exports.CollaborationController))],Se);function Ls(n){const{status$:t}=n;return function(){return w.createElement(ws,{status$:t})}}const pt=h.createIdentifier("uni.network.url-service");var Ns=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},z=(n,t)=>(e,s)=>t(e,s,n);let ce=class extends a.RxDisposable{constructor(n,t,e,s,i,r){super(),this._urlService=n,this._logService=t,this._commandService=e,this._localCacheService=s,this._snapshotService=i,r?r==null||r.whenReady().then(()=>this._init()):(this._logService.debug("[DataLoaderController]","No remote instance service injected. May not syncing edits to the web worker."),this._init())}async _init(){const n=this._urlService.getParam("unit"),t=this._urlService.getParam("type");if(!n||!t){this._logService.debug("[DataLoaderController]","No unitID or type in URL. Will not load files from remote address.");return}switch(Number(t)){case $.UNIVER_SHEET:{const e=await this._loadSheet(n);this._setupSubUnitSync(e);break}case $.UNIVER_DOC:{await this._loadDoc(n);break}default:{this._logService.error("[DataLoaderController]","Unknown type in URL. Will not load files from remote address.");break}}}async _setupSubUnitSync(n){await this._updateSubUnitFromURLParams(n),n.activeSheet$.pipe(v.takeUntil(this.dispose$)).subscribe(t=>{t&&this._updateURLWithCurrentState(t)}),this._urlService.urlChange$.pipe(v.takeUntil(this.dispose$)).subscribe(()=>this._updateSubUnitFromURLParams(n))}_updateURLWithCurrentState(n,t=!1){const e=this._urlService.getParam("subunit");n.getSheetId()!==e&&this._urlService.setParam("subunit",n.getSheetId(),t)}async _updateSubUnitFromURLParams(n){const t=this._urlService.getParam("subunit");if(!t||!n.getSheetBySheetId(t)){this._updateURLWithCurrentState(n.getActiveSheet(),!0);return}n.getActiveSheet().getSheetId()!==t&&await this._commandService.executeCommand(p.SetWorksheetActivateCommand.id,{unitId:n.getUnitId(),subUnitId:t})}async _loadSheet(n){let t=0;const e=await this._localCacheService.loadOfflineData(n);return e&&(e.awaitingChangeset||e.mutations.length!==0)&&(t=e.rev),t===0&&this._logService.debug("[DataLoaderController]","fetching the latest document from the server."),this._snapshotService.loadSheet(n,t)}async _loadDoc(n){let t=0;const e=await this._localCacheService.loadOfflineData(n);return e&&(e.awaitingChangeset||e.mutations.length!==0)&&(t=e.rev),t===0&&this._logService.debug("[DataLoaderController]","fetching the latest document from the server."),this._snapshotService.loadDoc(n,t)}};ce=Ns([a.OnLifecycle(a.LifecycleStages.Starting,ce),z(0,pt),z(1,a.ILogService),z(2,a.ICommandService),z(3,h.Inject(M)),z(4,h.Inject(_.SnapshotService)),z(5,h.Optional(Nt.IRemoteInstanceService))],ce);var As=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},st=(n,t)=>(e,s)=>t(e,s,n);const ks="DEFAULT_FILE_NAME",$s="Univer";let ve=class extends a.Disposable{constructor(n,t){super(),this._univerInstanceService=n,this._configService=t,this._init()}_init(){this.disposeWithMe(a.toDisposable(this._univerInstanceService.focused$.subscribe(()=>{var e;const n=this._univerInstanceService.getFocusedUnit();let t=(e=this._configService.getConfig(ks))!=null?e:$s;n instanceof a.Workbook&&(t=n.name),document.title=t})))}};ve=As([a.OnLifecycle(a.LifecycleStages.Ready,ve),st(0,a.IUniverInstanceService),st(1,a.IConfigService)],ve);const js={collabStatus:{fetchMiss:"正在同步服务端数据...",conflict:"编辑冲突",notCollab:"本地文件",synced:"已保存",syncing:"保存中...",offline:"编辑将在本地保存"},session:{"connection-failed":"连接失败,请检查你的网络","will-retry":"连接失败,将在一会儿之后重试","room-full":"协同房间已满,你的编辑将在本地保存","collaboration-timeout":"服务器未响应你的协同请求,你的编辑将在本地保存"},conflict:{title:"协同冲突",content:"你的本地文档和服务器的文档存在冲突。请在别处保存你的本地编辑,本地编辑将在刷新页面后丢弃。"},collaboration:{"single-unit":{warning:"你在另一个标签页打开了同一个文件。为了避免数据丢失,这个标签页的编辑行为将会被限制。"}},auth:{needGotoLoginAlert:"你的登录已过期,点击确认重新登陆,点击取消去保存你的本地编辑。"}},Et=js;var Ps=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},it=(n,t)=>(e,s)=>t(e,s,n);const bt="SNAPSHOT_SERVER_URL_KEY",xs="/universer-api/snapshot";let Pe=class{constructor(n,t){this._configService=n,this._httpService=t}async getUnitOnRev(n,t){var g;const{unitID:e,type:s,revision:i=0}=t,o=`${this._getAPIPrefixPath()}/${s}/unit/${e}/rev/${i===1?0:i}`,l=(await this._httpService.get(o)).body,u=(g=l.snapshot)==null?void 0:g.workbook;if(u){const S=u==null?void 0:u.originalMeta,f=a.textEncoder.encode(a.b64DecodeUnicode(S));u.originalMeta=f,Object.entries(u.sheets).forEach(([,C])=>{const E=C.originalMeta,y=a.textEncoder.encode(a.b64DecodeUnicode(E));C.originalMeta=y})}return l}async getSheetBlock(n,t){const{unitID:e,type:s,blockID:i}=t,o=`${this._getAPIPrefixPath()}/${s}/unit/${e}/block/${i}`;return(await this._httpService.get(o)).body}async fetchMissingChangesets(n,t){const{unitID:e,type:s,from:i,to:r}=t,c=`${this._getAPIPrefixPath()}/${s}/unit/${e}/fetchmissing?from=${i}&to=${r}`;return(await this._httpService.get(c)).body}_getAPIPrefixPath(){var n;return(n=this._configService.getConfig(bt))!=null?n:xs}async getResourcesRequest(n,t){const e=`/universer-api/snapshot/${t.type}/unit/${t.unitID}/resources`;return(await this._httpService.get(e,{params:{resourceId:JSON.stringify(t.resourceIDs)}})).body}saveSnapshot(){throw new Error("This method should not be called on the client side!")}saveSheetBlock(){throw new Error("This method should not be called on the client side!")}saveChangeset(){throw new Error("This method should not be called on the client side!")}};Pe=Ps([it(0,a.IConfigService),it(1,h.Inject(k.HTTPService))],Pe);var Hs=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},re=(n,t)=>(e,s)=>t(e,s,n);let xe=class extends a.LocalUndoRedoService{constructor(n,t,e,s,i){super(n,t,e),this._transformService=s,this._logService=i}transformUndoRedo(n,t){const e=this._getUndoStack(n);if(e)try{const i=this._transformStack(e,t);this._substituteUndoStack(n,i)}catch(i){this._logService.error("[CollaborationUndoRedoService]",i),this._clearUndo(n)}const s=this._getRedoStack(n);if(s)try{const i=this._transformStack(s,t);this._substituteRedoStack(n,i)}catch(i){this._logService.error(i),this._clearRedo(n)}}_clearUndo(n){const t=this._getUndoStack(n);t&&(t.length=0,this._updateStatus())}_clearRedo(n){const t=this._getRedoStack(n);t&&(t.length=0,this._updateStatus())}_substituteUndoStack(n,t){this._undoStacks.set(n,t),this._updateStatus()}_substituteRedoStack(n,t){this._redoStacks.set(n,t),this._updateStatus()}_transformStack(n,t){const e=[];let s=t,i=t;for(let r=n.length-1;r>=0;r--){const{unitID:o,undoMutations:c,redoMutations:l}=n[r],u=this._transformService.transformMutationsWithChangeset(s,c),g=this._transformService.transformMutationsWithChangeset(i,l);if(_.isTransformMutationsWithChangesetFailure(u)||_.isTransformMutationsWithChangesetFailure(g)){this._logService.error("[CollaborationUndoRedoService]","transformStack failed!",u,g);break}s=u.c1Prime,i=g.c1Prime,e.push({unitID:o,undoMutations:u.m2Prime,redoMutations:g.m2Prime})}return e.reverse()}};xe=Hs([re(0,a.IUniverInstanceService),re(1,a.ICommandService),re(2,a.IContextService),re(3,_.ITransformService),re(4,a.ILogService)],xe);class Bs extends a.RxDisposable{constructor(){super();d(this,"urlChange$");this.urlChange$=v.fromEvent(window,"popstate").pipe(v.takeUntil(this.dispose$),v.shareReplay(1),v.mapTo(void 0))}setParam(e,s,i=!1){const r=new URL(window.location.href);r.searchParams.set(e,s),i?window.history.replaceState("","",r.toString()):window.history.pushState("","",r.toString())}removeParam(e,s=!1){const i=new URL(window.location.href);i.searchParams.delete(e),s?window.history.replaceState("","",i.toString()):window.history.pushState("","",i.toString())}getParam(e){var i;return(i=new URL(window.location.href).searchParams.get(e))!=null?i:void 0}}const we="collab-text-anchor-",Vs="collab-text-range-",de=6,Fs=1.5,Ue=4,Ws=1.5,Gs="rgba(255, 255, 255, 0.01)";class Ys{constructor(t,e,s,i){d(this,"_shapes",[]);d(this,"_anchor",null);d(this,"_textBubble",null);d(this,"_anchorDot",null);d(this,"_hideTimer",null);d(this,"_eventUnsubscribe",null);this._cursor=t,this._scene=e,this._docSkeleton=s,this._document=i,this._render()}set _hover(t){t?(this._anchorDot&&this._anchorDot.hide(),this._textBubble&&this._textBubble.show()):(this._anchorDot&&this._anchorDot.show(),this._textBubble&&this._textBubble.hide())}dispose(){for(const t of this._shapes)t.dispose();this._textBubble&&this._textBubble.dispose(),this._anchorDot&&this._anchorDot.dispose(),this._anchor&&this._anchor.dispose(),this._eventUnsubscribe&&this._eventUnsubscribe()}_render(){const{_docSkeleton:t,_document:e}=this,{color:s,name:i,ranges:r}=this._cursor,o=e.getOffsetConfig(),{docsLeft:c,docsTop:l}=o,u=new R.NodePositionConvertToCursor(o,t);for(const{startOffset:g,endOffset:S,collapsed:f,isActive:C}of r){const E=t.findNodePositionByCharIndex(g),y=t.findNodePositionByCharIndex(S);if(C){const{contentBoxPointGroup:O}=u.getRangePointData(y,y);if(O.length===0)continue;this._drawAnchor(s,O,c,l,i),this._eventUnsubscribe=this._handleHover()}if(!f){const{contentBoxPointGroup:O}=u.getRangePointData(E,y);if(O.length===0)continue;this._drawRange(s,O,c,l)}}}_drawAnchor(t,e,s,i,r){const o=this._getAnchorBounding(e),{left:c,top:l,height:u}=o,g=this._getScale(),S=Ws/g,f=new R.Rect(we+a.Tools.generateRandomId(de),{left:c+s-S,top:l+i,height:u,width:Fs,fill:t||R.getColor(a.COLORS.black,0),strokeWidth:S,stroke:Gs,evented:!0});this._anchor=f,this._scene.addObject(f,R.TEXT_RANGE_LAYER_INDEX);const C=new R.Rect(we+a.Tools.generateRandomId(de),{left:c+s-S,top:l+i-Ue/2,height:Ue,width:Ue,fill:t||R.getColor(a.COLORS.black,0),strokeWidth:0,stroke:t||R.getColor(a.COLORS.black,0),evented:!1});this._anchorDot=C,this._scene.addObject(C,R.TEXT_RANGE_LAYER_INDEX);const E=new Re(we+a.Tools.generateRandomId(de),{left:c+s-S,top:l+i-ue,text:r,color:t});this._textBubble=E,this._scene.addObject(E,R.TEXT_RANGE_LAYER_INDEX),this._hover=!1}_handleHover(){const t=this._anchor.onPointerEnterObserver.add(()=>{this._hover=!0}),e=this._anchor.onPointerLeaveObserver.add(()=>{this._hideTimer&&clearTimeout(this._hideTimer),this._hideTimer=setTimeout(()=>{this._hover=!1},2e3)});return()=>{var s,i;(s=this._anchor)==null||s.onPointerEnterObserver.remove(t),(i=this._anchor)==null||i.onPointerLeaveObserver.remove(e)}}_drawRange(t,e,s,i){const o=new a.ColorKit(t).setAlpha(.2).toRgbString(),c=new R.RegularPolygon(Vs+a.Tools.generateRandomId(de),{pointsGroup:e,fill:o||R.getColor(a.COLORS.black,.2),left:s,top:i,evented:!1,debounceParentDirty:!1});this._shapes.push(c),this._scene.addObject(c,R.TEXT_RANGE_LAYER_INDEX)}_getAnchorBounding(t){const e=t[0],s=e[0],i=e[2],{x:r,y:o}=s,{x:c,y:l}=i;return{left:r,top:o,width:c-r,height:l-o}}_getScale(){const{scaleX:t,scaleY:e}=this._scene.getAncestorScale();return Math.max(t,e)}}var Ks=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},oe=(n,t)=>(e,s)=>t(e,s,n);let me=class extends a.RxDisposable{constructor(t,e,s,i,r){super();d(this,"_cursors",[]);this._collabCursorController=t,this._univerInstanceService=e,this._renderManagerService=s,this._docSkeletonManagerService=i,this._themeService=r,this._init()}_init(){this._docSkeletonManagerService.currentSkeleton$.pipe(T.takeUntil(this.dispose$),T.switchMap(t=>{if(t){const{unitId:e}=t;return v.combineLatest(this._collabCursorController.getCollabCursors$(e),this._themeService.currentTheme$).pipe(T.map(([s,i])=>({skeleton:t,cursors:[...s.values()].flatMap(r=>({...r,color:i[r.color]}))})))}return v.of({skeleton:null,cursors:[]})})).subscribe(({skeleton:t,cursors:e})=>{this._removeCollabCursors(),t&&this._updateCollabCursors(t.skeleton,e)})}_updateCollabCursors(t,e){const s=this._getDocObject();if(s==null)return;const{scene:i,document:r}=s,o=e.map(c=>new Ys(c,i,t,r));this._cursors=o}_removeCollabCursors(){this._cursors.forEach(t=>t.dispose()),this._cursors=[]}_getDocObject(){return N.getDocObject(this._univerInstanceService,this._renderManagerService)}};me=Ks([a.OnLifecycle(a.LifecycleStages.Steady,me),oe(0,h.Inject(J)),oe(1,a.IUniverInstanceService),oe(2,R.IRenderManagerService),oe(3,h.Inject(N.DocSkeletonManagerService)),oe(4,h.Inject(a.ThemeService))],me);var qs=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},Le=(n,t)=>(e,s)=>t(e,s,n);const Tt="LOGIN_URL_KEY",Xs="/universer-api/oidc/authpage";let Ee=class{constructor(n,t,e){this._configService=n,this._httpService=t,this.localeService=e,this.init()}init(){this._httpService.registerHTTPInterceptor({priority:1,interceptor:(n,t)=>t(n).pipe(v.concatMap(async e=>{if(e.status===401&&window.confirm(this.localeService.t("auth.needGotoLoginAlert"))){const i=window.encodeURIComponent(window.location.href);window.location.href=`${this._getLoginPath()}?url=${i}`}return e}))})}_getLoginPath(){var n;return(n=this._configService.getConfig(Tt))!=null?n:Xs}};Ee=qs([Le(0,a.IConfigService),Le(1,h.Inject(k.HTTPService)),Le(2,h.Inject(a.LocaleService))],Ee);var zs=(n,t,e,s)=>{for(var i=t,r=n.length-1,o;r>=0;r--)(o=n[r])&&(i=o(i)||i);return i},nt=(n,t)=>(e,s)=>t(e,s,n);const Js="collaboration-client";var Ne;exports.CollaborationClientPlugin=(Ne=class extends a.Plugin{constructor(t,e,s){super(),this._config=t,this._injector=e,this._localeService=s,this._localeService.load({zhCN:Et})}onStarting(t){var i,r,o,c;t.replace([a.IUndoRedoService,{useClass:xe}]);const e=[[exports.CollaborationSessionService],[Ge],[k.HTTPService],[pt,{useClass:Bs}],[G],[M],[k.WebSocketService],[Ce],[Ie],[fe],[We],[Ee],[Ve,{useClass:(r=(i=this._config)==null?void 0:i.socketService)!=null?r:exports.CollaborationSocketService}],[k.IHTTPImplementation,{useClass:k.XHRHTTPImplementation}],[a.ISnapshotServerService,{useClass:Pe}],[exports.CollaborationController],[ce],[Se],[ve],[J]];(o=this._config)!=null&&o.enableSingleActiveInstanceLock&&e.push([be,{useClass:qt}]),((c=this._config)==null?void 0:c.collaborationUniverTypes)==null||this._config.collaborationUniverTypes.includes(a.UniverInstanceType.UNIVER_SHEET)?e.push([ge]):this._config.collaborationUniverTypes.includes(a.UniverInstanceType.UNIVER_DOC)&&e.push([me]),e.forEach(l=>t.add(l)),t.get(k.HTTPService).registerHTTPInterceptor({priority:20,interceptor:t.invoke(k.ThresholdInterceptorFactory,{maxParallel:6})}),this._initModules()}_initModules(){var t,e;this._injector.get(ce),(t=this._config)!=null&&t.enableOfflineEditing||this._injector.get(M).disableLocalCache(),(e=this._config)!=null&&e.enableAuthServer&&this._injector.get(Ee)}},d(Ne,"pluginName",Js),Ne);exports.CollaborationClientPlugin=zs([nt(1,h.Inject(h.Injector)),nt(2,h.Inject(a.LocaleService))],exports.CollaborationClientPlugin);const Zs={collabStatus:{fetchMiss:"Syncing server data...",conflict:"Edit conflicts",notCollab:"Local file",synced:"Synced",syncing:"Syncing...",offline:"Offline, edits would be save on local"},session:{"connection-failed":"Connection failed, please check your network.","will-retry":"Connection failed, we retry in a while.","room-full":"Collaboration room is full. You edits would be saved locally.","collaboration-timeout":"The server is not responding to your collaboration request. Your edits would be saved locally."},conflict:{title:"Collaboration Conflict",content:"There is a conflict between your local copy and the copy on the server. Please save your local edits, because they will be lost when you reload the page."},collaboration:{"single-unit":{warning:"You opened the same file in another tab. In case of data missing, you cannot edit on this tab."}},auth:{needGotoLoginAlert:"Your login has expired, click OK to re-login, click Cancel to save your local edits."}},Qs=Zs;exports.COLLAB_SUBMIT_CHANGESET_URL_KEY=ct;exports.COLLAB_WEB_SOCKET_URL_KEY=ht;exports.HEARTBEAT_INTERVAL_KEY=ut;exports.HEARTBEAT_TIMEOUT_KEY=Fe;exports.ICollaborationSocketService=Ve;exports.LOCAL_CACHE_INTERVAL_KEY=dt;exports.LOGIN_URL_KEY=Tt;exports.SEND_CHANGESET_TIMEOUT_KEY=vt;exports.SNAPSHOT_SERVER_URL_KEY=bt;exports.SessionStatus=W;exports.deserializeToCombResponse=ot;exports.enUS=Qs;exports.serializeCombRequest=at;exports.zhCN=Et;
|