@@ -334,20 +334,26 @@ export default class CardStoreWithGarbageCollection implements CardStore {
334334 sweep ( api : typeof CardAPI ) {
335335 let dependencyGraph = this . makeDependencyGraph ( api ) ;
336336 let reachable = new Set < string > ( ) ;
337- let visited = new WeakSet < CardDef > ( ) ;
337+ let visited = new WeakSet < StoredInstance > ( ) ;
338338 let rootLocalIds : string [ ] = [ ] ;
339339
340340 for ( let instance of this . #cards. values ( ) ) {
341- if ( ! instance || ! isCardInstance ( instance ) ) {
341+ if ( ! instance || visited . has ( instance ) ) {
342342 continue ;
343343 }
344- if ( visited . has ( instance ) ) {
344+ visited . add ( instance ) ;
345+ if ( isCardInstance ( instance ) ) {
346+ let localId = instance [ localIdSymbol ] ;
347+ if ( this . hasReferences ( localId ) ) {
348+ rootLocalIds . push ( localId ) ;
349+ }
345350 continue ;
346351 }
347- visited . add ( instance ) ;
348- let localId = instance [ localIdSymbol ] ;
349- if ( this . hasReferences ( localId ) ) {
350- rootLocalIds . push ( localId ) ;
352+ if ( isFileDefInstance ( instance ) ) {
353+ let fileId = instance . id ;
354+ if ( fileId && this . hasReferences ( fileId ) ) {
355+ reachable . add ( fileId ) ;
356+ }
351357 }
352358 }
353359
@@ -367,32 +373,51 @@ export default class CardStoreWithGarbageCollection implements CardStore {
367373 }
368374 }
369375
370- visited = new WeakSet < CardDef > ( ) ;
376+ visited = new WeakSet < StoredInstance > ( ) ;
371377 for ( let instance of this . #cards. values ( ) ) {
372- if ( ! instance || ! isCardInstance ( instance ) ) {
378+ if ( ! instance || visited . has ( instance ) ) {
373379 continue ;
374380 }
375- if ( visited . has ( instance ) ) {
381+ visited . add ( instance ) ;
382+ if ( isCardInstance ( instance ) ) {
383+ let localId = instance [ localIdSymbol ] ;
384+ if ( ! reachable . has ( localId ) ) {
385+ if ( this . #gcCandidates. has ( localId ) ) {
386+ destroy ( instance ) ;
387+ // brand the instance to make it easier for debugging
388+ ( instance as unknown as any ) [
389+ Symbol . for ( '__instance_detached_from_store' )
390+ ] = true ;
391+ this . delete ( localId ) ;
392+ if ( instance . id ) {
393+ this . delete ( instance . id ) ;
394+ }
395+ } else {
396+ this . #gcCandidates. add ( localId ) ;
397+ }
398+ } else {
399+ this . #gcCandidates. delete ( localId ) ;
400+ }
376401 continue ;
377402 }
378- visited . add ( instance ) ;
379- let localId = instance [ localIdSymbol ] ;
380- if ( ! reachable . has ( localId ) ) {
381- if ( this . #gcCandidates. has ( localId ) ) {
382- destroy ( instance ) ;
383- // brand the instance to make it easier for debugging
384- ( instance as unknown as any ) [
385- Symbol . for ( '__instance_detached_from_store' )
386- ] = true ;
387- this . delete ( localId ) ;
388- if ( instance . id ) {
389- this . delete ( instance . id ) ;
403+ if ( isFileDefInstance ( instance ) ) {
404+ let fileId = instance . id ;
405+ if ( ! fileId ) {
406+ continue ;
407+ }
408+ if ( ! reachable . has ( fileId ) ) {
409+ if ( this . #gcCandidates. has ( fileId ) ) {
410+ destroy ( instance ) ;
411+ ( instance as unknown as any ) [
412+ Symbol . for ( '__instance_detached_from_store' )
413+ ] = true ;
414+ this . delete ( fileId ) ;
415+ } else {
416+ this . #gcCandidates. add ( fileId ) ;
390417 }
391418 } else {
392- this . #gcCandidates. add ( localId ) ;
419+ this . #gcCandidates. delete ( fileId ) ;
393420 }
394- } else {
395- this . #gcCandidates. delete ( localId ) ;
396421 }
397422 }
398423 }
@@ -569,10 +594,18 @@ export default class CardStoreWithGarbageCollection implements CardStore {
569594 }
570595 }
571596
572- private hasReferences ( localId : string ) : boolean {
573- let referenceCount = this . #referenceCount. get ( localId ) ?? 0 ;
574- for ( let remoteId of this . #idResolver. getRemoteIds ( localId ) ) {
575- referenceCount += this . #referenceCount. get ( remoteId ) ?? 0 ;
597+ private hasReferences ( id : string ) : boolean {
598+ let idsToCheck = new Set < string > ( [ id ] ) ;
599+ let localId = isLocalId ( id ) ? id : this . #idResolver. getLocalId ( id ) ;
600+ if ( localId ) {
601+ idsToCheck . add ( localId ) ;
602+ for ( let remoteId of this . #idResolver. getRemoteIds ( localId ) ) {
603+ idsToCheck . add ( remoteId ) ;
604+ }
605+ }
606+ let referenceCount = 0 ;
607+ for ( let refId of idsToCheck ) {
608+ referenceCount += this . #referenceCount. get ( refId ) ?? 0 ;
576609 }
577610 return referenceCount > 0 ;
578611 }
0 commit comments