< Summary

Information
Class: NexusLabs.Needlr.Generators.CodeGen.BootstrapCodeGenerator
Assembly: NexusLabs.Needlr.Generators
File(s): /home/runner/work/needlr/needlr/src/NexusLabs.Needlr.Generators/CodeGen/BootstrapCodeGenerator.cs
Line coverage
100%
Covered lines: 61
Uncovered lines: 0
Coverable lines: 61
Total lines: 121
Line coverage: 100%
Branch coverage
100%
Covered branches: 16
Total branches: 16
Branch coverage: 100%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
GenerateModuleInitializerBootstrapSource(...)100%1616100%

File(s)

/home/runner/work/needlr/needlr/src/NexusLabs.Needlr.Generators/CodeGen/BootstrapCodeGenerator.cs

#LineLine coverage
 1// Copyright (c) NexusLabs. All rights reserved.
 2// Licensed under the MIT License.
 3
 4using System.Collections.Generic;
 5using System.Text;
 6
 7namespace NexusLabs.Needlr.Generators.CodeGen;
 8
 9/// <summary>
 10/// Generates the <c>NeedlrSourceGenBootstrap.g.cs</c> module initializer file.
 11/// </summary>
 12internal static class BootstrapCodeGenerator
 13{
 14    /// <summary>
 15    /// Emits the module-initializer bootstrap source that registers TypeRegistry
 16    /// identity and callbacks and runs referenced TypeRegistry module constructors.
 17    /// </summary>
 18    internal static string GenerateModuleInitializerBootstrapSource(string assemblyName, IReadOnlyList<string> reference
 19    {
 56020        var builder = new StringBuilder();
 56021        var safeAssemblyName = GeneratorHelpers.SanitizeIdentifier(assemblyName);
 22
 56023        breadcrumbs.WriteFileHeader(builder, assemblyName, "Needlr Source-Gen Bootstrap");
 56024        builder.AppendLine("#nullable enable");
 56025        builder.AppendLine();
 56026        builder.AppendLine("using Microsoft.Extensions.Configuration;");
 56027        builder.AppendLine("using Microsoft.Extensions.DependencyInjection;");
 56028        builder.AppendLine();
 56029        builder.AppendLine($"namespace {safeAssemblyName}.Generated;");
 56030        builder.AppendLine();
 56031        builder.AppendLine("internal static class NeedlrSourceGenModuleInitializer");
 56032        builder.AppendLine("{");
 56033        builder.AppendLine("    [global::System.Runtime.CompilerServices.ModuleInitializer]");
 56034        builder.AppendLine("    internal static void Initialize()");
 56035        builder.AppendLine("    {");
 36
 37        // Generate the referenced-module initialization call when dependencies have registries.
 56038        if (referencedAssemblies.Count > 0)
 39        {
 1840            builder.AppendLine("        // Run referenced module constructors so their registries register");
 1841            builder.AppendLine("        ForceLoadReferencedAssemblies();");
 1842            builder.AppendLine();
 43        }
 44
 56045        builder.AppendLine("        global::NexusLabs.Needlr.Generators.NeedlrSourceGenBootstrap.Register(");
 56046        builder.AppendLine($"            typeof(global::{safeAssemblyName}.Generated.TypeRegistry),");
 56047        builder.AppendLine($"            global::{safeAssemblyName}.Generated.TypeRegistry.GetInjectableTypes,");
 56048        builder.AppendLine($"            global::{safeAssemblyName}.Generated.TypeRegistry.GetPluginTypes,");
 49
 50        // Generate the decorator/factory/provider applier lambda
 56051        if (hasFactories || hasProviders)
 52        {
 5553            builder.AppendLine("            services =>");
 5554            builder.AppendLine("            {");
 5555            builder.AppendLine($"                global::{safeAssemblyName}.Generated.TypeRegistry.ApplyDecorators((ISer
 5556            if (hasFactories)
 57            {
 3858                builder.AppendLine($"                global::{safeAssemblyName}.Generated.FactoryRegistrations.RegisterF
 59            }
 5560            if (hasProviders)
 61            {
 1762                builder.AppendLine($"                global::{safeAssemblyName}.Generated.TypeRegistry.RegisterProviders
 63            }
 5564            builder.AppendLine("            },");
 65        }
 66        else
 67        {
 50568            builder.AppendLine($"            services => global::{safeAssemblyName}.Generated.TypeRegistry.ApplyDecorato
 69        }
 70
 71        // Generate the options registrar lambda for NeedlrSourceGenBootstrap (for backward compat)
 56072        if (hasOptions)
 73        {
 16074            builder.AppendLine($"            (services, config) => global::{safeAssemblyName}.Generated.TypeRegistry.Reg
 75        }
 76        else
 77        {
 40078            builder.AppendLine("            null);");
 79        }
 80
 81        // Also register with SourceGenRegistry (for ConfiguredSyringe without Generators.Attributes dependency)
 56082        if (hasOptions)
 83        {
 16084            builder.AppendLine();
 16085            builder.AppendLine("        // Register options with core SourceGenRegistry for ConfiguredSyringe");
 16086            builder.AppendLine($"        global::NexusLabs.Needlr.SourceGenRegistry.RegisterOptionsRegistrar(");
 16087            builder.AppendLine($"            (services, config) => global::{safeAssemblyName}.Generated.TypeRegistry.Reg
 88        }
 89
 56090        builder.AppendLine("    }");
 91
 92        // Generate ForceLoadReferencedAssemblies method if needed
 56093        if (referencedAssemblies.Count > 0)
 94        {
 1895            builder.AppendLine();
 1896            builder.AppendLine("    /// <summary>");
 1897            builder.AppendLine("    /// Runs module constructors for referenced assemblies with");
 1898            builder.AppendLine("    /// [GenerateTypeRegistry], ensuring their registries register.");
 1899            builder.AppendLine("    /// </summary>");
 18100            builder.AppendLine("    /// <remarks>");
 18101            builder.AppendLine("    /// A typeof expression alone does not guarantee module initialization.");
 18102            builder.AppendLine("    /// RunModuleConstructor is idempotent when a dependency was already initialized.");
 18103            builder.AppendLine("    /// </remarks>");
 18104            builder.AppendLine("    private static void ForceLoadReferencedAssemblies()");
 18105            builder.AppendLine("    {");
 106
 74107            foreach (var referencedAssembly in referencedAssemblies)
 108            {
 19109                var safeRefAssemblyName = GeneratorHelpers.SanitizeIdentifier(referencedAssembly);
 19110                builder.AppendLine("        global::System.Runtime.CompilerServices.RuntimeHelpers.RunModuleConstructor(
 19111                builder.AppendLine($"            typeof(global::{safeRefAssemblyName}.Generated.TypeRegistry).Module.Mod
 112            }
 113
 18114            builder.AppendLine("    }");
 115        }
 116
 560117        builder.AppendLine("}");
 118
 560119        return builder.ToString();
 120    }
 121}