11/* eslint-disable func-names */
22/* eslint-disable no-use-before-define */
33/* eslint-disable no-param-reassign */
4-
54// links component state tree to library
65// changes the setState method to also update our snapshot
7-
86const Tree = require ( './tree' ) ;
97const astParser = require ( './astParser' ) ;
10- const { saveState } = require ( './masterState' ) ; // saves AST state as array for later use
8+ const { saveState } = require ( './masterState' ) ;
119
1210module . exports = ( snap , mode ) => {
13- // snap is the current tree
14- // mode is {jumping: bool, locked: bool, paused: bool}
15-
1611 let fiberRoot = null ;
1712 let astHooks ;
1813
19- function sendSnapshot ( ) { // send snapshot of current fiber tree to chrome extension ?
14+ function sendSnapshot ( ) {
2015 // don't send messages while jumping or while paused
21- // DEV: So that when we are jumping to an old snapshot it wouldn't think we want to create new snapshots
16+ // DEV: So that when we are jumping to an old snapshot it
17+ // wouldn't think we want to create new snapshots
2218 if ( mode . jumping || mode . paused ) return ;
23- const payload = snap . tree . getCopy ( ) ; // copy of current react fiber tree
19+ const payload = snap . tree . getCopy ( ) ;
2420 // console.log('payload', payload);
25- window . postMessage ( { // send to window
21+ window . postMessage ( {
2622 action : 'recordSnap' ,
2723 payload,
2824 } ) ;
2925 }
3026
31- function changeSetState ( component ) { // if invoked, change setState functionality so that it also updates our snapshot
32- // console.log("what is component?", component);
27+ function changeSetState ( component ) {
3328 // check that setState hasn't been changed yet
34- if ( component . setState . linkFiberChanged ) {
35- // console.log("setState has already been changed for", component);
36- return ;
37- } ;
29+ if ( component . setState . linkFiberChanged ) return ;
3830 // make a copy of setState
3931 const oldSetState = component . setState . bind ( component ) ;
4032 // replace component's setState so developer doesn't change syntax
@@ -43,30 +35,29 @@ module.exports = (snap, mode) => {
4335 // don't do anything if state is locked
4436 // UNLESS we are currently jumping through time
4537 if ( mode . locked && ! mode . jumping ) return ;
46- // continue normal setState functionality, except add sending message (to chrome extension) middleware
38+ // continue normal setState functionality, except add sending message middleware
4739 oldSetState ( state , ( ) => {
48- updateSnapShotTree ( ) ; // this doubles the actions in reactime for star wars app, also invokes changeSetState twice, also invokes changeSetState with Route and Characters
49- sendSnapshot ( ) ; //runs once on page load, after event listener: message (line 145)
50- callback . bind ( component ) ( ) ; // WHY DO WE NEED THIS ?
40+ updateSnapShotTree ( ) ;
41+ sendSnapshot ( ) ;
42+ callback . bind ( component ) ( ) ;
5143 } ) ;
5244 } ;
53- component . setState . linkFiberChanged = true ; // we changed setState.
45+ component . setState . linkFiberChanged = true ;
5446 }
5547
56- function changeUseState ( component ) { // if invoked, change useState dispatch functionality so that it also updates our snapshot
57- //check that changeUseState hasn't been changed yet
48+ function changeUseState ( component ) {
5849 if ( component . queue . dispatch . linkFiberChanged ) return ;
5950 // store the original dispatch function definition
6051 const oldDispatch = component . queue . dispatch . bind ( component . queue ) ;
6152 // redefine the dispatch function so we can inject our code
6253 component . queue . dispatch = ( fiber , queue , action ) => {
63- // don't do anything if state is locked, UNLESS we are currently jumping through time
54+ // don't do anything if state is locked
6455 if ( mode . locked && ! mode . jumping ) return ;
6556 oldDispatch ( fiber , queue , action ) ;
66- setTimeout ( ( ) => {
67- updateSnapShotTree ( ) ;
68- sendSnapshot ( ) ;
69- } , 100 ) ;
57+ // setTimeout(() => {
58+ updateSnapShotTree ( ) ;
59+ sendSnapshot ( ) ;
60+ // }, 100);
7061 } ;
7162 component . queue . dispatch . linkFiberChanged = true ;
7263 }
@@ -79,8 +70,10 @@ module.exports = (snap, mode) => {
7970 let index = 0 ;
8071 astHooks = Object . values ( astHooks ) ;
8172 // while memoizedState is truthy, save the value to the object
82- while ( memoizedState ) {
83- changeUseState ( memoizedState ) ;
73+ while ( memoizedState && memoizedState . queue ) { // prevents useEffect from crashing on load
74+ if ( memoizedState . next . queue === null ) { // prevents double pushing snapshot updates
75+ changeUseState ( memoizedState ) ;
76+ }
8477 // memoized[astHooks[index]] = memoizedState.memoizedState;
8578 memoized [ astHooks [ index ] ] = memoizedState . memoizedState ;
8679 // Reassign memoizedState to its next value
@@ -92,22 +85,21 @@ module.exports = (snap, mode) => {
9285 }
9386
9487 function createTree ( currentFiber , tree = new Tree ( 'root' ) ) {
95- // if there is no current fiber just return the new tree as-is
9688 if ( ! currentFiber ) return tree ;
97- // console.log("what is currentFiber", currentFiber);
89+
9890 const {
9991 sibling,
10092 stateNode,
10193 child,
10294 memoizedState,
10395 elementType,
104- } = currentFiber ; // extract properties of current fiber
96+ } = currentFiber ;
10597
106- let childTree = tree ; // initialize child fiber tree as current fiber tree
98+ let nextTree = tree ;
10799 // check if stateful component
108100 if ( stateNode && stateNode . state ) {
109101 // add component to tree
110- childTree = tree . appendChild ( stateNode ) ; // returns newly appended tree
102+ nextTree = tree . appendChild ( stateNode ) ;
111103 // change setState functionality
112104 changeSetState ( stateNode ) ;
113105 }
@@ -119,43 +111,34 @@ module.exports = (snap, mode) => {
119111 // Create a traversed property and assign to the evaluated result of
120112 // invoking traverseHooks with memoizedState
121113 memoizedState . traversed = traverseHooks ( memoizedState ) ;
122- childTree = tree . appendChild ( memoizedState ) ;
114+ nextTree = tree . appendChild ( memoizedState ) ;
123115 }
124116 // iterate through siblings
125117 createTree ( sibling , tree ) ;
126118 // iterate through children
127- createTree ( child , childTree ) ;
119+ createTree ( child , nextTree ) ;
128120
129121 return tree ;
130122 }
131-
132- // runs when page initially loads and on subsequent state changes
123+ // runs when page initially loads
133124 // but skips 1st hook click
134125 function updateSnapShotTree ( ) {
135- const { current } = fiberRoot ; // on initial page load, current - fiberNode is tag type HostRoot (entire fiber tree)
136- console . log ( "current" , current ) ;
126+ const { current } = fiberRoot ;
137127 snap . tree = createTree ( current ) ;
138128 }
139129
140- // RUNS ONCE, ON INITIAL PAGE LOAD ?
141130 return container => {
142- // on first page load, container is entire html hierarchy of top level div
143- // _reactRootContainer is that invisible top level object which wraps the top level div
144- // _reactRootContainer._internalRoot is an object with property .current which includes HostRoot fiberNode (entire fiber tree)
145131 const {
146132 _reactRootContainer : { _internalRoot } ,
147133 _reactRootContainer,
148134 } = container ;
149- // only assign internal root if it actually exists
135+ // only assign internal rootp if it actually exists
150136 fiberRoot = _internalRoot || _reactRootContainer ;
151137
152138 updateSnapShotTree ( ) ;
153139 // send the initial snapshot once the content script has started up
154140 window . addEventListener ( 'message' , ( { data : { action } } ) => {
155- if ( action === 'contentScriptStarted' ) { // runs once on initial page load
156- // console.log("in window.addEL")
157- sendSnapshot ( )
158- } ;
141+ if ( action === 'contentScriptStarted' ) sendSnapshot ( ) ;
159142 } ) ;
160143 } ;
161144} ;
0 commit comments