React's design is often discussed, but because of the many related documents, the source code reads more tired.Just recently saw under the Hood:reactjs this project shared a flowchart of the React Core code (MIT Protocol), taking several of them as a directory index when writing this article for reading source.
The article is divided into 4 parts:
Source code to v15.6.1 as an example, will not directly copy a large segment of coding, mainly with hyperlinks to the GitHub source corresponding to the location-usually linked to the location of the function is called, a few cases will be linked to the location of the statement.The core code will of course involve vdom and event agents, online related articles are very many, this article no longer repeat, the official documents already have content will try to omit.The flowchart is an SVG format, and the graphic fill color uses different colors depending on the file.Embedded with an IFRAME tag.This is the best way to compatibility, but do not know where this article will be taken to the crawler, and the various RSS reader support, so attach the original address: dmyz.org/archives/983
Reactdom.render&reactmount
V0.14 react is split into react and react-dom two packets, Reactdom.render just a
s an interface, the actual call is Reactmount.render.Suppose you create this component of exa
mplecomponent, which is usually passed to render such as <examplecomponent/> in a jsx wa
y.JSX is just a react.createelement of grammatical sugar.
The execution of the _rendersubtreeintocontainer creates
the Toplevelwrapper, which is the top-level element, and its child elements are the examplecomponent we
created (Nextelement in the co
de).The component is then instantiated via Instantiatereactcomponent (a Reactcompositecomponentwrapper instance is returned).The wireframe of the above flow is as follows:
To this step is only the instantiation of the component, most of the logic is implemented through Reactupdates.batchedupdates, with transaction.
Transaction
Compared to the other chapters, the transaction is not as intuitive as render, but it can be seen in the core code.The Transaction.js code comment describes in detail what Transaction does, simply by wrapper encapsulating initialize and close methods for the methods that n
eed to be per
formed. first, then calls t
he method itself, and then calls Clo
se.So see what a transaction does, mainly to see its wrapper.Transaction.js is equivalent to the base class, and other Transaction inherit from it.The reactupdates.batchedupdates, mentioned in the prev
ious chapter, uses Reactdefaultbatchingstrategytransaction, which has two kinds of wrapper:
https://github.com/facebook/react/blob/v15.6.1/src/renderers/shared/stack/reconciler/ Reactdefaultbatchingstrategy.js#l19
var reset_batched_updates = {
Initialize:emptyfunction,
Close:function () {
Reactdefaultbatchingstrategy.isbatchingupdates = false;
},
};
var flush_batched_updates = {
Initialize:emptyfunction,
Close:ReactUpdates.flushBatchedUpdates.bind (Reactupdates),
};
var transaction_wrappers =[FLUSH_BATCHED_UPDATES, RESET_BATCHED_UPDATES];
Initialize is an empt
y function.The cl
ose setting Reactdefaultbatchingstrategy.isbatchingupdates to Fals
e and the Reactupdates.flushbatchedupdates validation component.The above flow chart is as follows:
And look at another Transaction:ReactUpdates.batchedUpdates. The first param
eter is the Batchedmountcomponentintonode that is executed as a callback func
tion, and the transaction in
the function is REACTRECONCILETR Ansaction, this transaction has three kinds of wrapper:
https://github.com/facebook/react/blob/v15.6.1/src/renderers/dom/client/ReactReconcileTransaction.js#L88
var transaction_wrappers =;
Selection_restoration saves the t
ext selected in the current element (input/textarea/contenteditable) and then resumes after the call is complet
ed; Event_ Suppression call reactbrowsereventemitter.seten
abled suppress other events; On_dom_ready_ Q
ueueing save Componentdidupdate and
Componentdidmount in a queue
to callback in transaction.
Reactreconciletransaction executed th
e Mountcomponentintonode, Generate markup by reactreconciler.mountcomponent (actually Performinitialmount, which is menti
oned in the next chapter).At this point, the mount began.The previous content wireframe is as follows:
In summary, the transaction in react is different from the transaction of the database, it is more based on the consideration of efficiency rather than consistency, and there is no rollback operation.To understand a transaction is mainly to see what its wrapper does.
Mount
As the first chapter has already mentioned, Toplevelwrapp
er is located at the top level, and its child, the user-defined component, is handled by Reactcompositeco
mponent.
The key method of Reactcompositecomponent
is mountcomponent, get public props and context, pass to instance, call transaction Getupdatequeue method, Assign the returned rea
ctupdatequeue to the updater of the instance, with the following a
ssignment code:
https://github.com/facebook/react/blob/v15.6.1/src/renderers/shared/stack/reconciler/ReactCompositeComponent.js#L254
Inst.props = Publicprops;
Inst.context = Publiccontext;
Inst.refs = Emptyobject;
Inst.updater = Updatequeue; It's related to SetState, and then you'll mention
The subsequent execution to performinitialmount into the React life cycle (lifecycle).
Reactreconciler.mountcomponent will be different accordin
g to the label different processing, if it is audio/video/form/img such labels, can not do the event agent on the document to bind to the label; if it is input/ TextArea to process the input, which is performed by Reactreconciletransactio
n in bulk.After verifying props, use the createelement (NS) to create the DOM element, see this flowchart for the above operations:
After creation by _updatedomproperties to determine whether mount, three parameters are Lastprops, Nextprops, transaction, Lastprops
and Nextprops do n
ot work when they a
re inconsistent (the current phase is las
tprops null).In particular, the first step is to traver
se lastprops, if the attribute exists in N
extprops first do not handle (continue).If it does not exist, check whether the style attribute (style) is assigned to Las
tstyle and then refresh the style by Csspropertyoperations.setvalueforstyles, otherwise the DOM properties and the events that have been set are deleted.Then traverse Nextprops to check w
hether the property is the same as the lastprops,
and then the logic is similar to the processing of the l
astprops, the difference is that if the component binds the event, the Enqueuepuelistener process is performed, and the flow diagram is as follows:
Then the child object is processed, _createinitialchildren calls Reactm
ultichild.mountchildren, which is a recursive process until the child object is an HTML tag, and the returned markup passes through the Reactmount._ Mountimageintonode operation, replace the contents of the container with the generated HTML, finally issued a notification of the end of the mount, the entire mount process is complete.
This.setstate
The SetState
method comes from Reactcomponent, and the actual execution is reactupdatequeue.enqueuesetstat
e.Push the state (partialstate)
into the _pendingstatequeue, execute the batchingstrategy.batchedupdates, or push the
component into the dirtycomponents.After traversing dirtyc
omponents, call Reactupdates.runbatched
updates via Reactupdatesflushtransaction.The reactreconciler.performupdateifnecessary in the function will
invoke the instance, which is Reactcompositeco
mponent's performupdateifnecessary, to perform the updatecomponen
t.
Component update logic, the react document has been introduced in detail.SetState or
modify props will invoke updatecomponent.From the source view, modify props let willreceive = true, meet the conditions to invoke componentwillreceiv
eprops.method, Shouldupdate defaults to T
rue to determine whether to update the component based on the content r
eturned by Shouldcomponentupdate:
When Shouldupdate is true, call _performcomponentupdate, execute _updaterenderedcomponent, Method of the Reactreconciler.re
ceivecomponent actually calls the Reactdomcomponent method, reas
signing the component instance, upda
ting the component and child elements.
Finds child elements and, if the child element is still a react component, calls Updatechildren until it is a string or a number.When the update is complete, the component's componentdidupdate
will be invoked, and the react lifecycle ends.
Process diagram:
Afterword
There are many types of reactjs frameworks, such as Preact and Inferno, which prove that the Reactjs design is really worth learning.Even if you do not read the source code, follow the flowchart DIY A similar framework is also very interesting.Various react related projects are also very popular, such as the Project (UNDER-THE-HOOD:REACTJS) released in a few days, nearly 2000 of star.The title of this article is to see under the hood temporarily thought, although it seems not appropriate …