dotnet-source-generators
.NET source generators
A source generator is a compiler plugin: it runs during the build, reads the code being compiled, and adds new C# to that same compilation. It cannot mutate what you wrote - it only appends partial members, new types, or attributes. The payoff is moving work that would otherwise happen with runtime reflection (or by hand) to compile time, where it is faster, AOT-safe, and visible to the IDE. Baseline is .NET 8 / C# 12; the generator's own language conventions follow csharp.
First question: does a framework generator already do this?
Most teams never need to write a generator. The .NET BCL ships several, and each replaces a reflection-heavy pattern with generated, trim-friendly code. Reach for these before authoring anything:
[GeneratedRegex]- apartialmethod returningRegex, compiled at build time. Use it overnew Regex(pattern)for any pattern that lives in source. The generatedRegexskips the interpreter and the static-cache lookup, and the pattern is validated at build, not on first call.[LoggerMessage]- apartiallogging method that emits theILoggercall with zero boxing and no message-template parsing at runtime. Use it for hot or structured log paths instead oflogger.LogInformation("...", a, b).- The
System.Text.Jsoncontext - apartial class : JsonSerializerContextannotated with[JsonSerializable(typeof(T))], passed to serialize/deserialize. This removes the reflection metadata walk and is what makes JSON work under Native AOT and trimming.
These are configuration, not engineering. Add the attribute, mark the member or type partial, and the compiler fills in the body. Write a custom generator only when no built-in covers the shape you need.
Authoring: the non-negotiable foundation
If you do author one, the rules below are not stylistic - violating them produces a generator that is slow in the IDE, breaks in CI, or silently caches stale output. The mechanics that satisfy them - project file, packaging layout, the trigger pipeline, model shapes, emit details - are in references/authoring.md; load it when actually writing or reviewing generator code.