Vous êtes sur la page 1sur 9

Angular Universal

AngularUServerRenderingPresentation(6/25/2015):
https://www.youtube.com/watch?v=0wvZ7gakqV4
AngularConnectFullStackAngular2Presentation(10/20/2015):
https://www.youtube.com/watch?v=MtoHFDfi8FM

JeffWhelpley(
jeffwhelpley@gmail.com
)
PatrickJS(
patrick@gdi2290.com
)
TobiasBosch(
tbosch@google.com
)
JeffCross(
crossj@google.com
)

Objective
PriorArt
Rendr
Derby
Meteor
React
EmberFastBoot
Angular2
Usecases
1.Perceivedloadtime
2.Actualloadtime
3.Clientsideperformance
4.SEO
5.Browsersupport
6.Linkpreview
TechnicalRequirementsPrimary
Itjustworks
Seamlessstatetransfer
Performance
TechnicalRequirementsSecondary
Extensibility
ComponentRouting
Optimizations
TechnicalDesign
Approach
OverallFlow
ModuleServerDomRenderer
ModuleServerPlugin
ModulePreboot
KeyFeatures
Installation
Options
ListenStrategies
ReplayStrategies
FreezeStrategies
FutureItems
NonJSserverrendering
Packagingservice
Notes

Objective
ThenewrenderingarchitectureofAngular2willseparatetheAngularruntimeintotwolayers:theapplicationlayerandtherendering
layer.TheapplicationlayercontainsAPIsandruntimethattheapplicationcodeinteractswithdirectly.Therenderinglayerprovidesa
commonprotocolforperformingUIupdates.ThesplitwillallowAngular2applicationstorunindifferentenvironments/platforms
whileprovidingthesamesetofabstractionstoapplicationdevelopers.Thedefaultrenderingenvironmentisthebrowser,butother
environmentscouldincludewebworkers,webserversorotherdevices.Theprimarypurposeofthisdocumentistodesignasolution
forrenderingAngular2viewsonawebserveraswellastheprocessbywhichserverrenderedviewsseamlesslytransferstatedown
toanAngular2clientapprunninginabrowser.

Prior Art
SpikeBrehmfromAirBnbpopularizedtheterm
IsomorphicJavaScript
.Somepeopleusethistermjusttorefertosharedcodeused
forviewrenderingwhileotherpeopleusethetermforanysharedcodebetweentheclientandserver.Morerecently,Michael
Jacksonsuggestedcallingthis
UniversalJavaScript
.Thefollowingexistingframeworkssupportisomorphic/universalviewrendering
atsomelevel.

Rendr

About
Background
RendrwascreatedbySpikeBrehmatAirBnbtorenderBackboneviewsontheserver.

Popularity
~3,800GitHubstars,butnotethat
AirBnbisswitchingfromRendrtoReact
Howitworks

ThebasicstrategyofRendristocreatewrappersaroundallthecoreBackboneobjects.Anappuses
Rendr.viewinsteadofBackbone.view,Rendr.collectioninsteadofBackbone.collection,etc.Therearealsoasetofserver
specificlibrariesforrunningaRendrappontheserver.

Details
Templates
UsesHandlebarswhichisastringbasedtemplatingengine.Thesetypesoftemplatingenginesareactuallygood
forisomorphicrenderingbecausethereisnoneedtoanalyzethecontentsofthetemplateontheclientorserver.Also,
renderingforstringbasedtemplatesistypicallyveryfast.
Routing
Rendr.RouterwillfeedtheExpressrouterontheserversideandtheBackbone.Routerontheclientside
Statetransfer
Theserverputtheserializedstateintherenderedviewandthentheclientwill
hydratetheserverrendered
view
ontheclientusingthatserializedstate.

Notes
BackbonesubviewsandjQuerypluginsoftenmodifytheappstateafteraviewgetsrenderedandtherebypreventafull
rerenderwithoutlosingsomeofthatnewlyaddedstateandincurringaperformancehit
TightlycoupledtoExpressontheserverside

Derby

About
Background
Derbywascreatedin2011byNateSmith,thecurrentCTOofLever.
Popularity
~3,750GitHubstars(comparedto1,600twoyearsago)
Howitworks

DerbyisafullstackJavaScriptframework.Whereasalloftheotherframeworkslistedherehavethefeelofa
clientsideframeworkwithserversidefunctionality,Derbyismoreserverfocused.ItwasbuiltonExpressandusesstandard
node.jslibraries.

Details
Templates
Bydefaultusesitsownreactivetemplatingsystemthatcanrenderontheclientandserver.
Routing
RoutesthataredefinedinDerbyarefedintotheExpressrouterontheserversideandacustomrouterbuiltoff
Expresssrouterontheclientside.
Statetransfer
AftertheservergeneratesHTMLandsendsitdowntotheclient,theclientwill
attachtotheserverrendered
view
.ThismeansthattheclientviewstartsthegenerationprocessasitnormallywouldbutinsteadofinsertingnewDOM
elements,itcheckstoseewhatisalreadyintheDOMfromtheserverrenderedviewandthendoesanupdateonthat
existingelement.

Notes
TightlycoupledtoExpress

Meteor

About
Background
Builtandmaintainedbyaventurebasedstartup.
Popularity

7thmostpopularJavaScriptproject
onGitHubandhasincreasedinpopularityovertime.~26,000starson
GitHub(comparedto6,000twoyearsago).
Howitworks

Meteor,anultrasimple,databaseeverywhere,dataonthewire,pureJavascriptwebframework.Theprimary
focusonMeteorisonrealtimewebandmobileapps.

Details
Templates
Bydefaultituses
Blaze
foritstemplateengine.Thisonlyworksbydefaultontheclient,howeverthereis
a
projectfromthecommunity
toadaptBlazeforserverrendering.
Routing
Meteorcoredoesnothaveanyrouting,butthereareanumberofprojectsfromthecommunitysuchasthe
Meteor
IronRouter
.
Statetransfer
Meteorcoredoesnothaveserverrendering,soaccordinglythereisnomechanismtotransferstatefrom
serverrenderedviewstotheclient.

Notes
WhileitispossibletosetupserverrenderingwithMeteor,the
veryfirstcoreprincipleofMeteor
explicitlystatesMeteor
doesn'tsendHTMLoverthenetwork(theyuse
DDP
insteadofHTTPforclient/servercommunication).

React

About
Background
CreatedbyFacebookandreleasedtothepubliclastyear.
Popularity
8thmostpopularJavaScriptprojectonGitHub(~24,000stars)despiteonlybeingaroundforaboutayear.
Howitworks

ReactfocusesonlyontheviewlayerandusesavirtualDOMdiffimplementationforhighperformance.During
initialrenderingandanysubsequentchanges,theentirepageisrerenderedwithinthevirtualDOM,butonlythespecific
piecesofthevirtualDOMthatchangeareactuallypushedtotherealDOM.

Details
Templates
Atalowlevel,therearenotemplatesinReact.ReactusesJavaScriptcodetogenerateavirtualDOMobject.
However,thereisanabstractionontopofthislowlevelcodecalledJSXwhichlookslikeHTMLmixedintoJavaScript.The
onlydifferencebetweenclientandserverrenderingisthatwhilethevirtualDOMchangesarepushedtotheDOMonthe
clientside,thevirtualDOMissimplyserializedintoanHTMLstringontheserverbeforeitissentbacktotheclient.
Routing
Reactisonlyaviewlayeranddoesnotcontainanythingelse,includinganyrouter.However,the
reactrouter
built
bythecommunityisverypopularanddoesclientandserverrouting.

Statetransfer
ThereisnoneedtoserializeextrastatewithinaReactserverrenderedviewbecausethefirstthingReact
doesontheclientsideisdifftheinitialvirtualDOMagainsttheserverrenderedHTML.Thus,stateistheserverrendered
HTML.Note,however,thatthisdoesmeantheclientsidehastoreretrievedatafromtheAPI.

Notes
Currentlytheserverrenderingsolutionisrelativelyslowbecausetheserverhastodoalotofworkatruntimetoconcatenate
HTML.Mosttemplateengineswillprecompiletemplatesandthendosomecachingonceaviewhasbeenrenderedthefirst
time.Reactdoesnotcurrentlyuseeitheroftheseserversideoptimizations.Thereisworkongoingtotryandaddressthis
issue,butyoucanfindoutmoreaboutitatthefollowinglinks:
https://github.com/facebook/react/issues/1739
https://github.com/facebook/react/issues/3009
https://discuss.reactjs.org/t/whatsthebestwaytounblockthenodeeventloopduetoslowreactserversiderender/
1817/1
https://discuss.reactjs.org/t/reactdomstreamastreamingserversiderenderinglibraryforreactasmuchas47faste
rthanrendertostring/2286
https://github.com/facebook/react/issues/3009#issuecomment132001925

Ember FastBoot

NOTE:AlthoughEmberhasreleasedFastBootanditisbeingusedinthewild,theyareintheprocessofdevelopinganotherserver
renderingsolutionusingthe
Glimmerengine
whichwilluseavirtualDOMsimilartoReact(so,forexamplewillusevirtualDOMdiff
forstratetransfer),butwillhavesomeadditionalenhancementsliketemplateprecompilation.Thefollowinginfoisonlyapplicableto
thecurrentFastBootsolution:

About
Background
CreatedbyTomDaleaYehudaKatzfromTilde.
Popularity
13,173GitHubstarswitharelativelysmallbutextremelypassionateuserbase.
Howitworks

WhileEmberhasbeenaroundforawhile,FastBootwasjustrecentlycreatedandreleased.Thebasicstrategy
ofFastBootistousethe
simpledom
libraryontheserverside

Details
Templates
EmberpreviouslyusedHandlebars,buthasmorerecentlymovedtoanewlibrarycalled
HTMLBars
.Inboth
casestheyrelyonsomesortofDOMtoexistwhichiswhytheyhavetousesimpledom.
Routing
TheEmberRouterworksonboththeclientandserver.
Statetransfer
StateisserializedontheserversideintheHTMLandthenhydratedbytheclientappinthebrowser.

Notes
FastBootwasjustreleasedacouplemonthsago.

Angular 2
ThefollowingAngular2featuresexisttodayandwillhelpsupportserverrendering:

Angular2RenderingArchitecture
Angular2Router

Use cases
Eachoftheseusecasesprovideapossibleanswertothequestion:Whyisserverrenderingimportantforyourclientsidewebapp?
Thissectioncontainstheprimaryusecasesintheorderthatwebelievearemostimportanttothecommunity.

1. Perceived load time


Theinitialloadofaclientsidewebapplicationistypicallyveryslow.The
FilamentGroupreleasedastudy
recentlythatsaysthe
averageinitialpageloadtimeforsimpleAngular1.xappsonmobiledevicesis34seconds.Itcanbeevenworseformorecomplex
apps.Thisismostoftenanissueforconsumerfacingapps,especiallythosethataretypicallyaccessedonamobiledevice,butcan
beaproblemforanyapp.Thegoalofrenderingontheserverforthisusecaseistolowertheusersperceivedperformanceofthe
initialpageloadsothattheyseerealcontentinunder1secondregardlessofdeviceorconnectionspeed.Thisgoalismucheasier
toachieveconsistentlywithserverrenderingthanclientsiderendering.

2. Actual load time


Theinitialloadfortheclientwebappisgenerallyfasteriftheclientcodefileissmallerandonlyexecuteswhatisneededtorender
theinitialviews.Then,otherpartsoftheapplicationarelazilyloadedwhenneededorinthebackground.Forthemostpartthe
solutionforthisoccursatbuildtime.However,theremaybeadditionaloptimizationsthatcanbemadeand/oradjustedatruntime
basedoffadditionalinsightgleanedfromactuallyexecutingthecodeontheserver.

3. Client side performance


Thetypicalstoryforserverrenderingisthatitcoverstheinitialpageloadandthentheclienthandlesrenderingfromthatpoint
forward.However,therearesituationswhiletheclienthascontroloftheappwhereitwouldbefastertofetchafullyrenderedpage
snippetfromtheserverratherthanrenderitontheclient.Forexample,letssaythereisamostlystatic,butcomplexproductpage.
Considerthefollowingsituations:

1. Asectionofthepagetakesalongtimetorenderregardlessofthebestoptimizationeffortssinceitrequirespullingdowndata
fromaveryslowAPIcall.Thedataforthispartialdoesnotchangeoften,sowecancacheafullyrenderedversionofthe
partialontheserverandinsteadofpullingthedata,wepullthecached,renderedpartialHTML.
2. SameasbeforeexcepttheAPIcallisntquitethatbad.Itisdebateablewhetherthereisabenefittodothepartialserver
renderingatruntime.However,youcansetupaprocesswheretherenderedpartialiseitherpulledasynchronouslyand
cachedontheclientor,insomesituations,evenrenderthepartialatbuildtime.

3. Forcertainvisualizations,itmaybemoreefficienttorenderontheserverthantheclient.Thisisespeciallytrueforcomplex
graphsorchartswhichrequirealotofdataandheavycomputations,butthefinaloutputisrelativelysmall.

ItshouldbenotedthatTwitterhasusedthistypeofoptimizationforaround2years.Itsbenefitsmaybemostclearonlowerpowered
mobiledevices.

4. SEO
TheGooglesearchcrawlercontinuestogetbetteratindexingclientsiderenderedcontent,buttherearechallenges.

1. First,thecrawlerisntperfect(yet).Thereareanumberofsituationswherethecrawlermaynotindexexactlywhatis
rendered.ThisisoftenduetoeitherJavaScriptincapabilitiesortimingissueswithasyncloading.
2. Withserverrendering,thecrawlercandetermineexactlyhowlongittakesbeforetheuserseescontent(i.e.Document
Complete).Itisnotaseasyontheclientside(and,asmentionedintheprevioususecase,whenitismeasured,itisoften
muchslowerthanserverrendering).
3. Thereisnosuccessstoryoutthereforaclientsideonlywebappthatbeatsserverrenderedwebsitesforcompetitive
keywordsearches(ex.thinkanymajorpurchaseitemlikeflatscreentvorbestsedan2015).

TherelikelywillbeafuturewhereserverrenderingisnotneededforSEO,buttodayconsumerfacingappsthatreallycareabout
theirsearchrankingneedserverrendering.

5. Browser support
ThedownsideofusingmoreadvancedwebtechnologieslikeWebComponentsisthatitishardtokeepsupportforolderbrowsers.
ThisiswhyAngular2onlytargetsevergreenbrowsers.However,dependingontheappbeingbuilt,itmaybepossibletoreplace
certainrichclientbehaviorswithserversidebehaviorstosupportolderbrowserswhilelettingappdeveloperstakeadvantageofthe
latestwebplatform.Acoupleexamples:

1. TheappismostlyinformationalanditisOKforusersonolderbrowserstojustseetheinformationwithoutanyoftheclient
sidefunctionality.Inthiscase,itmaybealrighttogivelegacybrowserusersacompletelyserverrenderedwebsitewhile
evergreenbrowserusersgetthefullclientsideapp.
2. AnappmustsupportIE9(notanevergreenbrowser,butnotasbadasIE8).Mostoftheclientsidewebappfunctionality
works,butthereisonecomponentthatusesfunctionalitynotsupportedbyIE9.Forthatonecomponent,theappcould
potentiallyfetchthefullyrenderedpartialHTMLfromtheserver.

NotethatthisusecaseisNOTsothatwecansayAngular2actuallysupportssomethinglikeIE6becauseitwoulddependonthe
specificusecase.Agivenappmayrequirefeaturesinmodernbrowsersandthereisnoserverrenderedversionthatwouldhelp.
ThisismoreforusecaseswhereitisOKtohavetheappprovideastaticserverrenderedversionofacomponentorpageorwebsite
forlegacybrowsers.

6. Link preview
Programsthatshowwebsitepreviewsforprovidedlinksrelyonserverrendering.Duetothecomplexityinvolvedwithcapturingclient
siderenderedwebpages,theseprogramswilllikelycontinuetorelyonserverrenderingfortheforeseeablefuture.Themostwell
knownexamplesinvolvesocialmediaplatformslikeFacebook,G+orLinkedIn.SimilartotheSEOusecase,thisisonlyrelevantfor
consumerfacingapps.

Technical Requirements Primary


ThepurposeofthissectionistolayouttheprimaryrequirementsforaserverrenderingsolutioninAngular.

It just works
Rightoutofthebox,AngularshouldbeabletorenderanAngular2webapponaJavaScriptbackendserver.Itdoesnothaveto
renderperfectlyanditdoesnotneedtobeoptimizedrightoutofthebox,butitdoesneedtorender.Thegoalofthefunctionalityout
oftheboxistogivedevelopersabaselineforaserverrenderedsolution.AslongasanAngular2appdoesnotdirectlytouchthe
DOM(ex.referencethewindowordocumentobjectoutsideoftheAngular2APIs),thecomponentshouldrenderontheserverjust
likehowitrendersontheclient.

Seamless state transfer


Theclientshouldbeabletotakeovertheserverrenderedviewseamlessly.So,thereshouldntbeanyjankduringthetransferand
userinteractionsthatoccurwiththeserverrenderedpage(ex.userenteringdataintoaforminput)shouldnotbeinterruptedinany
way.So,iftheusertypesinasearchbox,boththecharactersinthesearchboxandthefocusofthecursorinthesearchboxshould
remainthroughoutthetransferprocess.

Performance
AsmentionedintheUseCasesabove,theprimaryreasondeveloperswantserverrenderingistoimproveperformance.So,itwillbe
importantthatasolutioninAngularmeetcertainperformancegoals(asmeasuredinBenchpress).Giventhefollowingconditions:

DesktopbrowseronlatestMacbookPro
Latency<10ms
ServerisequivalenttooneAWSt2instance
Singlerequest
Internetconnectionwith>11Mbpsdownloadspeed

Thentheperformanceofthissolutionshouldhitthefollowingtargets:

1. Serverrendertime<100ms
2. Perceivedloadtime<1s
3. Actualloadtime<3s

Technical Requirements Secondary


Oncetheprimaryrequirementshavebeenfulfilled,theseareadditionaltechnicalconsiderations.

Extensibility
TherearetwomajorareasofextensibilitythatareneededwiththeAngularserverrenderingsolution.First,theserversiderendering
enginemustbeabletointegratewithanyexistingNode.jsapp.Second,thesolutionmustbeabletobeadaptedtononJavaScript
backends.

Component Routing
Whilemostroutingwilldependonhowanappisimplemented(i.e.itisuptotheUIRouterorAngularRouter),theserverrendering
solutionwillneedtohaveagenericwayofroutingtospecificcomponents.ThiswillallowAngularappstoasktheservertorender
partials.

Optimizations
Whiletherearecommonperformancebottlenecks,eachwebapphastheirownsetofuniquechallenges.Itwillbeimportantthatthe
Angularserverrenderingsolutionincludesthefollowingoptionalfeatureswhichcanbeusedforperformanceoptimizations:

1. Server/client
Thedevelopershouldbeabletospecifyattheroute,pageorcomponentlevelwhetherapartoftheapp
shouldberenderedjustontheclient,justontheserverorboth.
2. Servercaching
Pagelevelcachingcanbehandledbythewebserver,butwithintheapp,wewillwanttoenablecachingat
thecomponentlevel.Thisshouldbeconfigurablesothatanymediumcanbeusedforthecachebackend.
3. Lazyloading
Theserverrenderingsolutionshouldbeabletoeasilyintegratewithalazyloadingsolutioninordertocut
downontheactualinitialloadtimeoftheapp.
4. Anonymousserverrendering
Insomecasesitwillbebeneficialtoallowtheservertorenderanonymously(i.e.without
usercontext)sothatpagescanbemoreaggressivelycached.Thisismostoftenusedbyappsthathavemostlypublic
contentwithacouplesmallpiecesofuserspecificcontent(ex.userprofilepicinupperright)forwhichitisOKtorender
clientonly.

Technical Design
ThissectioncontainsthedesignforimplementingserverrenderinginAngular.

Approach
Atahighlevel,therearetwomajorpiecestotheAngular2serverrenderingsolution:

1. Renderingontheserver
2. Transitioningfromtheserverviewtotheclientview

For#1,thissolutionsreliesontherenderingarchitectureofAngular2withoneadditionalpiecewhichisexplainedfurtherbelow,the
ServerDomRenderer:

For#2,thetransferfromtheserverviewtotheclientviewisfacilitatedbyprebootwhichisalsoexplainedfurtherbelow:

Overall Flow
LetsgooverafewvariationsoftheAngularrenderingsolutionflow.Thefirstoneistheoutofthebox,basicrenderingflowthatwill
occurbydefault:

1. HTTPGETrequestsenttotheserver

2. Serverrenderspagethatcontainsthefollowing:
a. RenderedHTMLfromServerDomRendererthattheuserwillseeinitially
b. InlineJavaScriptforpreboot(seeprebootsectionbelow)
3. Browserreceivesinitialpayloadfromserver
4. Userseesserverview
5. Prebootstartsrecordingevents
6. Requestsmadeforadditionalexternalimages,JS,CSS,etc.
7. Onceexternalresourcesloaded,Angularclientbootstrappingbegins
8. Clientviewrendered
9. Bootstrapcomplete,soAngularclientcallspreboot.done()
10. PrebooteventsreplayedinordertoadjusttheapplicationstatetoreflectchangesmadebytheuserbeforeAngular
bootstrapped(i.e.typingintextbox,clickingbutton,etc.)

Module ServerDomRenderer
Thismoduleimplementsthe
renderapiinterface
andwillmeettherequirements
laidouthere
.Itwillbuildandmaintainadata
structurewhichcorrelatestothebrowserDOM.WecaneasilytoString()thisinternalobjecttogenerateastringofHTMLwhichcan
bereturnedfromawebserverorusedfortestingpurposes.

(detailsofthismoduletofollow)

Module Server Plugin


ThismoduleisthecorelibrarythatwouldbeincludedontheserversidetorunanAngularapp.Itbasicallyconsistsofacustom
bootstrapimplementationalongwithsomeconvenienceAPIstomakeiteasiertoplugintoexistingnode.jswebserverframeworks
suchasHapiorExpress.

(detailsofthismoduletofollow)

Module Preboot
Thepurposeofthismoduleistotransitionaservergeneratedviewtoaclientwebapp.Thismodulehasnodependencieson
Angularandcanactuallybeusedbyanyframework,evenifitiscompletelyoutsidethecontextofAngularaltogether.Ingeneral,the
desiredbehaviorofapagebeforetheclienttakesoverwillbedifferentfordifferentusecases.So,thislibrarywascreatedinsucha
waythatdeveloperscanconfigureittomeettheirneeds.

Key Features

1. Recordandplaybackevents
Whicheventsarelistenedtoandhowtheyarereplayedarespecifiedthroughthepreboot
options.
2. Respondimmediatelytoevents
Insomecases,youwantanimmediateactiontotakeplace(i.e.notwaitfortheclientto
kickin).
3. Maintainfocusevenpageisrerendered
Ifthepagehastobererenderedandthefocusisinatextbox,wewantto
refocusinthecorrespondingtextboxintheclientview.
4. Bufferclientsidererenderingforsmoothertransition
AlthoughAngular2alreadyupdatesinbatches,theremaybeuse
caseswherewewanttobufferourclientupdatesandletprebootsmoothlyswitchthefullyrenderedclientviewfortheserver
view.Usingthisshouldensurethattheswitchfromservertoclientviewcanoccurin1frame.
5. Freezepageuntilbootstrapcompleteifuserclicksbutton
Ifselectedasanoption,wecanfreezethepagewhenthe
userclicksabuttonsothatnofurtheractionscanbemadeuntiltheclientprocessesthatbuttonclick.

Installation
Thisisaserversidelibrarythatgeneratesclientsidecode.Tousethislibrary,youwouldfirstinstallitthroughnpm:

npminstallpreboot

Theninyourserversidecodeyouwoulddosomethinglikethis:

varpreboot=require('preboot')
varprebootOptions={}//seeoptionssectionbelow
varclientCode=preboot(prebootOptions)

YoutheninjectclientCodeintotheHEADsectionofyourserversidetemplate.WewantpreboottoONLYstartrecordingoncethe
webapprootexistsintheDOM.Wearestillplayingwiththebestwaytodothis(NOTE:wehavetriedonLoadand
itdoesnotworkbecausethecallbackdoesnotgetexecutedquicklyenough).Fornow,tryputtingthefollowing
`preboot.start()`callimmediatelyafteryourwebapprootinyourserversidetemplate:

<webapproothere>
</webapproothere>
<script>
preboot.start()
</script>

Finally,onceyourclientsidewebappis"alive"ithastotellprebootthatitisOKtoreplayevents.

preboot.complete()

Options
Thereare5differenttypesofoptionsthatcanbepassedintopreboot.Inadditiontotheseoptions,wemayinthefutureaddthe
conceptofpresetssothatsomeonecouldsimplysaypreset=angularandwouldgetallthedefaultoptionsthataretypicallyused
withanAngularapp.

Selectors
appRootAselectorthatcanbeusedtofindtherootelementfortheview(defaultis'body')

Strategies
Thesecaneitherbestringvaluesifyouwanttouseaprebuiltstrategythatcomeswiththeframeworkoryoucanimplementyour
ownstrategyandpassitinhereasafunctionorobject.Theideabehindastrategyintheprebootlibraryistoallowthedeveloperto
customizethelibrarytosuittheirneeds.Therearetypicallyacouplebuiltinoptionsforeachtypeofstrategy,butthedevelopercan
alwayswritetheirown.Theclientsidecodegeneratedbyprebootwillonlycontainthestrategiesthatareactuallybeingused.So,in
otherwords,ifyoudon'tspecify'attributes'asalistenstrategyintheprebootoptions,thennoneofthelist_by_attributes.jscodewill
beincludedinthegeneratedclientsidecode.

listen
Howprebootlistensforevents.SeeListenStrategiessectionbelowformoredetails
replay
Howprebootreplayscapturedeventsonclientview.SeeReplayStrategiessectionbelowformoredetails
freeze
Howprebootfreezesthescreenwhencertaineventsoccur.SeeFreezeStrategiessectionbelowformoredetails

Flags
Allflagsfalsebydefault.

focus
Iftrue,willtrackandmaintainfocusevenifpagererendered
buffer
Iftrue,clientwillwritetoahiddendivwhichisonlydisplayedafterbootstrapcomplete
keyPress
Iftrue,allkeystrokesinatextboxortextareawillbetransferredfromtheserver
viewtotheclientview
buttonPress
Iftrue,buttonpresseswillberecordedandtheUIwillfreezeuntilbootstrapcomplete
pauseOnTyping
Iftrue,theprebootwillnotcompleteuntiluserfocusoutoftextinputelements
doNotReplay
Iftrue,noneoftheeventsrecordedwillbereplayed

WorkflowEvents
Thesearethenamesofglobaleventsthatcanaffecttheprebootworkflow.

pauseEvent
Whenthisisraised,prebootwilldelaytheplaybackofrecordedevents(default'PrebootPause')
resumeEvent
Whenthisisraised,prebootwillresumetheplaybackofevents(default'PrebootResume')

BuildParams
uglify
Youcanalwaysuglifytheoutputoftheclientcodestreamyourself,butifyousetthisoptiontotrueprebootwilldoitfor
you.

Listen Strategies
The'listen'optioncaneitherbeastring(thenameoftheprebuiltstrategy),configurationobject(seebelow)oranarrayof
configurationobjects.Eachconfigurationobjectcancontainthefollowingvalues:

name
Thenameofoneofthefollowingprebuiltstrategies:
selectors
Anobjectthatmapsaselectortoanarrayofevents
attributes
Thisstrategywillinspecttheserverviewforanyelementthatcontainsaparticularattributename(default
is'prebootevents').Soifthereisa`<inputprebootevents="keypress,focus">`thenallkeypressandfocuseventson
thatinputelementwouldbetracked.
event_bindings
UseAngular2eventbindingsdefinedintheserverviewHTML
getNodeEvents
Acustomstrategyimplementation
preventDefault
Stopeventpropagation
dispatchEvent
Thenameofancustomeventthatshouldbedispatchedwheneventoccurs
trackFocus
Trackcurrentfocusifonthetargetnode
doNotReplay
Nonotreplaytheseevents
attributeName
Onlyusedbytheattributesstrategytoidentifythenameoftheattributethatwillhavealltheeventsthatneed
toberecorded(defaultvalueis'prebootevents')
eventsBySelector
Thisisonlyusedbytheselectorsstrategy.Itshouldbeanobjectthatmapsaselector
stringtoanarrayofevents.
action
Customfunctionexecutedwheneventsoccur

Eachstrategywillreturnanarrayofobjectswithtwovalues:eventName(nameoftheeventthatoccurred)andnode(theDOM
elementnodeonwhichtheeventoccurred).

Replay Strategies
The'replay'optioncaneitherbeastring(thenameoftheprebuiltstrategy),configurationobject(seebelow)oranarrayof
configurationobjects.

Eachconfigurationobjectmusthaveoneoftwovalues:

name
Thenameofthestrategy(seebelow)
replayEvents
Acustomstrategyimplementation

TheprebuiltstrategyorcustomreplayEventsimplementationwillattempttoreplayalleventspassedin.
If,however,anyeventscan'tbereplayedforanyreason,theycanbereturnedinanarray.Ifthereis
anarrayofreplaystrategiesdefinedforpreboot,theremainingeventsfromonereplaystrategywillbe
feedintothenext.

Theprebuiltreplaystrategiesare:

hydrate
Thisassumesthattheserverviewandtheclientviewarethesame.Inotherwords,theDOMelementsinmemory
fortheserverviewarestilltherewiththeclientview.So,whenreplayingevents,wecansimplyusetheexistingnodesin
memory.Easypeasy.
rerender
Duringarerender,theclientviewtypicallyblowstheserverviewaway.Thiswouldmeanthatthenodeswehave
inmemoryarenolongervalid.However,wecanusethenodesinmemorytohelpfindthenewclientrenderednodes.Once
wedo,wereplaytheevents,setfocus,etc.

Freeze Strategies
Althoughwewanttogivetheusersomefunctionalitybeforetheclientsidewebappbootstrapiscomplete,itmakessensetofreeze
theUIwhencertainthingshappenonthepage.Forexample,iftheuserfillsinaformandhits'submit'wedon'twanttheusertobe
abletodoanythingonthepageuntiltheclientsidewebapphastheopportunitytoprocesstheform.Typicallythistypeofthing
includesanoverlayand/oraspinner.Theideabehindthefreezestrategyistocustomizehowanoverlayand/orspinner
worksandhowitlooks.

NOTE:Youcanalsocustomizethestyleoftheoverlayandspinnerbysimplyoverriding/replacingtheCSSfilethatcomeswiththis
libraryinthedistfolder.

Future Items
Thissectioncontainsitemsthatarepartofthisinitiativebutwillnotbeexploreduntilaftertheinitialsolutionasdescribedaboveis
deliveredandwidelyavailable.

NonJS server rendering


Wewillgetintothisafterthedesignforothercomponentsaremorebaked,butthekeyfornonJSrenderingwillbeeitherstatically
analyzingawebapporpotentiallyusingsomethinglike
Nashorn
toexecuteJavaScriptinJava.

Packaging service
Oncethemainrenderingsolutiondesignisinplace,wecandiveintothepackagingservicewhichwouldbeusedtoimplementlazy
loadingandlowertheactualloadtimeofthewebapp.

Notes
Thissectioncontainsnotesandbrainstormingfrommeetingsthathavenotbeenfullyintegratedintotherestofthedesigndocyet.
Thissectionwilleventuallyberemoved.

Restrictions:
supportnonJSbackends,astheyarethehardestandmakethesolutiongeneral
shouldbeonline,assumingthattheresultisdependingonrequestparametersthatcannotbeenumerated
e.g.becausetheycontainuserinput,...
supportprerenderingnotonlyforinitialpagebutforanyviewlateron
supportlazyloadingofthecomponentcodethatwilltakeovertheprerenderedareasoftheapplication
needstocaptureandreplayusereventsuntilthecomponenthaswokenup
willreducenetworksizeoftheapp
supportdelayedwakeupofcomponents
e.g.foralongthreadofmessages,wemightonlyneedtowakeupthecomponentthattheuserclickedon
triggers:
wakeuponspecifiedevents
wakeuponchangeofaspecifiedexpression
wakeupwhencodeforcomponenthasbeenloaded

Benchmarkdetails
makeaslittlerequestsaspossible>concatenatesourcefiles
estimatenetworktimebasedontransferredamounttogetstablenumbersthatalsoincorporatethenetworktraffic
togetthedata,createbenchmarksinAngular2andaddmetricstobenchpress

Mainideas:
reusetemplate,butnotapplicationlogicontheserver
fromtheloadedcomponent'sperspectiveitshouldbethesamewhetheritwasloadedviatherouterorprerendered
usesamemechanismastherouterforlazyloading(i.e.dynamiccomponents)
usesamemechanismforpassingdatatothecomponent(e.g.programmaticdatabinding(notthereyet),oraservice)

Implications
ForeverycomponentthatshouldbeprerenderedthereneedstobenonJScodeaswell
NonJSbackendneedstogenerate2setsofdata
onesetofdatathatshouldbesenttotheclientforwakeup
onesetofdatathatrepresentsthecorrectlyformatteddataforallvaluesintheviewthatshouldberendered

Offline:extractmetadatafromdirectivesandprecompiletemplates
thisneedstorunJStocalculatethevaluesoftheannotations(astheymightcontainListconcatenation,)
thisneedstobeimplementedinJSasitneedstoevaluatethemoduletogetthecorrectvaluesfortheannotations
referencestootherdirectives(e.g.fromthe@Templateannotation)needtobereplacedwithpathstothesemodules
importsofthemoduleneedtobeanalyzed...

Online:renderusingagenericrenderserver
NonJSbackendloadsdata,sendsdirectivemetadata+precompiledtemplates+datatogenericrenderserver
Asrenderserverisgeneric,itcanbeimplementedinJS(e.g.canruninthecloud,parallelized,)
asthelogicissimple,itispossibletoreimplementitalsoinaNonJSlanguage,althoughthiswouldbemorework
Downside:NonJSbackendneedstogenerate2setsofdata
onesetofdatathatshouldbesenttotheclientforwakeup
onesetofdatathatrepresentsthecorrectlyformatteddataforallvaluesintheviewthatshouldberendered

Developmentmode:verifythatthe2datasetsfromthenonJSbackendmatchup
comparethevaluesthatthecomponentsendstotherendererwiththevaluesthatthenonJSbackendsenttotherenderer
duringprerendering

Vous aimerez peut-être aussi