Source Generators
Moongate uses source generators to move registration and mapping work from runtime to compile-time. This improves startup predictability, reduces reflection-heavy paths, and helps NativeAOT compatibility.
Why We Use Generators
- Remove manual opcode/registration duplication.
- Keep runtime bootstrap deterministic.
- Reduce reflection-based discovery in hot startup paths.
- Keep AOT behavior stable by emitting explicit code.
Current Generators
Moongate now uses a single generator project: Moongate.Generators.
It contains these generators:
Packet Table Generator
- Input: packet classes decorated with
[PacketHandler(...)] - Output:
- generated packet-table registration (
PacketTable.RegisterGenerated(...)) - generated opcode constants (
PacketDefinition)
- generated packet-table registration (
Packet Listener Registration Generator
- Input: listener classes decorated with
[RegisterPacketHandler(...)] - Output:
- generated bootstrap listener wiring (
BootstrapPacketHandlerRegistration.RegisterGenerated(...)) - compile-time mapping
opcode -> RegisterPacketHandler<TListener>(...)
- generated bootstrap listener wiring (
Game Event Listener Registration Generator
- Input: listener classes decorated with
[RegisterGameEventListener]and implementing one or moreIGameEventListener<TEvent> - Output:
- generated bootstrap game-event subscription wiring (
BootstrapGameEventListenerRegistration.SubscribeGenerated(...)) - compile-time mapping
listener -> RegisterListener<TEvent>(...)
- generated bootstrap game-event subscription wiring (
Console Command Registration Generator
- Input: command classes decorated with
[RegisterConsoleCommand(...)]and implementingICommandExecutor - Output:
- generated DI singleton registrations (
BootstrapConsoleCommandRegistration.RegisterServicesGenerated(...)) - generated command bindings (
BootstrapConsoleCommandRegistration.RegisterCommandsGenerated(...)) - compile-time mapping
attribute metadata -> ICommandSystemService.RegisterCommand(...)
- generated DI singleton registrations (
Metrics Mapper Generator
- Input: snapshot properties decorated with metric metadata
- Output:
- generated metric mapper extensions used by collection/HTTP export
Script Module Registration Generator
- Input: classes in
Moongate.ScriptingandMoongate.Serverdecorated with[ScriptModule(...)] - Output:
- generated
Moongate.Scripting.Generated.ScriptModuleRegistry.Register(...) - compile-time registration of script modules in DryIoc
- generated
Version Metadata Generator
- Input:
Moongate.Serverproject properties (Version,Codename) - Output:
- generated
Moongate.Server.Data.Version.VersionUtils - strongly-typed version/codename values for runtime bootstrap usage
- generated
File Loader Registration Generator
- Input: classes implementing
IFileLoaderdecorated with[RegisterFileLoader] - Output:
- generated
BootstrapFileLoaderRegistration.RegisterGenerated(...) - compile-time registration of file loaders in DryIoc
- generated
Lua User Data Registration Generator
- Input: classes decorated with
[MoonSharpUserData]or similar Lua binding attributes - Output:
- generated Lua user data type registrations for MoonSharp engine
- compile-time binding of .NET types as Lua user data
Runtime Flow
- Build compiles generators and emits generated C# files.
- Runtime projects consume generated artifacts through analyzer references.
- At runtime:
- packet descriptors come from generated packet table registration.
- listener wiring comes from generated bootstrap registration.
- game-event listeners are subscribed from generated bootstrap registration.
- command executors are registered and bound from generated console command registration.
- metric snapshots are mapped through generated mappers.
- script modules are registered through generated script module registry.
- file loaders are registered through generated bootstrap file loader registration.
- Lua user data types are registered through generated Lua user data registry.
- version/codename are read from generated
VersionUtils.
Notes
- Generators are implementation tools and are excluded from DocFX API metadata output.
- Public runtime APIs remain documented under normal module namespaces.
Previous: Solution Structure | Next: Network System