maui-hot-reload-diagnostics
npx skills add https://github.com/davidortinau/maui-skills --skill maui-hot-reload-diagnostics
Agent 安装分布
Skill 文档
.NET MAUI Hot Reload Diagnostics
Systematically diagnose Hot Reload failures for .NET MAUI apps.
Quick Diagnosis Checklist
- Identify what’s failing: XAML Hot Reload (
.xamlchanges) vs C# Hot Reload (.cschanges) - Check run configuration: Must be Debug config, started with F5/debugger attached
- Save file and re-execute code path: C# changes require re-triggering the code
- Check Hot Reload output: View > Output > “Hot Reload” (VS) or “C# Hot Reload” (VS Code)
Environment Variables for Diagnostics
Enable detailed logging
# Mac/Linux - Edit and Continue logs
export Microsoft_CodeAnalysis_EditAndContinue_LogDir=/tmp/HotReloadLog
# Windows
set Microsoft_CodeAnalysis_EditAndContinue_LogDir=%temp%\HotReloadLog
# XAML Hot Reload logging
export HOTRELOAD_XAML_LOG_MESSAGES=1
# Xamarin-style debug logging (legacy, may help)
export XAMARIN_HOT_RELOAD_SHOW_DEBUG_LOGGING=1
Check if variables are set
# Mac/Linux
env | grep -i hotreload
env | grep -i EditAndContinue
# Windows PowerShell
Get-ChildItem Env: | Where-Object { $_.Name -match "hotreload|EditAndContinue" }
File Encoding Requirement
CRITICAL: All .cs files must be UTF-8 with BOM encoding.
Check encoding
# Check if file has BOM (should show "UTF-8 Unicode (with BOM)")
file -I *.cs
# Find files without BOM
find . -name "*.cs" -exec sh -c 'head -c 3 "$1" | od -An -tx1 | grep -q "ef bb bf" || echo "$1"' _ {} \;
Fix encoding (convert to UTF-8 with BOM)
# Single file
sed -i '1s/^\(\xef\xbb\xbf\)\?/\xef\xbb\xbf/' file.cs
# Or use VS Code: Open file > Save with Encoding > UTF-8 with BOM
VS Code Settings
Enable in VS Code settings (search “Hot Reload”):
{
"csharp.experimental.debug.hotReload": true,
"csharp.debug.hotReloadOnSave": true,
"csharp.debug.hotReloadVerbosity": "detailed"
}
Visual Studio Settings
- Tools > Options > Debugging > .NET/C++ Hot Reload
- Enable: Enable Hot Reload, Apply on file save
- Set Logging verbosity to Detailed or Diagnostic
MetadataUpdateHandler
For custom hot reload handling (e.g., MauiReactor), implement MetadataUpdateHandler:
[assembly: System.Reflection.Metadata.MetadataUpdateHandler(typeof(HotReloadService))]
internal static class HotReloadService
{
// Called when hot reload clears cached metadata
public static void ClearCache(Type[]? updatedTypes) { }
// Called after hot reload updates are applied
public static void UpdateApplication(Type[]? updatedTypes)
{
// Trigger UI refresh here
MainThread.BeginInvokeOnMainThread(() =>
{
// Refresh your UI framework
});
}
}
Verify MetadataUpdateHandler is registered
# Search for handler in codebase
grep -rn "MetadataUpdateHandler" --include="*.cs"
# Check assembly attributes
grep -rn "assembly:.*MetadataUpdateHandler" --include="*.cs"
MauiReactor-Specific Hot Reload
MauiReactor v3+ uses .NET’s feature switch pattern for hot reload (no code call needed).
Setup (MauiReactor v3+)
Add to your .csproj file:
<ItemGroup Condition="'$(Configuration)'=='Debug'">
<RuntimeHostConfigurationOption Include="MauiReactor.HotReload" Value="true" Trim="false" />
</ItemGroup>
<!-- For Release builds (AOT compatibility) -->
<ItemGroup Condition="'$(Configuration)'=='Release'">
<RuntimeHostConfigurationOption Include="MauiReactor.HotReload" Value="false" Trim="true" />
</ItemGroup>
Note: If migrating from MauiReactor v2, remove the EnableMauiReactorHotReload() call from MauiProgram.cs.
Check MauiReactor hot reload setup
# Verify RuntimeHostConfigurationOption in csproj
grep -A2 "MauiReactor.HotReload" *.csproj
# Ensure EnableMauiReactorHotReload is NOT present (v3+)
grep -rn "EnableMauiReactorHotReload" --include="*.cs" && echo "WARNING: Remove this call for v3+"
MauiReactor hot reload requirements
RuntimeHostConfigurationOptionset in.csproj(not a code call)- Debug configuration
- Debugger attached (F5)
- Works on all platforms (iOS, Android, Mac Catalyst, Windows)
- Works in VS Code and Visual Studio
C# Markup (CommunityToolkit.Maui.Markup) Hot Reload
C# Markup apps need the ICommunityToolkitHotReloadHandler to refresh UI on hot reload.
Setup
-
Add the NuGet package:
CommunityToolkit.Maui.Markup -
Enable in MauiProgram.cs:
var builder = MauiApp.CreateBuilder();
builder
.UseMauiApp<App>()
.UseMauiCommunityToolkitMarkup(); // Enables hot reload support
- Implement the handler interface on pages/views that need refresh:
public partial class MainPage : ContentPage, ICommunityToolkitHotReloadHandler
{
public MainPage()
{
Build();
}
void Build() => Content = new VerticalStackLayout
{
Children =
{
new Label().Text("Hello, World!"),
new Button().Text("Click Me")
}
};
// Called by hot reload - rebuild UI
void ICommunityToolkitHotReloadHandler.OnHotReload() => Build();
}
Check C# Markup hot reload setup
# Verify package reference
grep -i "CommunityToolkit.Maui.Markup" *.csproj
# Check for UseMauiCommunityToolkitMarkup in MauiProgram.cs
grep -n "UseMauiCommunityToolkitMarkup" MauiProgram.cs
# Find classes implementing ICommunityToolkitHotReloadHandler
grep -rn "ICommunityToolkitHotReloadHandler" --include="*.cs"
Key points for C# Markup hot reload
- Extract UI building into a separate
Build()method - Implement
ICommunityToolkitHotReloadHandleron any page/view needing refresh - The
OnHotReload()method is called automatically after C# hot reload - Works alongside standard C# Hot Reload (method body changes)
Blazor Hybrid Hot Reload
Blazor Hybrid apps in MAUI have their own hot reload behavior for .razor and .css files.
How Blazor Hybrid hot reload works
- Razor components (
.razor): Changes to markup and C# code blocks reload automatically - CSS files (
.css): Style changes apply immediately - C# code-behind (
.razor.cs): Uses standard C# Hot Reload rules - Shared C# code: Standard C# Hot Reload applies
Setup requirements
- Debug configuration (not Release)
- Debugger attached (F5, not Ctrl+F5)
- For Visual Studio: Ensure “Hot Reload on File Save” is enabled
Check Blazor Hybrid setup
# Verify BlazorWebView is configured
grep -rn "BlazorWebView" --include="*.xaml" --include="*.cs"
# Check for _Imports.razor
find . -name "_Imports.razor"
# Verify wwwroot exists
ls -la */wwwroot/ 2>/dev/null || ls -la wwwroot/ 2>/dev/null
Blazor Hybrid hot reload limitations
- Adding new components: May require restart
- Changing component parameters: Usually works
- Modifying
@injectservices: May require restart - Static asset changes (images, fonts): Require restart
- Changes to
Program.csorMauiProgram.cs: Always require restart
Troubleshooting Blazor Hybrid
-
Razor changes not applying:
- Ensure file is saved
- Check browser dev tools console (if available) for errors
- Verify the component is actually being rendered
-
CSS changes not applying:
- Hard refresh may be needed (changes cached)
- Check CSS isolation (
.razor.css) is properly linked
-
Partial updates / flickering:
- This is normal for Blazor’s diff-based rendering
- State may reset if component re-initializes
Environment variable for Blazor debugging
# Enable detailed Blazor logging
export ASPNETCORE_ENVIRONMENT=Development
Common Issues and Fixes
Issue: “Nothing happens when I save”
- Verify Debug configuration (not Release)
- Check Hot Reload output for errors
- Ensure file is saved (not just modified)
- Re-execute the code path (navigate again, tap button again)
Issue: “Unsupported edit” / “Rude edit”
Some changes require app restart:
- Adding/removing methods, fields, properties
- Changing method signatures
- Modifying static constructors
- Changes to generics
Issue: XAML changes don’t apply (iOS)
- Set Linker to Don’t Link in iOS build settings
- Config must be named exactly Debug
- Don’t use
XamlCompilationOptions.Skip
Issue: Changes apply but UI doesn’t update
- For C#: Must re-trigger the code (re-navigate, re-tap)
- Check for cached binding values or state
- Verify you’re editing the correct target framework file
Diagnostic Commands
Collect full diagnostic bundle
# 1. Environment info
dotnet --info > dotnet-info.txt
dotnet workload list > workloads.txt
# 2. Build with binary log
dotnet build -bl:build.binlog -c Debug
# 3. Check for encoding issues
find . -name "*.cs" -path "*/src/*" | head -20 | xargs file
# 4. Check hot reload env vars
env | grep -iE "(hotreload|editandcontinue|xamarin.*debug)" || echo "No hot reload env vars set"
Enable all diagnostic logging then reproduce
export Microsoft_CodeAnalysis_EditAndContinue_LogDir=/tmp/HotReloadLog
export HOTRELOAD_XAML_LOG_MESSAGES=1
# Launch IDE from this terminal, reproduce issue, then check /tmp/HotReloadLog/