You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
The Release publish currently runs with <PublishTrimmed>False</PublishTrimmed>. Enabling trimming would shrink the self-contained payload by an expected 30-50% on top of the wins already shipped in PR #19, taking the MSI down to roughly 30-40 MB (the bitwarden Command Palette reference produces a 20 MB MSI for a comparable WinUI 3 app shape).
Attempted this in PR #19 and reverted: with PublishTrimmed=true and TrimMode=partial, the .NET 10 trimmer hard-strips System.StubHelpers.InterfaceMarshaler (and friends) when classic-COM interop is reachable, even with:
An explicit TrimmerRootDescriptor rooting System.StubHelpers.InterfaceMarshaler, StubHelpers, MngdRefCustomMarshaler, etc., plus NAudio.Core, NAudio.Wasapi, and Earmark.Audio.
The trimmer prints IL2026: Built-in COM support is not trim compatible (https://aka.ms/dotnet-illink/com), and the runtime then throws TypeLoadException: Could not load type 'System.StubHelpers.InterfaceMarshaler' on the first MMDeviceEnumerator constructor call.
Proposed Solution
Land #22 (own classic-COM interop) and #23 (NAudio.CoreAudioApi side) first, then re-enable trimming:
Set <PublishTrimmed>true</PublishTrimmed> and <TrimMode>partial</TrimMode> in src/Earmark.App/Earmark.App.csproj.
Turn on <EnableTrimAnalyzer>true</EnableTrimAnalyzer> and fix any IL2026/IL2072 warnings in our own code (the JSON path is already trim-safe via the JsonSerializerContext pair landed in perf(installer): shrink MSI size #19; expect a small handful of additional sites).
Set <ILLinkTreatWarningsAsErrors>false</ILLinkTreatWarningsAsErrors> so the rolled-up library trim warnings (CsWinRT, .NET WinRT projection, System.Drawing.Common rollup via System.Private.Windows.Core) don't block the build.
Validate the trimmed publish:
No new IL2xxx warnings on our code at build time.
App launches from the MSI install dir, parks in the tray, surfaces the main window via secondary activation.
Log shows Audio services initialized, Activated factory ... as Win11 layout, and Applied rule ... lines, i.e. the COM paths still execute.
Update CLAUDE.md ## Build, run, and iterate so the inner-loop publish command no longer carries the trimming-disabled caveat.
Alternatives Considered
Workarounds with the existing classic-COM code. Tried BuiltInComInteropSupport=true, the Trim=\"false\" host configuration option, and a TrimmerRootDescriptor covering System.Private.CoreLib's System.StubHelpers.* types and entire-assembly preserves for NAudio.Core / NAudio.Wasapi / Earmark.Audio. None worked: see PR perf(installer): shrink MSI size #19's reverted commits for the full sequence. Microsoft's official guidance at https://aka.ms/dotnet-illink/com is to migrate to ComWrappers.
Native AOT instead of trimmed self-contained. WinUI 3 unpackaged + Native AOT is not yet supported by Microsoft.WindowsAppSDK 1.8 in a way Earmark could ship. Re-evaluate when WAS adds first-class AOT support.
Reference pattern: HoobiBitwardenCommandPaletteExtension.csproj ships with PublishTrimmed=true, IsAotCompatible=true, CsWinRTAotOptimizerEnabled=true, and ILLinkTreatWarningsAsErrors=false in Release. That config produces a 20 MB MSI for a similarly-shaped WinUI 3 app.
Problem
The Release publish currently runs with
<PublishTrimmed>False</PublishTrimmed>. Enabling trimming would shrink the self-contained payload by an expected 30-50% on top of the wins already shipped in PR #19, taking the MSI down to roughly 30-40 MB (the bitwarden Command Palette reference produces a 20 MB MSI for a comparable WinUI 3 app shape).Attempted this in PR #19 and reverted: with
PublishTrimmed=trueandTrimMode=partial, the .NET 10 trimmer hard-stripsSystem.StubHelpers.InterfaceMarshaler(and friends) when classic-COM interop is reachable, even with:<BuiltInComInteropSupport>true</BuiltInComInteropSupport><RuntimeHostConfigurationOption Include=\"System.Runtime.InteropServices.BuiltInComInterop.IsSupported\" Value=\"true\" Trim=\"false\" />TrimmerRootDescriptorrootingSystem.StubHelpers.InterfaceMarshaler,StubHelpers,MngdRefCustomMarshaler, etc., plusNAudio.Core,NAudio.Wasapi, andEarmark.Audio.The trimmer prints
IL2026: Built-in COM support is not trim compatible(https://aka.ms/dotnet-illink/com), and the runtime then throwsTypeLoadException: Could not load type 'System.StubHelpers.InterfaceMarshaler'on the firstMMDeviceEnumeratorconstructor call.Proposed Solution
Land #22 (own classic-COM interop) and #23 (NAudio.CoreAudioApi side) first, then re-enable trimming:
<PublishTrimmed>true</PublishTrimmed>and<TrimMode>partial</TrimMode>insrc/Earmark.App/Earmark.App.csproj.<EnableTrimAnalyzer>true</EnableTrimAnalyzer>and fix any IL2026/IL2072 warnings in our own code (the JSON path is already trim-safe via theJsonSerializerContextpair landed in perf(installer): shrink MSI size #19; expect a small handful of additional sites).<ILLinkTreatWarningsAsErrors>false</ILLinkTreatWarningsAsErrors>so the rolled-up library trim warnings (CsWinRT, .NET WinRT projection,System.Drawing.Commonrollup viaSystem.Private.Windows.Core) don't block the build.Audio services initialized,Activated factory ... as Win11 layout, andApplied rule ...lines, i.e. the COM paths still execute.## Build, run, and iterateso the inner-loop publish command no longer carries the trimming-disabled caveat.Alternatives Considered
BuiltInComInteropSupport=true, theTrim=\"false\"host configuration option, and aTrimmerRootDescriptorcoveringSystem.Private.CoreLib'sSystem.StubHelpers.*types and entire-assembly preserves forNAudio.Core/NAudio.Wasapi/Earmark.Audio. None worked: see PR perf(installer): shrink MSI size #19's reverted commits for the full sequence. Microsoft's official guidance at https://aka.ms/dotnet-illink/com is to migrate to ComWrappers.Microsoft.WindowsAppSDK1.8 in a way Earmark could ship. Re-evaluate when WAS adds first-class AOT support.Additional Context
HoobiBitwardenCommandPaletteExtension.csprojships withPublishTrimmed=true,IsAotCompatible=true,CsWinRTAotOptimizerEnabled=true, andILLinkTreatWarningsAsErrors=falsein Release. That config produces a 20 MB MSI for a similarly-shaped WinUI 3 app.Checklist