Open sandboxFocusImprove this doc

Compilation pipeline

Step 1: Initialization

  1. Generate the compile-time compilation:
    1. Identify and load referenced compile-time projects.
    2. Identify compile-time code in the current compilation and create a separate compile-time compilation.
      1. Transform templates into code generating Roslyn syntax trees.
      2. Transform nameof and typeof expressions to make them independent from run-time references.
  2. Initialize aspect classes:
    1. Create a prototype instance of each aspect class using FormatterServices.GetUninitializedObject.
    2. Execute the BuildEligibility method and discover the aspect layers.
    3. Discover aspect ordering relationships in the current project and all referenced assemblies.
    4. Order aspect layers.

Step 2: Applying aspects

For each aspect layer, in order of application (inverse order of execution, see Ordering aspects):

  • For the default aspect layer:

    • Evaluate aspect sources for this aspect type, resulting in a set of target declarations.
    • Visit target declarations in breadth-first order of depth level. For each target declaration:
      • Instantiate the aspect.
      • Invoke the BuildAspect method.
      • Add advice to the subsequent steps of the pipeline.
  • For all aspect layers and for all target declarations visited in breadth-first order:

    • Execute advice. Advice can provide observable or non-observable transformations (or both):
      • Observable transformations are transformations observable from outside, for instance, adding a new type member or adding a method parameter.
      • Non-observable transformations are transformations that only affect the implementation of declarations (for example, overriding a method).
  • Before executing the next aspect layer or the next visiting depth, create a new code model version incrementally from the previous version, which includes all observable transformations added by advice.

Step 3: Transforming the compilation

Before this step, the algorithm collected transformations, but the compilation was never modified.

The subsequent actions depend on whether the pipeline runs at design time or at compile time.

Compile time

  1. Introduce all transformations (observable and non-observable) into a new compilation. Expand templates during this step.
  2. Link the code together and inline where possible.

Design time

At design time, Metalama ignores non-observable transformations and creates partial files for observable transformations. Templates are never executed at design time.