@@ -24,12 +24,14 @@ import {
24
24
import core , {
25
25
type AccountUuid ,
26
26
type Doc ,
27
+ DOMAIN_TX ,
27
28
type PersonId ,
28
29
pickPrimarySocialId ,
29
30
type Ref ,
30
31
SocialIdType ,
31
32
type Space ,
32
- toIdMap
33
+ toIdMap ,
34
+ type TxUpdateDoc
33
35
} from '@hcengineering/core'
34
36
import {
35
37
createDefaultSpace ,
@@ -48,6 +50,7 @@ import {
48
50
getSocialKeyByOldAccount
49
51
} from '@hcengineering/model-core'
50
52
import setting , { DOMAIN_SETTING , type Integration } from '@hcengineering/setting'
53
+ import contact , { type SocialIdentityRef , type SocialIdentity } from '@hcengineering/contact'
51
54
import { DOMAIN_CALENDAR , DOMAIN_EVENT } from '.'
52
55
import calendar from './plugin'
53
56
@@ -371,6 +374,71 @@ async function migrateEventUserToNewAccounts (client: MigrationClient): Promise<
371
374
client . logger . log ( 'finished processing events user ' , { } )
372
375
}
373
376
377
+ async function migrateEventUserForDeleted ( client : MigrationClient ) : Promise < void > {
378
+ const socialKeyByAccount = await getSocialKeyByOldAccount ( client )
379
+ const deletedSocialIdByOldAccount = new Map < string , PersonId | null > ( )
380
+
381
+ client . logger . log ( 'processing events user ' , { } )
382
+ const iterator = await client . traverse ( DOMAIN_EVENT , {
383
+ _class : { $in : [ calendar . class . Event , calendar . class . ReccuringEvent ] }
384
+ } )
385
+
386
+ try {
387
+ let processed = 0
388
+ while ( true ) {
389
+ const docs = await iterator . next ( 200 )
390
+ if ( docs === null || docs . length === 0 ) {
391
+ break
392
+ }
393
+
394
+ const operations : { filter : MigrationDocumentQuery < Doc > , update : MigrateUpdate < Doc > } [ ] = [ ]
395
+
396
+ for ( const doc of docs ) {
397
+ const event = doc as Event
398
+ const oldAccount = event . user
399
+ if ( ! deletedSocialIdByOldAccount . has ( oldAccount ) ) {
400
+ const socialKey = socialKeyByAccount [ oldAccount ]
401
+ if ( socialKey == null ) continue
402
+
403
+ const deletedIdentityTx = (
404
+ await client . find < TxUpdateDoc < SocialIdentity > > ( DOMAIN_TX , {
405
+ _class : core . class . TxUpdateDoc ,
406
+ objectClass : contact . class . SocialIdentity ,
407
+ 'operations.key' : { $like : `${ socialKey } #%` }
408
+ } )
409
+ ) [ 0 ]
410
+
411
+ if ( deletedIdentityTx == null ) continue
412
+
413
+ deletedSocialIdByOldAccount . set ( oldAccount , deletedIdentityTx . objectId as SocialIdentityRef )
414
+ }
415
+ const socialId = deletedSocialIdByOldAccount . get ( oldAccount )
416
+
417
+ const newUser = socialId ?? event . user
418
+
419
+ if ( newUser === event . user ) continue
420
+
421
+ operations . push ( {
422
+ filter : { _id : doc . _id } ,
423
+ update : {
424
+ user : newUser
425
+ }
426
+ } )
427
+ }
428
+
429
+ if ( operations . length > 0 ) {
430
+ await client . bulk ( DOMAIN_EVENT , operations )
431
+ }
432
+
433
+ processed += docs . length
434
+ client . logger . log ( '...processed' , { count : processed } )
435
+ }
436
+ } finally {
437
+ await iterator . close ( )
438
+ }
439
+ client . logger . log ( 'finished processing events user ' , { } )
440
+ }
441
+
374
442
async function fillBlockTime ( client : MigrationClient ) : Promise < void > {
375
443
await client . update ( DOMAIN_EVENT , { blockTime : { $exists : false } , allDay : true } , { blockTime : false } )
376
444
await client . update ( DOMAIN_EVENT , { blockTime : { $exists : false } } , { blockTime : true } )
@@ -455,6 +523,11 @@ export const calendarOperation: MigrateOperation = {
455
523
state : 'migrate-ev-user-to-new-accounts' ,
456
524
mode : 'upgrade' ,
457
525
func : migrateEventUserToNewAccounts
526
+ } ,
527
+ {
528
+ state : 'migrate-ev-user-for-deleted' ,
529
+ mode : 'upgrade' ,
530
+ func : migrateEventUserForDeleted
458
531
}
459
532
] )
460
533
} ,
0 commit comments