fix(di): use factory lambdas for internal-ctor services
C3 bootstrap throws "A suitable constructor for type HellionChat.Ipc.ExtraChat could not be located" because Microsoft.Extensions.DependencyInjection's ActivatorUtilities only binds to PUBLIC constructors via reflection. ExtraChat is a public class with an internal ctor; Commands and StatusBar are internal classes whose implicit default ctor inherits class accessibility (internal); every IHostedService adapter is `internal sealed class X(deps)` with a primary ctor that is also internal. The fix routes all eight singletons and all seven hosted-service adapters through factory lambdas. `new T(...)` inside the PluginHostFactory namespace sees the internal surface, so the container never has to reflect over internal ctors.
This commit is contained in:
@@ -86,14 +86,22 @@ internal static class PluginHostFactory
|
|||||||
// constraint; ctors that need a Plugin backref go through a factory
|
// constraint; ctors that need a Plugin backref go through a factory
|
||||||
// lambda that resolves Plugin from the container.
|
// lambda that resolves Plugin from the container.
|
||||||
// -----------------------------------------------------------------
|
// -----------------------------------------------------------------
|
||||||
services.AddSingleton<IPlatformUtil, DalamudPlatformUtil>();
|
// Factory lambdas across the board: Microsoft.Extensions.DependencyInjection's
|
||||||
services.AddSingleton<IPluginLogProxy, DalamudPluginLogProxy>();
|
// ActivatorUtilities only inspects PUBLIC constructors via reflection,
|
||||||
services.AddSingleton<FileDialogManager>();
|
// and several HellionChat classes are `internal sealed` with implicit-
|
||||||
services.AddSingleton<Commands>();
|
// internal default ctors (Commands, StatusBar) or explicitly `internal`
|
||||||
services.AddSingleton<FontManager>();
|
// ctors on public classes (ExtraChat). The lambda body compiles inside
|
||||||
services.AddSingleton<StatusBar>();
|
// the HellionChat namespace, so `new T()` sees the internal surface.
|
||||||
services.AddSingleton<IpcManager>();
|
services.AddSingleton<IPlatformUtil>(_ => new DalamudPlatformUtil());
|
||||||
services.AddSingleton<ExtraChat>();
|
services.AddSingleton<IPluginLogProxy>(sp => new DalamudPluginLogProxy(
|
||||||
|
sp.GetRequiredService<IPluginLog>()
|
||||||
|
));
|
||||||
|
services.AddSingleton<FileDialogManager>(_ => new FileDialogManager());
|
||||||
|
services.AddSingleton(_ => new Commands());
|
||||||
|
services.AddSingleton(_ => new FontManager());
|
||||||
|
services.AddSingleton(_ => new StatusBar());
|
||||||
|
services.AddSingleton(_ => new IpcManager());
|
||||||
|
services.AddSingleton(_ => new ExtraChat());
|
||||||
|
|
||||||
services.AddSingleton(sp => new ThemeRegistry(
|
services.AddSingleton(sp => new ThemeRegistry(
|
||||||
Path.Combine(
|
Path.Combine(
|
||||||
@@ -149,13 +157,31 @@ internal static class PluginHostFactory
|
|||||||
// making the services themselves implement IHostedService (Lightless'
|
// making the services themselves implement IHostedService (Lightless'
|
||||||
// pattern) — DI-2a leaves service classes untouched.
|
// pattern) — DI-2a leaves service classes untouched.
|
||||||
// -----------------------------------------------------------------
|
// -----------------------------------------------------------------
|
||||||
services.AddHostedService<FontManagerInitHostedService>();
|
// Same internal-ctor pitfall as the singletons above - the adapter
|
||||||
services.AddHostedService<ThemeRegistryInitHostedService>();
|
// classes are `internal sealed` with primary constructors, so the
|
||||||
services.AddHostedService<IpcManagerInitHostedService>();
|
// direct AddHostedService<T>() overload's ActivatorUtilities fails.
|
||||||
services.AddHostedService<TypingIpcInitHostedService>();
|
services.AddHostedService(sp => new FontManagerInitHostedService(
|
||||||
services.AddHostedService<ExtraChatInitHostedService>();
|
sp.GetRequiredService<FontManager>()
|
||||||
services.AddHostedService<MessageManagerInitHostedService>();
|
));
|
||||||
services.AddHostedService<AutoTellTabsServiceInitHostedService>();
|
services.AddHostedService(sp => new ThemeRegistryInitHostedService(
|
||||||
|
sp.GetRequiredService<ThemeRegistry>()
|
||||||
|
));
|
||||||
|
services.AddHostedService(sp => new IpcManagerInitHostedService(
|
||||||
|
sp.GetRequiredService<IpcManager>()
|
||||||
|
));
|
||||||
|
services.AddHostedService(sp => new TypingIpcInitHostedService(
|
||||||
|
sp.GetRequiredService<TypingIpc>()
|
||||||
|
));
|
||||||
|
services.AddHostedService(sp => new ExtraChatInitHostedService(
|
||||||
|
sp.GetRequiredService<ExtraChat>()
|
||||||
|
));
|
||||||
|
services.AddHostedService(sp => new MessageManagerInitHostedService(
|
||||||
|
sp.GetRequiredService<IDalamudPluginInterface>(),
|
||||||
|
sp.GetRequiredService<MessageManager>()
|
||||||
|
));
|
||||||
|
services.AddHostedService(sp => new AutoTellTabsServiceInitHostedService(
|
||||||
|
sp.GetRequiredService<AutoTellTabsService>()
|
||||||
|
));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user