@@ -28,66 +28,63 @@ const ApiDOMDereferenceStrategy: stampit.Stamp<IDereferenceStrategy> = stampit(
28
28
} ,
29
29
30
30
async dereference ( file : IFile , options : IReferenceOptions ) : Promise < Element > {
31
- const refSet = options . dereference . refSet ?? ReferenceSet ( ) ;
31
+ const immutableRefSet = options . dereference . refSet ?? ReferenceSet ( ) ;
32
+ const mutableRefsSet = ReferenceSet ( ) ;
33
+ let refSet = immutableRefSet ;
32
34
let reference ;
33
35
34
36
// determine the initial reference
35
- if ( ! refSet . has ( file . uri ) ) {
37
+ if ( ! immutableRefSet . has ( file . uri ) ) {
36
38
reference = Reference ( { uri : file . uri , value : file . parseResult } ) ;
37
- refSet . add ( reference ) ;
39
+ immutableRefSet . add ( reference ) ;
38
40
} else {
39
41
// pre-computed refSet was provided as configuration option
40
- reference = refSet . find ( ( ref ) => ref . uri === file . uri ) ;
42
+ reference = immutableRefSet . find ( ( ref ) => ref . uri === file . uri ) ;
41
43
}
42
44
43
45
/**
44
46
* Clone refSet due the dereferencing process being mutable.
45
47
* We don't want to mutate the original refSet and the references.
46
48
*/
47
49
if ( options . dereference . immutable ) {
48
- const immutableRefs = refSet . refs . map ( ( ref ) =>
49
- Reference ( {
50
- ...ref ,
51
- uri : `immutable://${ ref . uri } ` ,
52
- } ) ,
53
- ) ;
54
- const mutableRefs = refSet . refs . map ( ( ref ) =>
55
- Reference ( {
56
- ...ref ,
57
- value : cloneDeep ( ref . value ) ,
58
- } ) ,
59
- ) ;
60
-
61
- refSet . clean ( ) ;
62
- mutableRefs . forEach ( ( ref ) => refSet . add ( ref ) ) ;
63
- immutableRefs . forEach ( ( ref ) => refSet . add ( ref ) ) ;
64
- reference = refSet . find ( ( ref ) => ref . uri === file . uri ) ;
50
+ immutableRefSet . refs
51
+ . map ( ( ref ) =>
52
+ Reference ( {
53
+ ...ref ,
54
+ value : cloneDeep ( ref . value ) ,
55
+ } ) ,
56
+ )
57
+ . forEach ( ( ref ) => mutableRefsSet . add ( ref ) ) ;
58
+ reference = mutableRefsSet . find ( ( ref ) => ref . uri === file . uri ) ;
59
+ refSet = mutableRefsSet ;
65
60
}
66
61
67
62
const visitor = ApiDOMDereferenceVisitor ( { reference, options } ) ;
68
63
const dereferencedElement = await visitAsync ( refSet . rootRef . value , visitor ) ;
69
64
70
- if ( options . dereference . refSet === null ) {
71
- /**
72
- * Release all memory if this refSet was not provided as a configuration option.
73
- * If provided as configuration option, then provider is responsible for cleanup.
74
- */
75
- refSet . clean ( ) ;
76
- } else if ( options . dereference . immutable ) {
77
- /**
78
- * If immutable option is set, then we need to remove mutable refs from the refSet.
79
- */
80
- const immutableRefs = refSet . refs
65
+ /**
66
+ * If immutable option is set, replay refs from the refSet.
67
+ */
68
+ if ( options . dereference . immutable ) {
69
+ mutableRefsSet . refs
81
70
. filter ( ( ref ) => ref . uri . startsWith ( 'immutable://' ) )
82
71
. map ( ( ref ) =>
83
72
Reference ( {
84
73
...ref ,
85
74
uri : ref . uri . replace ( / ^ i m m u t a b l e : \/ \/ / , '' ) ,
86
75
} ) ,
87
- ) ;
76
+ )
77
+ . forEach ( ( ref ) => immutableRefSet . add ( ref ) ) ;
78
+ reference = immutableRefSet . find ( ( ref ) => ref . uri === file . uri ) ;
79
+ refSet = immutableRefSet ;
80
+ }
88
81
89
- refSet . clean ( ) ;
90
- immutableRefs . forEach ( ( ref ) => refSet . add ( ref ) ) ;
82
+ /**
83
+ * Release all memory if this refSet was not provided as a configuration option.
84
+ * If provided as configuration option, then provider is responsible for cleanup.
85
+ */
86
+ if ( options . dereference . refSet === null ) {
87
+ immutableRefSet . clean ( ) ;
91
88
}
92
89
93
90
return dereferencedElement ;
0 commit comments