Prism Module InitializationMode Comparison


As part of my self-improvement challenge, I have been watching the Introduction to Prism course from PluralSight.
I chose this course so I am better equipped for my teams’ Prism application project at work where I was recently tasked to improve the startup performance.

At this time, the project contains sixty-nine IModule implementation types; however, that number is continuing to grow.
All of these modules will not be loaded at once and some of them may not be used/loaded at all.
Some of them are conditionally loaded during runtime, when certain criteria is met.

While watching the Initializing Modules video I found myself wondering if anything would change if I were to change these conditionally loaded modules InitializationMode from the default WhenReady to OnDemand.
My reasoning behind this is because Brian Lagunas explains that WhenReady initializes modules as soon as possible or OnDemand when the application needs them in the video.
Brian recommends using OnDemand if the module is not required to run, is not always used, and/or is rarely used.

I have a few concerns:

  1. Impacting features because the module is not loaded beforehand or the Module initialization is not done manually.
  2. No performance impact because this project handles module initialization itself in an effort to parallelize it instead of letting Prism manage it.

In the end, only benchmarking each option will provide information to make a decision.
To do this I used JetBrains dotTrace, focusing on the timings for App.OnStartup, Bootstrapper.Run, Bootstrapper.ConfigureModuleCatalog, and Bootstrapper.InitializeModules.
Since we try to load modules in parallel, I ended up adding the timing for this as well - otherwise the timing may have appeared off.

Baseline - InitializationMode.WhenAvailable

The first step was to gather baseline metrics.

Profile #1 Profile #2 Profile #3 Profile #4 Profile #5 Min Average Median Max STD
App.OnStartup 5845 4687 4220 4545 4973 4220 4854 4687 5845 551.6462635
Bootstrapper.Run 5954 3986 2598 3293 2779 2598 3722 3293 5954 1215.581013
Bootstrapper.ConfigureModuleCatalog 1148 767 363 511 1.5 1.5 558.1 511 1148 385.1511911
Bootstrapper.InitializeModules 184 109 117 85 71 71 113.2 109 184 39.0404918
Asynchronous Module Initialization 1821 2233 2311 2571 2564 1821 2300 2311 2571 274.6590614

Not terrible, but not ideal.
The application splash screen is displayed for about 4.5 seconds on average on a developer machine with only a few conditional modules enabled.


With the baseline determined, a comparison can be made when switching the modules to be loaded OnDemand.

Profile #1 Profile #2 Profile #3 Profile #4 Profile #5 Min Average Median Max STD
App.OnStartup 5419 3969 4391 5919 5490 3969 5037.6 5419 5919 733.0750575
Bootstrapper.Run 2770 2197 2017 2086 2238 2017 2261.6 2197 2770 266.0320281
Bootstrapper.ConfigureModuleCatalog 408 374 340 352 388 340 372.4 374 408 24.40983408
Bootstrapper.InitializeModules 143 67 69 69 66 66 82.8 69 143 30.1224169
Asynchronous Module Initialization 1926 1639 1699 1603 1632 1603 1699.8 1639 1926 117.3292802

All the Bootstrapper methods seemed to have improved, but overall the App.OnStartup took approximately the same amount of time.


There was an impact, but not in the overall startup time - which I find a little peculiar.
It seems as though the overhead may have been shifted elsewhere in the startup process.

This may mean that a hybrid approach to Bootstrapper.InitializeModules does have merits although not as much as I had hoped.
Another option may be to change the Bootstrapper.ConfigureModuleCatalog to conditionally determine to add modules instead of applying a ‘safe’ default.
Or perhaps I am diagnosing the wrong problem and should at other options - such as switching Dependency Injection frameworks.

In any case, I am going to discuss this as an option with my team - and see if additional testing can be done with more conditional modules enabled.

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now