From 05a73eff35de60b4f2261d46be93278515445660 Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Wed, 5 Nov 2025 02:04:06 +0000 Subject: [PATCH 01/18] Update dependencies from https://github.com/microsoft/testfx build 20251104.7 On relative base path root Microsoft.Testing.Platform From Version 2.1.0-preview.25553.3 -> To Version 2.1.0-preview.25554.7 MSTest From Version 4.1.0-preview.25553.3 -> To Version 4.1.0-preview.25554.7 --- eng/Version.Details.props | 4 ++-- eng/Version.Details.xml | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index 5980474f1ad2..0e4b1ed8813b 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -142,8 +142,8 @@ This file should be imported by eng/Versions.props 10.0.0-beta.25522.2 10.0.0-beta.25522.2 - 2.1.0-preview.25553.3 - 4.1.0-preview.25553.3 + 2.1.0-preview.25554.7 + 4.1.0-preview.25554.7 diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index 755d740bac77..bda2555be11f 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -553,13 +553,13 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - + https://github.com/microsoft/testfx - b2b75ecb52bcff592001df6d08f5fffccd945fdd + 36a23010d6fb8062381e5a7e9f766c4e4e1ad8e0 - + https://github.com/microsoft/testfx - b2b75ecb52bcff592001df6d08f5fffccd945fdd + 36a23010d6fb8062381e5a7e9f766c4e4e1ad8e0 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet From 00c5249ac4c25af6659c19737bbe71c80d8bd6b7 Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Fri, 7 Nov 2025 11:03:20 +0000 Subject: [PATCH 02/18] Backflow from https://github.com/dotnet/dotnet / 6f4c060 build 289866 [[ commit created by automation ]] --- Directory.Packages.props | 1 + eng/Publishing.props | 4 + eng/Versions.props | 4 +- ...osoft.Extensions.DotNetDeltaApplier.csproj | 2 + .../HotReload/CompilationHandler.cs | 32 +++---- .../HotReload/IncrementalMSBuildWorkspace.cs | 4 +- .../dotnet-watch/dotnet-watch.csproj | 1 + src/RazorSdk/Tool/GenerateCommand.cs | 2 + .../MSBuild/GivenMSBuildLogger.cs | 96 +++++++++++++++++++ 9 files changed, 126 insertions(+), 20 deletions(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index ecc47ba3f164..27339ff8be28 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -37,6 +37,7 @@ + diff --git a/eng/Publishing.props b/eng/Publishing.props index 2eb794f98bb4..802134fadee4 100644 --- a/eng/Publishing.props +++ b/eng/Publishing.props @@ -43,6 +43,10 @@ + + + + - 17.14.8 + 17.14.28 18.0 @@ -126,7 +126,7 @@ - 1.8.1 + 1.10.2 4.0.1 diff --git a/src/BuiltInTools/DotNetDeltaApplier/Microsoft.Extensions.DotNetDeltaApplier.csproj b/src/BuiltInTools/DotNetDeltaApplier/Microsoft.Extensions.DotNetDeltaApplier.csproj index 87a397c3dd15..6391d60021e1 100644 --- a/src/BuiltInTools/DotNetDeltaApplier/Microsoft.Extensions.DotNetDeltaApplier.csproj +++ b/src/BuiltInTools/DotNetDeltaApplier/Microsoft.Extensions.DotNetDeltaApplier.csproj @@ -8,6 +8,8 @@ --> net6.0;net10.0 MicrosoftAspNetCore + + true diff --git a/src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs b/src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs index 55770d524293..2929d4f1e71e 100644 --- a/src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs +++ b/src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs @@ -6,7 +6,7 @@ using Microsoft.Build.Graph; using Microsoft.CodeAnalysis; using Microsoft.CodeAnalysis.CSharp; -using Microsoft.CodeAnalysis.ExternalAccess.Watch.Api; +using Microsoft.CodeAnalysis.ExternalAccess.HotReload.Api; using Microsoft.DotNet.HotReload; using Microsoft.Extensions.Logging; @@ -16,7 +16,7 @@ internal sealed class CompilationHandler : IDisposable { public readonly IncrementalMSBuildWorkspace Workspace; private readonly ILogger _logger; - private readonly WatchHotReloadService _hotReloadService; + private readonly HotReloadService _hotReloadService; private readonly ProcessRunner _processRunner; /// @@ -35,7 +35,7 @@ internal sealed class CompilationHandler : IDisposable /// /// All updates that were attempted. Includes updates whose application failed. /// - private ImmutableList _previousUpdates = []; + private ImmutableList _previousUpdates = []; private bool _isDisposed; @@ -44,7 +44,7 @@ public CompilationHandler(ILogger logger, ProcessRunner processRunner) _logger = logger; _processRunner = processRunner; Workspace = new IncrementalMSBuildWorkspace(logger); - _hotReloadService = new WatchHotReloadService(Workspace.CurrentSolution.Services, () => ValueTask.FromResult(GetAggregateCapabilities())); + _hotReloadService = new HotReloadService(Workspace.CurrentSolution.Services, () => ValueTask.FromResult(GetAggregateCapabilities())); } public void Dispose() @@ -299,7 +299,7 @@ private static void PrepareCompilations(Solution solution, string projectPath, C } public async ValueTask<( - ImmutableArray projectUpdates, + ImmutableArray projectUpdates, ImmutableArray projectsToRebuild, ImmutableArray projectsToRedeploy, ImmutableArray projectsToRestart)> HandleManagedCodeChangesAsync( @@ -315,14 +315,14 @@ private static void PrepareCompilations(Solution solution, string projectPath, C let runningProject = GetCorrespondingRunningProject(project, runningProjects) where runningProject != null let autoRestartProject = autoRestart || runningProject.ProjectNode.IsAutoRestartEnabled() - select (project.Id, info: new WatchHotReloadService.RunningProjectInfo() { RestartWhenChangesHaveNoEffect = autoRestartProject })) + select (project.Id, info: new HotReloadService.RunningProjectInfo() { RestartWhenChangesHaveNoEffect = autoRestartProject })) .ToImmutableDictionary(e => e.Id, e => e.info); var updates = await _hotReloadService.GetUpdatesAsync(currentSolution, runningProjectInfos, cancellationToken); await DisplayResultsAsync(updates, runningProjectInfos, cancellationToken); - if (updates.Status is WatchHotReloadService.Status.NoChangesToApply or WatchHotReloadService.Status.Blocked) + if (updates.Status is HotReloadService.Status.NoChangesToApply or HotReloadService.Status.Blocked) { // If Hot Reload is blocked (due to compilation error) we ignore the current // changes and await the next file change. @@ -364,7 +364,7 @@ private static void PrepareCompilations(Solution solution, string projectPath, C return (updates.ProjectUpdates, projectsToRebuild, projectsToRedeploy, projectsToRestart); } - public async ValueTask ApplyUpdatesAsync(ImmutableArray updates, CancellationToken cancellationToken) + public async ValueTask ApplyUpdatesAsync(ImmutableArray updates, CancellationToken cancellationToken) { Debug.Assert(!updates.IsEmpty); @@ -403,7 +403,7 @@ await ForEachProjectAsync(projectsToUpdate, async (runningProject, cancellationT } // msbuild workspace doesn't set TFM if the project is not multi-targeted - var tfm = WatchHotReloadService.GetTargetFramework(project); + var tfm = HotReloadService.GetTargetFramework(project); if (tfm == null) { return projectsWithPath[0]; @@ -412,18 +412,18 @@ await ForEachProjectAsync(projectsToUpdate, async (runningProject, cancellationT return projectsWithPath.SingleOrDefault(p => string.Equals(p.ProjectNode.GetTargetFramework(), tfm, StringComparison.OrdinalIgnoreCase)); } - private async ValueTask DisplayResultsAsync(WatchHotReloadService.Updates2 updates, ImmutableDictionary runningProjectInfos, CancellationToken cancellationToken) + private async ValueTask DisplayResultsAsync(HotReloadService.Updates updates, ImmutableDictionary runningProjectInfos, CancellationToken cancellationToken) { switch (updates.Status) { - case WatchHotReloadService.Status.ReadyToApply: + case HotReloadService.Status.ReadyToApply: break; - case WatchHotReloadService.Status.NoChangesToApply: + case HotReloadService.Status.NoChangesToApply: _logger.Log(MessageDescriptor.NoCSharpChangesToApply); break; - case WatchHotReloadService.Status.Blocked: + case HotReloadService.Status.Blocked: _logger.Log(MessageDescriptor.UnableToApplyChanges); break; @@ -451,7 +451,7 @@ await ForEachProjectAsync( void ReportCompilationDiagnostics(DiagnosticSeverity severity) { - foreach (var diagnostic in updates.CompilationDiagnostics) + foreach (var diagnostic in updates.PersistentDiagnostics) { if (diagnostic.Id == "CS8002") { @@ -492,7 +492,7 @@ void ReportRudeEdits() .Where(p => !updates.ProjectsToRestart.ContainsKey(p)) .ToHashSet(); - foreach (var (projectId, diagnostics) in updates.RudeEdits) + foreach (var (projectId, diagnostics) in updates.TransientDiagnostics) { foreach (var diagnostic in diagnostics) { @@ -689,7 +689,7 @@ public bool TryGetRunningProject(string projectPath, out ImmutableArray> projects, Func action, CancellationToken cancellationToken) => Task.WhenAll(projects.SelectMany(entry => entry.Value).Select(project => action(project, cancellationToken))).WaitAsync(cancellationToken); - private static ImmutableArray ToManagedCodeUpdates(ImmutableArray updates) + private static ImmutableArray ToManagedCodeUpdates(ImmutableArray updates) => [.. updates.Select(update => new HotReloadManagedCodeUpdate(update.ModuleId, update.MetadataDelta, update.ILDelta, update.PdbDelta, update.UpdatedTypes, update.RequiredCapabilities))]; } } diff --git a/src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs b/src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs index 65ab6089466c..06b79772ddf6 100644 --- a/src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs +++ b/src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs @@ -4,7 +4,7 @@ using System.Collections.Immutable; using System.Diagnostics; using Microsoft.CodeAnalysis; -using Microsoft.CodeAnalysis.ExternalAccess.Watch.Api; +using Microsoft.CodeAnalysis.ExternalAccess.HotReload.Api; using Microsoft.CodeAnalysis.Host.Mef; using Microsoft.CodeAnalysis.MSBuild; using Microsoft.CodeAnalysis.Text; @@ -76,7 +76,7 @@ public async Task UpdateProjectConeAsync(string rootProjectPath, CancellationTok continue; } - newSolution = WatchHotReloadService.WithProjectInfo(newSolution, ProjectInfo.Create( + newSolution = HotReloadService.WithProjectInfo(newSolution, ProjectInfo.Create( oldProjectId, newProjectInfo.Version, newProjectInfo.Name, diff --git a/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj b/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj index 9d089001e2b2..aab9d8b174dc 100644 --- a/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj +++ b/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj @@ -43,6 +43,7 @@ + diff --git a/src/RazorSdk/Tool/GenerateCommand.cs b/src/RazorSdk/Tool/GenerateCommand.cs index c12f59063555..bf889875d0f7 100644 --- a/src/RazorSdk/Tool/GenerateCommand.cs +++ b/src/RazorSdk/Tool/GenerateCommand.cs @@ -4,6 +4,7 @@ #nullable disable using System.Diagnostics; +using System.Threading; using Microsoft.AspNetCore.Razor.Language; using Microsoft.CodeAnalysis.CSharp; using Microsoft.NET.Sdk.Razor.Tool.CommandLineUtils; @@ -433,6 +434,7 @@ private class StaticTagHelperFeature : RazorEngineFeatureBase, ITagHelperFeature { public IReadOnlyList TagHelpers { get; set; } + public IReadOnlyList GetDescriptors(CancellationToken cancellationToken) => TagHelpers; public IReadOnlyList GetDescriptors() => TagHelpers; } } diff --git a/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs b/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs index 12a75b9493ee..eb5678178da1 100644 --- a/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs +++ b/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs @@ -214,5 +214,101 @@ public void ItIgnoresNonIntegerPropertiesDuringAggregation() fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty"); fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty2"); } + + [Fact] + public void ItAggregatesEvents() + { + var fakeTelemetry = new FakeTelemetry(); + fakeTelemetry.Enabled = true; + var logger = new MSBuildLogger(fakeTelemetry); + + var event1 = new TelemetryEventArgs + { + EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, + Properties = new Dictionary + { + { "AssemblyTaskFactoryTasksExecutedCount", "2" }, + { "RoslynCodeTaskFactoryTasksExecutedCount", "1" } + } + }; + + var event2 = new TelemetryEventArgs + { + EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, + Properties = new Dictionary + { + { "AssemblyTaskFactoryTasksExecutedCount", "3" }, + { "CustomTaskFactoryTasksExecutedCount", "2" } + } + }; + + var event3 = new TelemetryEventArgs + { + EventName = MSBuildLogger.TasksTelemetryAggregatedEventName, + Properties = new Dictionary + { + { "TasksExecutedCount", "3" }, + { "TaskHostTasksExecutedCount", "2" } + } + }; + + var event4 = new TelemetryEventArgs + { + EventName = MSBuildLogger.TasksTelemetryAggregatedEventName, + Properties = new Dictionary + { + { "TasksExecutedCount", "5" } + } + }; + + logger.AggregateEvent(event1); + logger.AggregateEvent(event2); + logger.AggregateEvent(event3); + logger.AggregateEvent(event4); + + logger.SendAggregatedEventsOnBuildFinished(fakeTelemetry); + + fakeTelemetry.LogEntries.Should().HaveCount(2); + + var taskFactoryEntry = fakeTelemetry.LogEntries.FirstOrDefault(e => e.EventName == $"msbuild/{MSBuildLogger.TaskFactoryTelemetryAggregatedEventName}"); + taskFactoryEntry.Should().NotBeNull(); + taskFactoryEntry.Properties["AssemblyTaskFactoryTasksExecutedCount"].Should().Be("5"); // 2 + 3 + taskFactoryEntry.Properties["RoslynCodeTaskFactoryTasksExecutedCount"].Should().Be("1"); // 1 + 0 + taskFactoryEntry.Properties["CustomTaskFactoryTasksExecutedCount"].Should().Be("2"); // 0 + 2 + + var tasksEntry = fakeTelemetry.LogEntries.FirstOrDefault(e => e.EventName == $"msbuild/{MSBuildLogger.TasksTelemetryAggregatedEventName}"); + tasksEntry.Should().NotBeNull(); + tasksEntry.Properties["TasksExecutedCount"].Should().Be("8"); // 3 + 5 + tasksEntry.Properties["TaskHostTasksExecutedCount"].Should().Be("2"); // 2 + 0 + } + + [Fact] + public void ItIgnoresNonIntegerPropertiesDuringAggregation() + { + var fakeTelemetry = new FakeTelemetry(); + fakeTelemetry.Enabled = true; + var logger = new MSBuildLogger(fakeTelemetry); + + var eventArgs = new TelemetryEventArgs + { + EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, + Properties = new Dictionary + { + { "AssemblyTaskFactoryTasksExecutedCount", "3" }, + { "InvalidProperty", "not-a-number" }, + { "InvalidProperty2", "1.234" }, + } + }; + + logger.AggregateEvent(eventArgs); + + logger.SendAggregatedEventsOnBuildFinished(fakeTelemetry); + + fakeTelemetry.LogEntry.Should().NotBeNull(); + fakeTelemetry.LogEntry.EventName.Should().Be($"msbuild/{MSBuildLogger.TaskFactoryTelemetryAggregatedEventName}"); + fakeTelemetry.LogEntry.Properties["AssemblyTaskFactoryTasksExecutedCount"].Should().Be("3"); + fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty"); + fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty2"); + } } } From 6029a62f34e379ac8ef32153bf7be3f613ebece3 Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Fri, 7 Nov 2025 11:03:21 +0000 Subject: [PATCH 03/18] Update dependencies from https://github.com/dotnet/dotnet build 289866 Updated Dependencies: Microsoft.AspNetCore.Mvc.Razor.Extensions.Tooling.Internal, Microsoft.CodeAnalysis.Razor.Tooling.Internal, Microsoft.NET.Sdk.Razor.SourceGenerators.Transport (Version 10.0.0-preview.25502.107 -> 10.0.0-preview.25556.109) Microsoft.Build, Microsoft.Build.Localization, Microsoft.NET.Test.Sdk, Microsoft.TestPlatform.Build, Microsoft.TestPlatform.CLI (Version 18.0.0-preview-25502-107 -> 18.1.0-preview-25556-109) Microsoft.Build.NuGetSdkResolver, NuGet.Build.Tasks, NuGet.Build.Tasks.Console, NuGet.Build.Tasks.Pack, NuGet.CommandLine.XPlat, NuGet.Commands, NuGet.Common, NuGet.Configuration, NuGet.Credentials, NuGet.DependencyResolver.Core, NuGet.Frameworks, NuGet.LibraryModel, NuGet.Localization, NuGet.Packaging, NuGet.ProjectModel, NuGet.Protocol, NuGet.Versioning (Version 7.0.0-rc.307 -> 7.0.0-preview.2.5709) Microsoft.CodeAnalysis, Microsoft.CodeAnalysis.BuildClient, Microsoft.CodeAnalysis.CSharp, Microsoft.CodeAnalysis.CSharp.CodeStyle, Microsoft.CodeAnalysis.CSharp.Features, Microsoft.CodeAnalysis.CSharp.Workspaces, Microsoft.CodeAnalysis.PublicApiAnalyzers, Microsoft.CodeAnalysis.Workspaces.Common, Microsoft.CodeAnalysis.Workspaces.MSBuild, Microsoft.Net.Compilers.Toolset, Microsoft.Net.Compilers.Toolset.Framework (Version 5.0.0-2.25502.107 -> 5.3.0-1.25556.109) Microsoft.DotNet.Arcade.Sdk, Microsoft.DotNet.Build.Tasks.Installers, Microsoft.DotNet.Build.Tasks.Templating, Microsoft.DotNet.Build.Tasks.Workloads, Microsoft.DotNet.Helix.Sdk, Microsoft.DotNet.SignTool, Microsoft.DotNet.XliffTasks, Microsoft.DotNet.XUnitExtensions (Version 10.0.0-beta.25522.2 -> 10.0.0-beta.25556.109) Microsoft.FSharp.Compiler (Version 14.0.100-rc2.25502.107 -> 15.0.200-servicing.25556.109) Microsoft.TemplateEngine.Abstractions, Microsoft.TemplateEngine.Authoring.TemplateVerifier, Microsoft.TemplateEngine.Edge, Microsoft.TemplateEngine.Mocks, Microsoft.TemplateEngine.Orchestrator.RunnableProjects, Microsoft.TemplateEngine.TestHelper, Microsoft.TemplateEngine.Utils, Microsoft.TemplateSearch.Common, Microsoft.TemplateSearch.TemplateDiscovery (Version 10.0.100-rc.2.25502.107 -> 10.0.100-rc.2.25556.109) Added Dependencies: Microsoft.CodeAnalysis.ExternalAccess.HotReload (Version 5.3.0-1.25556.109) --- eng/Version.Details.props | 228 ++++++------ eng/Version.Details.xml | 330 +++++++++--------- eng/common/SetupNugetSources.ps1 | 17 +- eng/common/SetupNugetSources.sh | 17 +- .../job/publish-build-assets.yml | 5 + .../core-templates/post-build/post-build.yml | 5 + global.json | 6 +- 7 files changed, 324 insertions(+), 284 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index 5980474f1ad2..e2030f9ee83a 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -5,6 +5,63 @@ This file should be imported by eng/Versions.props --> + + 10.0.0-preview.25556.109 + 18.1.0-preview-25556-109 + 18.1.0-preview-25556-109 + 7.0.0-preview.2.5709 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 10.0.0-preview.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 10.0.0-beta.25556.109 + 15.0.200-servicing.25556.109 + 5.3.0-1.25556.109 + 5.3.0-1.25556.109 + 10.0.0-preview.7.25377.103 + 10.0.0-preview.25556.109 + 18.1.0-preview-25556-109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 10.0.100-rc.2.25556.109 + 18.1.0-preview-25556-109 + 18.1.0-preview-25556-109 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 + 7.0.0-preview.2.5709 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 @@ -28,23 +85,9 @@ This file should be imported by eng/Versions.props 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 - 10.0.0-preview.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 - 18.0.0-preview-25502-107 - 18.0.0-preview-25502-107 - 7.0.0-rc.307 10.0.0-beta.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 - 10.0.0-preview.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 2.0.0-preview.1.25502.107 2.2.0-beta.25502.107 10.0.0-rc.2.25502.107 @@ -58,16 +101,11 @@ This file should be imported by eng/Versions.props 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 - 14.0.100-rc2.25502.107 10.0.0-rc.2.25502.107 - 5.0.0-2.25502.107 - 5.0.0-2.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 - 10.0.0-preview.25502.107 10.0.0-rc.2.25502.107 - 18.0.0-preview-25502-107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 10.0.0-beta.25502.107 @@ -75,37 +113,10 @@ This file should be imported by eng/Versions.props 10.0.0-beta.25502.107 10.0.0-beta.25502.107 10.0.0-beta.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 10.0.100-rc.2.25502.107 - 18.0.0-preview-25502-107 - 18.0.0-preview-25502-107 3.2.0-preview.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 - 7.0.0-rc.307 10.0.0-rc.2.25502.107 2.0.0-rc.2.25502.107 10.0.0-rc.2.25502.107 @@ -130,23 +141,69 @@ This file should be imported by eng/Versions.props 10.0.0-rc.2.25502.107 2.1.0 - - 10.0.0-preview.7.25377.103 - - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 - 10.0.0-beta.25522.2 2.1.0-preview.25553.3 4.1.0-preview.25553.3 + + $(MicrosoftAspNetCoreMvcRazorExtensionsToolingInternalPackageVersion) + $(MicrosoftBuildPackageVersion) + $(MicrosoftBuildLocalizationPackageVersion) + $(MicrosoftBuildNuGetSdkResolverPackageVersion) + $(MicrosoftCodeAnalysisPackageVersion) + $(MicrosoftCodeAnalysisBuildClientPackageVersion) + $(MicrosoftCodeAnalysisCSharpPackageVersion) + $(MicrosoftCodeAnalysisCSharpCodeStylePackageVersion) + $(MicrosoftCodeAnalysisCSharpFeaturesPackageVersion) + $(MicrosoftCodeAnalysisCSharpWorkspacesPackageVersion) + $(MicrosoftCodeAnalysisExternalAccessHotReloadPackageVersion) + $(MicrosoftCodeAnalysisPublicApiAnalyzersPackageVersion) + $(MicrosoftCodeAnalysisRazorToolingInternalPackageVersion) + $(MicrosoftCodeAnalysisWorkspacesCommonPackageVersion) + $(MicrosoftCodeAnalysisWorkspacesMSBuildPackageVersion) + $(MicrosoftDotNetArcadeSdkPackageVersion) + $(MicrosoftDotNetBuildTasksInstallersPackageVersion) + $(MicrosoftDotNetBuildTasksTemplatingPackageVersion) + $(MicrosoftDotNetBuildTasksWorkloadsPackageVersion) + $(MicrosoftDotNetHelixSdkPackageVersion) + $(MicrosoftDotNetSignToolPackageVersion) + $(MicrosoftDotNetXliffTasksPackageVersion) + $(MicrosoftDotNetXUnitExtensionsPackageVersion) + $(MicrosoftFSharpCompilerPackageVersion) + $(MicrosoftNetCompilersToolsetPackageVersion) + $(MicrosoftNetCompilersToolsetFrameworkPackageVersion) + $(MicrosoftNETRuntimeEmscriptenSdkInternalPackageVersion) + $(MicrosoftNETSdkRazorSourceGeneratorsTransportPackageVersion) + $(MicrosoftNETTestSdkPackageVersion) + $(MicrosoftTemplateEngineAbstractionsPackageVersion) + $(MicrosoftTemplateEngineAuthoringTemplateVerifierPackageVersion) + $(MicrosoftTemplateEngineEdgePackageVersion) + $(MicrosoftTemplateEngineMocksPackageVersion) + $(MicrosoftTemplateEngineOrchestratorRunnableProjectsPackageVersion) + $(MicrosoftTemplateEngineTestHelperPackageVersion) + $(MicrosoftTemplateEngineUtilsPackageVersion) + $(MicrosoftTemplateSearchCommonPackageVersion) + $(MicrosoftTemplateSearchTemplateDiscoveryPackageVersion) + $(MicrosoftTestPlatformBuildPackageVersion) + $(MicrosoftTestPlatformCLIPackageVersion) + $(NuGetBuildTasksPackageVersion) + $(NuGetBuildTasksConsolePackageVersion) + $(NuGetBuildTasksPackPackageVersion) + $(NuGetCommandLineXPlatPackageVersion) + $(NuGetCommandsPackageVersion) + $(NuGetCommonPackageVersion) + $(NuGetConfigurationPackageVersion) + $(NuGetCredentialsPackageVersion) + $(NuGetDependencyResolverCorePackageVersion) + $(NuGetFrameworksPackageVersion) + $(NuGetLibraryModelPackageVersion) + $(NuGetLocalizationPackageVersion) + $(NuGetPackagingPackageVersion) + $(NuGetProjectModelPackageVersion) + $(NuGetProtocolPackageVersion) + $(NuGetVersioningPackageVersion) $(dotnetdevcertsPackageVersion) $(dotnetuserjwtsPackageVersion) @@ -170,23 +227,9 @@ This file should be imported by eng/Versions.props $(MicrosoftAspNetCoreMetadataPackageVersion) $(MicrosoftAspNetCoreMvcAnalyzersPackageVersion) $(MicrosoftAspNetCoreMvcApiAnalyzersPackageVersion) - $(MicrosoftAspNetCoreMvcRazorExtensionsToolingInternalPackageVersion) $(MicrosoftAspNetCoreTestHostPackageVersion) $(MicrosoftBclAsyncInterfacesPackageVersion) - $(MicrosoftBuildPackageVersion) - $(MicrosoftBuildLocalizationPackageVersion) - $(MicrosoftBuildNuGetSdkResolverPackageVersion) $(MicrosoftBuildTasksGitPackageVersion) - $(MicrosoftCodeAnalysisPackageVersion) - $(MicrosoftCodeAnalysisBuildClientPackageVersion) - $(MicrosoftCodeAnalysisCSharpPackageVersion) - $(MicrosoftCodeAnalysisCSharpCodeStylePackageVersion) - $(MicrosoftCodeAnalysisCSharpFeaturesPackageVersion) - $(MicrosoftCodeAnalysisCSharpWorkspacesPackageVersion) - $(MicrosoftCodeAnalysisPublicApiAnalyzersPackageVersion) - $(MicrosoftCodeAnalysisRazorToolingInternalPackageVersion) - $(MicrosoftCodeAnalysisWorkspacesCommonPackageVersion) - $(MicrosoftCodeAnalysisWorkspacesMSBuildPackageVersion) $(MicrosoftDeploymentDotNetReleasesPackageVersion) $(MicrosoftDiaSymReaderPackageVersion) $(MicrosoftDotNetWebItemTemplates100PackageVersion) @@ -200,16 +243,11 @@ This file should be imported by eng/Versions.props $(MicrosoftExtensionsLoggingAbstractionsPackageVersion) $(MicrosoftExtensionsLoggingConsolePackageVersion) $(MicrosoftExtensionsObjectPoolPackageVersion) - $(MicrosoftFSharpCompilerPackageVersion) $(MicrosoftJSInteropPackageVersion) - $(MicrosoftNetCompilersToolsetPackageVersion) - $(MicrosoftNetCompilersToolsetFrameworkPackageVersion) $(MicrosoftNETHostModelPackageVersion) $(MicrosoftNETILLinkTasksPackageVersion) $(MicrosoftNETRuntimeEmscripten3156Cachewinx64PackageVersion) - $(MicrosoftNETSdkRazorSourceGeneratorsTransportPackageVersion) $(MicrosoftNETSdkWindowsDesktopPackageVersion) - $(MicrosoftNETTestSdkPackageVersion) $(MicrosoftNETCoreAppRefPackageVersion) $(MicrosoftNETCorePlatformsPackageVersion) $(MicrosoftSourceLinkAzureReposGitPackageVersion) @@ -217,37 +255,10 @@ This file should be imported by eng/Versions.props $(MicrosoftSourceLinkCommonPackageVersion) $(MicrosoftSourceLinkGitHubPackageVersion) $(MicrosoftSourceLinkGitLabPackageVersion) - $(MicrosoftTemplateEngineAbstractionsPackageVersion) - $(MicrosoftTemplateEngineAuthoringTemplateVerifierPackageVersion) - $(MicrosoftTemplateEngineEdgePackageVersion) - $(MicrosoftTemplateEngineMocksPackageVersion) - $(MicrosoftTemplateEngineOrchestratorRunnableProjectsPackageVersion) - $(MicrosoftTemplateEngineTestHelperPackageVersion) - $(MicrosoftTemplateEngineUtilsPackageVersion) - $(MicrosoftTemplateSearchCommonPackageVersion) - $(MicrosoftTemplateSearchTemplateDiscoveryPackageVersion) - $(MicrosoftTestPlatformBuildPackageVersion) - $(MicrosoftTestPlatformCLIPackageVersion) $(MicrosoftWebXdtPackageVersion) $(MicrosoftWin32SystemEventsPackageVersion) $(MicrosoftWindowsDesktopAppInternalPackageVersion) $(MicrosoftWindowsDesktopAppRefPackageVersion) - $(NuGetBuildTasksPackageVersion) - $(NuGetBuildTasksConsolePackageVersion) - $(NuGetBuildTasksPackPackageVersion) - $(NuGetCommandLineXPlatPackageVersion) - $(NuGetCommandsPackageVersion) - $(NuGetCommonPackageVersion) - $(NuGetConfigurationPackageVersion) - $(NuGetCredentialsPackageVersion) - $(NuGetDependencyResolverCorePackageVersion) - $(NuGetFrameworksPackageVersion) - $(NuGetLibraryModelPackageVersion) - $(NuGetLocalizationPackageVersion) - $(NuGetPackagingPackageVersion) - $(NuGetProjectModelPackageVersion) - $(NuGetProtocolPackageVersion) - $(NuGetVersioningPackageVersion) $(SystemCodeDomPackageVersion) $(SystemCommandLinePackageVersion) $(SystemComponentModelCompositionPackageVersion) @@ -272,17 +283,6 @@ This file should be imported by eng/Versions.props $(SystemWindowsExtensionsPackageVersion) $(NETStandardLibraryRefPackageVersion) - - $(MicrosoftNETRuntimeEmscriptenSdkInternalPackageVersion) - - $(MicrosoftDotNetArcadeSdkPackageVersion) - $(MicrosoftDotNetBuildTasksInstallersPackageVersion) - $(MicrosoftDotNetBuildTasksTemplatingPackageVersion) - $(MicrosoftDotNetBuildTasksWorkloadsPackageVersion) - $(MicrosoftDotNetHelixSdkPackageVersion) - $(MicrosoftDotNetSignToolPackageVersion) - $(MicrosoftDotNetXliffTasksPackageVersion) - $(MicrosoftDotNetXUnitExtensionsPackageVersion) $(MicrosoftTestingPlatformPackageVersion) $(MSTestPackageVersion) diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index 755d740bac77..b6fab92d0129 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -1,42 +1,42 @@ - + - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet @@ -72,138 +72,138 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet @@ -371,25 +371,25 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - - https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet - 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet @@ -515,39 +515,43 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 + - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 - - https://github.com/dotnet/arcade - 63eed293471985f6fc4a60fd8b6f8f5ce3d03f38 + + https://github.com/dotnet/dotnet + 6f4c060932973b6b570b8444c8dc76d38af555e8 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet diff --git a/eng/common/SetupNugetSources.ps1 b/eng/common/SetupNugetSources.ps1 index fc8d618014e0..65ed3a8adef0 100644 --- a/eng/common/SetupNugetSources.ps1 +++ b/eng/common/SetupNugetSources.ps1 @@ -1,6 +1,7 @@ # This script adds internal feeds required to build commits that depend on internal package sources. For instance, -# dotnet6-internal would be added automatically if dotnet6 was found in the nuget.config file. In addition also enables -# disabled internal Maestro (darc-int*) feeds. +# dotnet6-internal would be added automatically if dotnet6 was found in the nuget.config file. Similarly, +# dotnet-eng-internal and dotnet-tools-internal are added if dotnet-eng and dotnet-tools are present. +# In addition, this script also enables disabled internal Maestro (darc-int*) feeds. # # Optionally, this script also adds a credential entry for each of the internal feeds if supplied. # @@ -173,4 +174,16 @@ foreach ($dotnetVersion in $dotnetVersions) { } } +# Check for dotnet-eng and add dotnet-eng-internal if present +$dotnetEngSource = $sources.SelectSingleNode("add[@key='dotnet-eng']") +if ($dotnetEngSource -ne $null) { + AddOrEnablePackageSource -Sources $sources -DisabledPackageSources $disabledSources -SourceName "dotnet-eng-internal" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-eng-internal/nuget/$feedSuffix" -Creds $creds -Username $userName -pwd $Password +} + +# Check for dotnet-tools and add dotnet-tools-internal if present +$dotnetToolsSource = $sources.SelectSingleNode("add[@key='dotnet-tools']") +if ($dotnetToolsSource -ne $null) { + AddOrEnablePackageSource -Sources $sources -DisabledPackageSources $disabledSources -SourceName "dotnet-tools-internal" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-tools-internal/nuget/$feedSuffix" -Creds $creds -Username $userName -pwd $Password +} + $doc.Save($filename) diff --git a/eng/common/SetupNugetSources.sh b/eng/common/SetupNugetSources.sh index b97cc536379d..b2163abbe71b 100755 --- a/eng/common/SetupNugetSources.sh +++ b/eng/common/SetupNugetSources.sh @@ -1,8 +1,9 @@ #!/usr/bin/env bash # This script adds internal feeds required to build commits that depend on internal package sources. For instance, -# dotnet6-internal would be added automatically if dotnet6 was found in the nuget.config file. In addition also enables -# disabled internal Maestro (darc-int*) feeds. +# dotnet6-internal would be added automatically if dotnet6 was found in the nuget.config file. Similarly, +# dotnet-eng-internal and dotnet-tools-internal are added if dotnet-eng and dotnet-tools are present. +# In addition, this script also enables disabled internal Maestro (darc-int*) feeds. # # Optionally, this script also adds a credential entry for each of the internal feeds if supplied. # @@ -173,6 +174,18 @@ for DotNetVersion in ${DotNetVersions[@]} ; do fi done +# Check for dotnet-eng and add dotnet-eng-internal if present +grep -i " /dev/null +if [ "$?" == "0" ]; then + AddOrEnablePackageSource "dotnet-eng-internal" "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-eng-internal/nuget/$FeedSuffix" +fi + +# Check for dotnet-tools and add dotnet-tools-internal if present +grep -i " /dev/null +if [ "$?" == "0" ]; then + AddOrEnablePackageSource "dotnet-tools-internal" "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-tools-internal/nuget/$FeedSuffix" +fi + # I want things split line by line PrevIFS=$IFS IFS=$'\n' diff --git a/eng/common/core-templates/job/publish-build-assets.yml b/eng/common/core-templates/job/publish-build-assets.yml index 37dff559fc1b..e7daa6d2fafe 100644 --- a/eng/common/core-templates/job/publish-build-assets.yml +++ b/eng/common/core-templates/job/publish-build-assets.yml @@ -180,6 +180,11 @@ jobs: PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} is1ESPipeline: ${{ parameters.is1ESPipeline }} + # Darc is targeting 8.0, so make sure it's installed + - task: UseDotNet@2 + inputs: + version: 8.0.x + - task: AzureCLI@2 displayName: Publish Using Darc inputs: diff --git a/eng/common/core-templates/post-build/post-build.yml b/eng/common/core-templates/post-build/post-build.yml index f6f87fe5c675..55361908c2e9 100644 --- a/eng/common/core-templates/post-build/post-build.yml +++ b/eng/common/core-templates/post-build/post-build.yml @@ -307,6 +307,11 @@ stages: - task: NuGetAuthenticate@1 + # Darc is targeting 8.0, so make sure it's installed + - task: UseDotNet@2 + inputs: + version: 8.0.x + - task: AzureCLI@2 displayName: Publish Using Darc inputs: diff --git a/global.json b/global.json index aa17ec7efcf5..fa4098d4abdc 100644 --- a/global.json +++ b/global.json @@ -7,7 +7,7 @@ "errorMessage": "The .NET SDK is not installed or is not configured correctly. Please run ./build to install the correct SDK version locally." }, "tools": { - "dotnet": "10.0.100-rc.1.25451.107", + "dotnet": "10.0.100-rc.2.25502.107", "runtimes": { "dotnet": [ "$(MicrosoftNETCorePlatformsPackageVersion)" @@ -21,8 +21,8 @@ } }, "msbuild-sdks": { - "Microsoft.DotNet.Arcade.Sdk": "10.0.0-beta.25522.2", - "Microsoft.DotNet.Helix.Sdk": "10.0.0-beta.25522.2", + "Microsoft.DotNet.Arcade.Sdk": "10.0.0-beta.25556.109", + "Microsoft.DotNet.Helix.Sdk": "10.0.0-beta.25556.109", "Microsoft.Build.NoTargets": "3.7.0", "Microsoft.Build.Traversal": "3.4.0", "Microsoft.WixToolset.Sdk": "5.0.2-dotnet.2811440" From dcc8cfe0cf5ff09e8cd39392a6c979e4fb35e156 Mon Sep 17 00:00:00 2001 From: Tomas Matousek Date: Fri, 7 Nov 2025 07:57:28 -0800 Subject: [PATCH 04/18] Delete duplicate tests --- .../MSBuild/GivenMSBuildLogger.cs | 96 ------------------- 1 file changed, 96 deletions(-) diff --git a/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs b/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs index eb5678178da1..12a75b9493ee 100644 --- a/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs +++ b/test/dotnet.Tests/CommandTests/MSBuild/GivenMSBuildLogger.cs @@ -214,101 +214,5 @@ public void ItIgnoresNonIntegerPropertiesDuringAggregation() fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty"); fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty2"); } - - [Fact] - public void ItAggregatesEvents() - { - var fakeTelemetry = new FakeTelemetry(); - fakeTelemetry.Enabled = true; - var logger = new MSBuildLogger(fakeTelemetry); - - var event1 = new TelemetryEventArgs - { - EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, - Properties = new Dictionary - { - { "AssemblyTaskFactoryTasksExecutedCount", "2" }, - { "RoslynCodeTaskFactoryTasksExecutedCount", "1" } - } - }; - - var event2 = new TelemetryEventArgs - { - EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, - Properties = new Dictionary - { - { "AssemblyTaskFactoryTasksExecutedCount", "3" }, - { "CustomTaskFactoryTasksExecutedCount", "2" } - } - }; - - var event3 = new TelemetryEventArgs - { - EventName = MSBuildLogger.TasksTelemetryAggregatedEventName, - Properties = new Dictionary - { - { "TasksExecutedCount", "3" }, - { "TaskHostTasksExecutedCount", "2" } - } - }; - - var event4 = new TelemetryEventArgs - { - EventName = MSBuildLogger.TasksTelemetryAggregatedEventName, - Properties = new Dictionary - { - { "TasksExecutedCount", "5" } - } - }; - - logger.AggregateEvent(event1); - logger.AggregateEvent(event2); - logger.AggregateEvent(event3); - logger.AggregateEvent(event4); - - logger.SendAggregatedEventsOnBuildFinished(fakeTelemetry); - - fakeTelemetry.LogEntries.Should().HaveCount(2); - - var taskFactoryEntry = fakeTelemetry.LogEntries.FirstOrDefault(e => e.EventName == $"msbuild/{MSBuildLogger.TaskFactoryTelemetryAggregatedEventName}"); - taskFactoryEntry.Should().NotBeNull(); - taskFactoryEntry.Properties["AssemblyTaskFactoryTasksExecutedCount"].Should().Be("5"); // 2 + 3 - taskFactoryEntry.Properties["RoslynCodeTaskFactoryTasksExecutedCount"].Should().Be("1"); // 1 + 0 - taskFactoryEntry.Properties["CustomTaskFactoryTasksExecutedCount"].Should().Be("2"); // 0 + 2 - - var tasksEntry = fakeTelemetry.LogEntries.FirstOrDefault(e => e.EventName == $"msbuild/{MSBuildLogger.TasksTelemetryAggregatedEventName}"); - tasksEntry.Should().NotBeNull(); - tasksEntry.Properties["TasksExecutedCount"].Should().Be("8"); // 3 + 5 - tasksEntry.Properties["TaskHostTasksExecutedCount"].Should().Be("2"); // 2 + 0 - } - - [Fact] - public void ItIgnoresNonIntegerPropertiesDuringAggregation() - { - var fakeTelemetry = new FakeTelemetry(); - fakeTelemetry.Enabled = true; - var logger = new MSBuildLogger(fakeTelemetry); - - var eventArgs = new TelemetryEventArgs - { - EventName = MSBuildLogger.TaskFactoryTelemetryAggregatedEventName, - Properties = new Dictionary - { - { "AssemblyTaskFactoryTasksExecutedCount", "3" }, - { "InvalidProperty", "not-a-number" }, - { "InvalidProperty2", "1.234" }, - } - }; - - logger.AggregateEvent(eventArgs); - - logger.SendAggregatedEventsOnBuildFinished(fakeTelemetry); - - fakeTelemetry.LogEntry.Should().NotBeNull(); - fakeTelemetry.LogEntry.EventName.Should().Be($"msbuild/{MSBuildLogger.TaskFactoryTelemetryAggregatedEventName}"); - fakeTelemetry.LogEntry.Properties["AssemblyTaskFactoryTasksExecutedCount"].Should().Be("3"); - fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty"); - fakeTelemetry.LogEntry.Properties.Should().NotContainKey("InvalidProperty2"); - } } } From 11ededf2ba8f6932ce32d43bb027f0e039bdd5e5 Mon Sep 17 00:00:00 2001 From: Jan Jones Date: Fri, 7 Nov 2025 18:43:30 +0100 Subject: [PATCH 05/18] Update baseline --- src/Cli/dotnet/Commands/Run/CSharpCompilerCommand.Generated.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Cli/dotnet/Commands/Run/CSharpCompilerCommand.Generated.cs b/src/Cli/dotnet/Commands/Run/CSharpCompilerCommand.Generated.cs index d53f7052b754..94e889267f86 100644 --- a/src/Cli/dotnet/Commands/Run/CSharpCompilerCommand.Generated.cs +++ b/src/Cli/dotnet/Commands/Run/CSharpCompilerCommand.Generated.cs @@ -15,7 +15,7 @@ private IEnumerable GetCscArguments( [ "/unsafe-", "/checked-", - "/nowarn:1701,1702,IL2121,1701,1702", + "/nowarn:1701,1702,IL2121,1701,1702,8002", "/fullpaths", "/nostdlib+", "/errorreport:prompt", From 6a04a91c5523b2210300acee5f4d9fb76a788c04 Mon Sep 17 00:00:00 2001 From: "Eric St. John" Date: Mon, 13 Oct 2025 15:06:48 -0700 Subject: [PATCH 06/18] Make GlobalPrefixRemover override VisitAliasQualifiedName instead of VisitQualifiedName --- .../SyntaxRewriter/GlobalPrefixRemover.cs | 15 ++++----------- 1 file changed, 4 insertions(+), 11 deletions(-) diff --git a/src/Compatibility/ApiDiff/Microsoft.DotNet.ApiDiff/SyntaxRewriter/GlobalPrefixRemover.cs b/src/Compatibility/ApiDiff/Microsoft.DotNet.ApiDiff/SyntaxRewriter/GlobalPrefixRemover.cs index 74b1fdd5d3b1..0cd75f738168 100644 --- a/src/Compatibility/ApiDiff/Microsoft.DotNet.ApiDiff/SyntaxRewriter/GlobalPrefixRemover.cs +++ b/src/Compatibility/ApiDiff/Microsoft.DotNet.ApiDiff/SyntaxRewriter/GlobalPrefixRemover.cs @@ -11,15 +11,8 @@ internal class GlobalPrefixRemover : CSharpSyntaxRewriter { public static readonly GlobalPrefixRemover Singleton = new(); - private const string GlobalPrefix = "global"; - - public override SyntaxNode? VisitQualifiedName(QualifiedNameSyntax node) - { - if (node.Left is AliasQualifiedNameSyntax alias && - alias.Alias.Identifier.Text == GlobalPrefix) - { - node = SyntaxFactory.QualifiedName(alias.Name, node.Right).WithTriviaFrom(node); - } - return base.VisitQualifiedName(node); - } + public override SyntaxNode? VisitAliasQualifiedName(AliasQualifiedNameSyntax node) + => node.Alias.Identifier.IsKind(SyntaxKind.GlobalKeyword) + ? node.Name.WithTriviaFrom(node) + : base.VisitAliasQualifiedName(node); } From 82e2e7d70400cf5074efb8b4c7aad2d94a07f39c Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Sat, 8 Nov 2025 02:03:40 +0000 Subject: [PATCH 07/18] Update dependencies from https://github.com/microsoft/testfx build 20251107.4 On relative base path root Microsoft.Testing.Platform From Version 2.1.0-preview.25553.3 -> To Version 2.1.0-preview.25557.4 MSTest From Version 4.1.0-preview.25553.3 -> To Version 4.1.0-preview.25557.4 --- eng/Version.Details.props | 4 ++-- eng/Version.Details.xml | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index 0e4b1ed8813b..f2e33152f7ee 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -142,8 +142,8 @@ This file should be imported by eng/Versions.props 10.0.0-beta.25522.2 10.0.0-beta.25522.2 - 2.1.0-preview.25554.7 - 4.1.0-preview.25554.7 + 2.1.0-preview.25557.4 + 4.1.0-preview.25557.4 diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index bda2555be11f..898c63397438 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -553,13 +553,13 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - + https://github.com/microsoft/testfx - 36a23010d6fb8062381e5a7e9f766c4e4e1ad8e0 + 0f7c5727aaaf3aa289f20ef65241847a405bbb6e - + https://github.com/microsoft/testfx - 36a23010d6fb8062381e5a7e9f766c4e4e1ad8e0 + 0f7c5727aaaf3aa289f20ef65241847a405bbb6e https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet From 0cfbcaf8ab0e1e2218f79a4eb5c4125d80705a4b Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Sun, 9 Nov 2025 02:02:28 +0000 Subject: [PATCH 08/18] Update dependencies from https://github.com/microsoft/testfx build 20251108.6 On relative base path root Microsoft.Testing.Platform From Version 2.1.0-preview.25553.3 -> To Version 2.1.0-preview.25558.6 MSTest From Version 4.1.0-preview.25553.3 -> To Version 4.1.0-preview.25558.6 --- eng/Version.Details.props | 4 ++-- eng/Version.Details.xml | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index f2e33152f7ee..84a41eac5dee 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -142,8 +142,8 @@ This file should be imported by eng/Versions.props 10.0.0-beta.25522.2 10.0.0-beta.25522.2 - 2.1.0-preview.25557.4 - 4.1.0-preview.25557.4 + 2.1.0-preview.25558.6 + 4.1.0-preview.25558.6 diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index 898c63397438..f02a18de617b 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -553,13 +553,13 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - + https://github.com/microsoft/testfx - 0f7c5727aaaf3aa289f20ef65241847a405bbb6e + 7df896aeec9505a44371dbe0dd2712764d0ce0f6 - + https://github.com/microsoft/testfx - 0f7c5727aaaf3aa289f20ef65241847a405bbb6e + 7df896aeec9505a44371dbe0dd2712764d0ce0f6 https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet From 31f5075d736dd843812ca94c96b9a70779d17f2e Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Mon, 10 Nov 2025 02:02:55 +0000 Subject: [PATCH 09/18] Update dependencies from https://github.com/microsoft/testfx build 20251109.1 On relative base path root Microsoft.Testing.Platform From Version 2.1.0-preview.25553.3 -> To Version 2.1.0-preview.25559.1 MSTest From Version 4.1.0-preview.25553.3 -> To Version 4.1.0-preview.25559.1 --- eng/Version.Details.props | 4 ++-- eng/Version.Details.xml | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index 84a41eac5dee..ca9a7cbdd11e 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -142,8 +142,8 @@ This file should be imported by eng/Versions.props 10.0.0-beta.25522.2 10.0.0-beta.25522.2 - 2.1.0-preview.25558.6 - 4.1.0-preview.25558.6 + 2.1.0-preview.25559.1 + 4.1.0-preview.25559.1 diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index f02a18de617b..cc3f23f7b4a0 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -553,13 +553,13 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - + https://github.com/microsoft/testfx - 7df896aeec9505a44371dbe0dd2712764d0ce0f6 + 29aa788ac17beff2313e392de6c484f585b4f59b - + https://github.com/microsoft/testfx - 7df896aeec9505a44371dbe0dd2712764d0ce0f6 + 29aa788ac17beff2313e392de6c484f585b4f59b https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet From d91154f356eaf845258cfd7681f4ffac2d628444 Mon Sep 17 00:00:00 2001 From: Jan Jones Date: Tue, 11 Nov 2025 13:02:16 +0100 Subject: [PATCH 10/18] Fix failing build task tests Needed due to https://github.com/dotnet/sdk/pull/51192. --- test/Microsoft.NET.Build.Tests/RoslynBuildTaskTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/Microsoft.NET.Build.Tests/RoslynBuildTaskTests.cs b/test/Microsoft.NET.Build.Tests/RoslynBuildTaskTests.cs index 2f473b12d72f..8e9074e1b377 100644 --- a/test/Microsoft.NET.Build.Tests/RoslynBuildTaskTests.cs +++ b/test/Microsoft.NET.Build.Tests/RoslynBuildTaskTests.cs @@ -59,7 +59,7 @@ public void FullMSBuild_SdkStyle_ToolsetPackage(bool useSharedCompilation, Langu { var testAsset = CreateProject(useSharedCompilation, language, AddCompilersToolsetPackage); var buildCommand = BuildAndRunUsingMSBuild(testAsset); - VerifyCompiler(buildCommand, AppHostCompilerFileName(language), useSharedCompilation, toolsetPackage: true); + VerifyCompiler(buildCommand, DotNetExecCompilerFileName(language), useSharedCompilation, toolsetPackage: true); } [Theory, CombinatorialData] From 599261f1dada8f68d626375b957d62ad681373a2 Mon Sep 17 00:00:00 2001 From: Youssef Victor Date: Tue, 11 Nov 2025 23:42:32 +0100 Subject: [PATCH 11/18] Suppress --- .../TestProject/Program.cs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/TestAssets/TestProjects/TestProjectSolutionWithTestsAndArtifacts/TestProject/Program.cs b/test/TestAssets/TestProjects/TestProjectSolutionWithTestsAndArtifacts/TestProject/Program.cs index 8191677e5472..9fc0d44ada52 100644 --- a/test/TestAssets/TestProjects/TestProjectSolutionWithTestsAndArtifacts/TestProject/Program.cs +++ b/test/TestAssets/TestProjects/TestProjectSolutionWithTestsAndArtifacts/TestProject/Program.cs @@ -81,7 +81,9 @@ public async Task ExecuteRequestAsync(ExecuteRequestContext context) { Uid = "Test5", DisplayName = "Test5", +#pragma warning disable CS0618 // Type or member is obsolete Properties = new PropertyBag(new CancelledTestNodeStateProperty(new Exception("this is a cancelled exception"), "not OK")), +#pragma warning restore CS0618 // Type or member is obsolete })); await context.MessageBus.PublishAsync(this, new FileArtifact(new FileInfo("file.txt"), "file", "file description")); From f0c7627c17dc94fd0b4e4ed29fcd489cd0e85de6 Mon Sep 17 00:00:00 2001 From: Youssef Victor Date: Tue, 11 Nov 2025 23:43:31 +0100 Subject: [PATCH 12/18] Suppress --- .../TestProjectWithMultipleTFMsSolution/TestProject/Program.cs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/TestAssets/TestProjects/TestProjectWithMultipleTFMsSolution/TestProject/Program.cs b/test/TestAssets/TestProjects/TestProjectWithMultipleTFMsSolution/TestProject/Program.cs index 99cfc02234a4..f8b19141f356 100644 --- a/test/TestAssets/TestProjects/TestProjectWithMultipleTFMsSolution/TestProject/Program.cs +++ b/test/TestAssets/TestProjects/TestProjectWithMultipleTFMsSolution/TestProject/Program.cs @@ -81,7 +81,9 @@ public async Task ExecuteRequestAsync(ExecuteRequestContext context) { Uid = "Test5", DisplayName = "Test5", +#pragma warning disable CS0618 // Type or member is obsolete Properties = new PropertyBag(new CancelledTestNodeStateProperty(new Exception("this is a cancelled exception"), "")), +#pragma warning restore CS0618 // Type or member is obsolete })); context.Complete(); From 52f47bfd67af2f839caf0c58422af1cf1db213ce Mon Sep 17 00:00:00 2001 From: Youssef Victor Date: Tue, 11 Nov 2025 23:44:16 +0100 Subject: [PATCH 13/18] Suppress --- .../HybridTestRunnerTestProjects/OtherTestProject/Program.cs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/TestAssets/TestProjects/HybridTestRunnerTestProjects/OtherTestProject/Program.cs b/test/TestAssets/TestProjects/HybridTestRunnerTestProjects/OtherTestProject/Program.cs index 1b9b5e92af36..fc9f8d4bb07f 100644 --- a/test/TestAssets/TestProjects/HybridTestRunnerTestProjects/OtherTestProject/Program.cs +++ b/test/TestAssets/TestProjects/HybridTestRunnerTestProjects/OtherTestProject/Program.cs @@ -84,7 +84,9 @@ public async Task ExecuteRequestAsync(ExecuteRequestContext context) { Uid = "Test5", DisplayName = "Test5", +#pragma warning disable CS0618 // Type or member is obsolete Properties = new PropertyBag(new CancelledTestNodeStateProperty(new Exception("this is a cancelled exception"), "not OK")), +#pragma warning restore CS0618 // Type or member is obsolete })); await context.MessageBus.PublishAsync(this, new FileArtifact(new FileInfo("file.txt"), "file", "file description")); From ec46acd0a9e21758a15f6950eebd7343a636c0a2 Mon Sep 17 00:00:00 2001 From: Youssef Victor Date: Tue, 11 Nov 2025 23:44:48 +0100 Subject: [PATCH 14/18] Suppress --- .../OtherTestProject/Program.cs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/TestAssets/TestProjects/ClassLibraryWithIsTestProjectAndOtherTestProjects/OtherTestProject/Program.cs b/test/TestAssets/TestProjects/ClassLibraryWithIsTestProjectAndOtherTestProjects/OtherTestProject/Program.cs index 1b9b5e92af36..fc9f8d4bb07f 100644 --- a/test/TestAssets/TestProjects/ClassLibraryWithIsTestProjectAndOtherTestProjects/OtherTestProject/Program.cs +++ b/test/TestAssets/TestProjects/ClassLibraryWithIsTestProjectAndOtherTestProjects/OtherTestProject/Program.cs @@ -84,7 +84,9 @@ public async Task ExecuteRequestAsync(ExecuteRequestContext context) { Uid = "Test5", DisplayName = "Test5", +#pragma warning disable CS0618 // Type or member is obsolete Properties = new PropertyBag(new CancelledTestNodeStateProperty(new Exception("this is a cancelled exception"), "not OK")), +#pragma warning restore CS0618 // Type or member is obsolete })); await context.MessageBus.PublishAsync(this, new FileArtifact(new FileInfo("file.txt"), "file", "file description")); From 4f0a377c8b50fa4f5a51977859d8da2543dfb3dd Mon Sep 17 00:00:00 2001 From: "dotnet-maestro[bot]" Date: Wed, 12 Nov 2025 02:02:55 +0000 Subject: [PATCH 15/18] Update dependencies from https://github.com/microsoft/testfx build 20251111.13 On relative base path root Microsoft.Testing.Platform From Version 2.1.0-preview.25553.3 -> To Version 2.1.0-preview.25561.13 MSTest From Version 4.1.0-preview.25553.3 -> To Version 4.1.0-preview.25561.13 --- eng/Version.Details.props | 4 ++-- eng/Version.Details.xml | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/eng/Version.Details.props b/eng/Version.Details.props index c0b871382d85..5d1051c21c45 100644 --- a/eng/Version.Details.props +++ b/eng/Version.Details.props @@ -142,8 +142,8 @@ This file should be imported by eng/Versions.props 2.1.0 - 2.1.0-preview.25559.1 - 4.1.0-preview.25559.1 + 2.1.0-preview.25561.13 + 4.1.0-preview.25561.13 diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml index 245b06976411..976130c07c01 100644 --- a/eng/Version.Details.xml +++ b/eng/Version.Details.xml @@ -557,13 +557,13 @@ https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet 89c8f6a112d37d2ea8b77821e56d170a1bccdc5a - + https://github.com/microsoft/testfx - 29aa788ac17beff2313e392de6c484f585b4f59b + c60f4f766766774d2b45ff4f62abe3d9b269ebee - + https://github.com/microsoft/testfx - 29aa788ac17beff2313e392de6c484f585b4f59b + c60f4f766766774d2b45ff4f62abe3d9b269ebee https://dev.azure.com/dnceng/internal/_git/dotnet-dotnet From 27674c074824c779b0252ea9c351deddcf27ebc2 Mon Sep 17 00:00:00 2001 From: Copilot <198982749+Copilot@users.noreply.github.com> Date: Wed, 12 Nov 2025 18:37:21 +0100 Subject: [PATCH 16/18] Improve clarity of 'dotnet project convert' output directory prompt (#51443) Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: jjonescz <3669664+jjonescz@users.noreply.github.com> --- src/Cli/dotnet/Commands/CliCommandStrings.resx | 2 +- src/Cli/dotnet/Commands/xlf/CliCommandStrings.cs.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.de.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.es.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.fr.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.it.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.ja.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.ko.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.pl.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.pt-BR.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.ru.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.tr.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hans.xlf | 4 ++-- src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hant.xlf | 4 ++-- 14 files changed, 27 insertions(+), 27 deletions(-) diff --git a/src/Cli/dotnet/Commands/CliCommandStrings.resx b/src/Cli/dotnet/Commands/CliCommandStrings.resx index 2c94953811c9..aa6b906e6ec0 100644 --- a/src/Cli/dotnet/Commands/CliCommandStrings.resx +++ b/src/Cli/dotnet/Commands/CliCommandStrings.resx @@ -1533,7 +1533,7 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man Convert a file-based program to a project-based program. - Specify the output directory ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.cs.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.cs.xlf index 6215a2a91ec5..a4ed38fb3289 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.cs.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.cs.xlf @@ -2411,8 +2411,8 @@ Nástroj {1} (verze {2}) se úspěšně nainstaloval. Do souboru manifestu {3} s - Specify the output directory ({0}): - Zadejte výstupní adresář ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Zadejte výstupní adresář ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.de.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.de.xlf index 451f2ccc2f5a..3edecf5eb775 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.de.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.de.xlf @@ -2411,8 +2411,8 @@ Das Tool "{1}" (Version {2}) wurde erfolgreich installiert. Der Eintrag wird der - Specify the output directory ({0}): - Ausgabeverzeichnis ({0}) angeben: + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Ausgabeverzeichnis ({0}) angeben: {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.es.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.es.xlf index 602df59ae22b..25f8f46501af 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.es.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.es.xlf @@ -2411,8 +2411,8 @@ La herramienta "{1}" (versión "{2}") se instaló correctamente. Se ha agregado - Specify the output directory ({0}): - Especifique el directorio de salida ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Especifique el directorio de salida ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.fr.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.fr.xlf index 420523dd6317..43d8e78cf478 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.fr.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.fr.xlf @@ -2411,8 +2411,8 @@ L'outil '{1}' (version '{2}') a été correctement installé. L'entrée est ajou - Specify the output directory ({0}): - Spécifiez le répertoire de sortie ({0}) : + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Spécifiez le répertoire de sortie ({0}) : {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.it.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.it.xlf index 51634ff32480..2fd688bba6af 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.it.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.it.xlf @@ -2411,8 +2411,8 @@ Lo strumento '{1}' versione '{2}' è stato installato. La voce è stata aggiunta - Specify the output directory ({0}): - Specifica la directory di output ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Specifica la directory di output ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ja.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ja.xlf index c0081e525ea6..b087bf0b8ea2 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ja.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ja.xlf @@ -2412,8 +2412,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - 出力ディレクトリ ({0}) を指定します: + Specify the output directory (press Enter for default: '{0}', directory must not exist): + 出力ディレクトリ ({0}) を指定します: {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ko.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ko.xlf index 9bc8643027c0..f441615c4f20 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ko.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ko.xlf @@ -2411,8 +2411,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - 출력 디렉터리 지정({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + 출력 디렉터리 지정({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pl.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pl.xlf index 175ac52a189b..ccdd390a647f 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pl.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pl.xlf @@ -2411,8 +2411,8 @@ Narzędzie „{1}” (wersja „{2}”) zostało pomyślnie zainstalowane. Wpis - Specify the output directory ({0}): - Określ katalog wyjściowy ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Określ katalog wyjściowy ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pt-BR.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pt-BR.xlf index 3aba8ac88a6c..f6c9c85dffdb 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pt-BR.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.pt-BR.xlf @@ -2411,8 +2411,8 @@ A ferramenta '{1}' (versão '{2}') foi instalada com êxito. A entrada foi adici - Specify the output directory ({0}): - Especificar o diretório de saída ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Especificar o diretório de saída ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ru.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ru.xlf index 285f17f59043..bb20ad91e059 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ru.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.ru.xlf @@ -2411,8 +2411,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - Укажите выходной каталог ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Укажите выходной каталог ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.tr.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.tr.xlf index 15f4ee6866d1..f268875b2834 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.tr.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.tr.xlf @@ -2411,8 +2411,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - Çıkış dizinini belirtin ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + Çıkış dizinini belirtin ({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hans.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hans.xlf index 5d926d853b92..b95583b5088e 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hans.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hans.xlf @@ -2411,8 +2411,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - 指定输出目录({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + 指定输出目录({0}): {0} is the default value diff --git a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hant.xlf b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hant.xlf index 12c8075de8b4..a1fd6f561922 100644 --- a/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hant.xlf +++ b/src/Cli/dotnet/Commands/xlf/CliCommandStrings.zh-Hant.xlf @@ -2411,8 +2411,8 @@ Tool '{1}' (version '{2}') was successfully installed. Entry is added to the man - Specify the output directory ({0}): - 指定輸出目錄 ({0}): + Specify the output directory (press Enter for default: '{0}', directory must not exist): + 指定輸出目錄 ({0}): {0} is the default value From f2d6e46cbcf07b14a0a729692270687e6be62ac4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tom=C3=A1=C5=A1=20Matou=C5=A1ek?= Date: Wed, 12 Nov 2025 10:34:14 -0800 Subject: [PATCH 17/18] Refactor dotnet-watch into a package consumable from Aspire.CLI (#51223) --- sdk.slnx | 4 + .../Watch.Aspire/DotNetWatchLauncher.cs | 84 +++++++++++++ .../Watch.Aspire/DotNetWatchOptions.cs | 82 ++++++++++++ ...osoft.DotNet.HotReload.Watch.Aspire.csproj | 40 ++++++ src/BuiltInTools/Watch.Aspire/Program.cs | 12 ++ .../Watch.Aspire/Properties/AssemblyInfo.cs | 7 ++ .../AppModels/BlazorWebAssemblyAppModel.cs | 0 .../BlazorWebAssemblyHostedAppModel.cs | 0 .../AppModels/DefaultAppModel.cs | 0 .../AppModels/HotReloadAppModel.cs | 0 .../AppModels/WebApplicationAppModel.cs | 2 +- .../AppModels/WebServerAppModel.cs | 0 .../Aspire/AspireServiceFactory.cs | 0 .../Browser/BrowserLauncher.cs | 2 +- .../Browser/BrowserRefreshServerFactory.cs | 0 .../Build/BuildNames.cs | 1 + .../Build/BuildReporter.cs | 0 .../Watch/Build/BuildUtilities.cs | 19 +++ .../Build/EvaluationResult.cs | 2 +- .../{dotnet-watch => Watch}/Build/FileItem.cs | 0 .../Build/FilePathExclusions.cs | 0 .../Build/ProjectGraphFactory.cs | 0 .../Build/ProjectGraphUtilities.cs | 13 +- .../Build/ProjectInstanceId.cs | 0 .../Build/ProjectNodeMap.cs | 0 .../Context}/DotNetWatchContext.cs | 0 .../Context}/EnvironmentOptions.cs | 12 +- .../Context}/EnvironmentVariables.cs | 0 .../Context}/GlobalOptions.cs | 0 .../Context}/ProjectOptions.cs | 6 + .../FileWatcher/ChangeKind.cs | 0 .../FileWatcher/DirectoryWatcher.cs | 0 .../FileWatcher/EventBasedDirectoryWatcher.cs | 0 .../FileWatcher/FileWatcher.cs | 0 .../FileWatcher/PollingDirectoryWatcher.cs | 0 .../HotReload/CompilationHandler.cs | 0 .../HotReload/HotReloadDotNetWatcher.cs | 0 .../HotReload/HotReloadEventSource.cs | 0 .../HotReload/IncrementalMSBuildWorkspace.cs | 0 .../HotReload/ScopedCssFileHandler.cs | 0 .../HotReload/StaticFileHandler.cs | 0 .../Microsoft.DotNet.HotReload.Watch.csproj | 39 ++++++ .../Process/IRuntimeProcessLauncher.cs | 0 .../Process/IRuntimeProcessLauncherFactory.cs | 0 .../Process/LaunchSettingsProfile.cs | 14 ++- .../Process/ProcessLaunchResult.cs | 0 .../Process/ProcessRunner.cs | 0 .../Process/ProcessSpec.cs | 0 .../Process/ProjectLauncher.cs | 0 .../Process/RunningProject.cs | 0 .../Process/WebServerProcessStateObserver.cs | 0 .../Watch/Properties/AssemblyInfo.cs | 11 ++ .../Watch/RuntimeDependencies.props | 38 ++++++ .../{dotnet-watch => Watch}/UI/BuildOutput.cs | 0 .../UI/ConsoleInputReader.cs | 0 .../UI/ConsoleReporter.cs | 0 src/BuiltInTools/Watch/UI/IConsole.cs | 18 +++ .../{dotnet-watch => Watch}/UI/IReporter.cs | 1 - .../{dotnet-watch => Watch}/UI/OutputLine.cs | 0 .../UI/PhysicalConsole.cs | 0 .../UI/RestartPrompt.cs | 0 src/BuiltInTools/Watch/UI/ShutdownHandler.cs | 44 +++++++ .../Utilities/CommandLineUtilities.cs | 0 .../Utilities/Disposables.cs | 0 .../Utilities/PathUtilities.cs | 3 + .../Utilities/ProcessUtilities.cs | 0 .../Utilities/Versions.cs | 0 src/BuiltInTools/dotnet-watch.slnf | 5 + .../CommandLine/CommandLineOptions.cs | 18 --- src/BuiltInTools/dotnet-watch/Program.cs | 47 ++----- src/BuiltInTools/dotnet-watch/UI/IConsole.cs | 19 --- .../dotnet-watch/Watch/BuildEvaluator.cs | 2 +- .../Watch/MsBuildFileSetFactory.cs | 2 +- .../dotnet-watch/dotnet-watch.csproj | 48 +------ test/Common/Program.cs | 3 +- ...osoft.DotNet.HotReload.Client.Tests.csproj | 2 +- .../AssertEx.cs | 0 .../AwaitableProcess.cs | 15 ++- .../DebugTestOutputLogger.cs | 0 ...oft.DotNet.HotReload.Test.Utilities.csproj | 19 +++ .../Properties/AssemblyInfo.cs | 9 ++ .../TestAssetExtensions.cs | 12 ++ .../TestLogger.cs | 4 +- .../DotNetWatchLauncherTests.cs | 37 ++++++ .../DotNetWatchOptionsTests.cs | 117 ++++++++++++++++++ ...DotNet.HotReload.Watch.Aspire.Tests.csproj | 19 +++ ...Extensions.DotNetDeltaApplier.Tests.csproj | 4 +- ...rosoft.WebTools.AspireService.Tests.csproj | 2 +- .../Build/BuildUtilitiesTests.cs | 30 +++++ .../CommandLine/CommandLineOptionsTests.cs | 23 ---- .../TestUtilities/TestOptions.cs | 7 +- .../TestUtilities/WatchableApp.cs | 5 +- .../dotnet-watch.Tests.csproj | 7 +- 93 files changed, 730 insertions(+), 180 deletions(-) create mode 100644 src/BuiltInTools/Watch.Aspire/DotNetWatchLauncher.cs create mode 100644 src/BuiltInTools/Watch.Aspire/DotNetWatchOptions.cs create mode 100644 src/BuiltInTools/Watch.Aspire/Microsoft.DotNet.HotReload.Watch.Aspire.csproj create mode 100644 src/BuiltInTools/Watch.Aspire/Program.cs create mode 100644 src/BuiltInTools/Watch.Aspire/Properties/AssemblyInfo.cs rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/BlazorWebAssemblyAppModel.cs (100%) rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/BlazorWebAssemblyHostedAppModel.cs (100%) rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/DefaultAppModel.cs (100%) rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/HotReloadAppModel.cs (100%) rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/WebApplicationAppModel.cs (97%) rename src/BuiltInTools/{dotnet-watch/HotReload => Watch}/AppModels/WebServerAppModel.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Aspire/AspireServiceFactory.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Browser/BrowserLauncher.cs (98%) rename src/BuiltInTools/{dotnet-watch => Watch}/Browser/BrowserRefreshServerFactory.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/BuildNames.cs (97%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/BuildReporter.cs (100%) create mode 100644 src/BuiltInTools/Watch/Build/BuildUtilities.cs rename src/BuiltInTools/{dotnet-watch => Watch}/Build/EvaluationResult.cs (99%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/FileItem.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/FilePathExclusions.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/ProjectGraphFactory.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/ProjectGraphUtilities.cs (95%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/ProjectInstanceId.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Build/ProjectNodeMap.cs (100%) rename src/BuiltInTools/{dotnet-watch/CommandLine => Watch/Context}/DotNetWatchContext.cs (100%) rename src/BuiltInTools/{dotnet-watch/CommandLine => Watch/Context}/EnvironmentOptions.cs (88%) rename src/BuiltInTools/{dotnet-watch/CommandLine => Watch/Context}/EnvironmentVariables.cs (100%) rename src/BuiltInTools/{dotnet-watch/CommandLine => Watch/Context}/GlobalOptions.cs (100%) rename src/BuiltInTools/{dotnet-watch/CommandLine => Watch/Context}/ProjectOptions.cs (85%) rename src/BuiltInTools/{dotnet-watch => Watch}/FileWatcher/ChangeKind.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/FileWatcher/DirectoryWatcher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/FileWatcher/EventBasedDirectoryWatcher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/FileWatcher/FileWatcher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/FileWatcher/PollingDirectoryWatcher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/CompilationHandler.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/HotReloadDotNetWatcher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/HotReloadEventSource.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/IncrementalMSBuildWorkspace.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/ScopedCssFileHandler.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/HotReload/StaticFileHandler.cs (100%) create mode 100644 src/BuiltInTools/Watch/Microsoft.DotNet.HotReload.Watch.csproj rename src/BuiltInTools/{dotnet-watch => Watch}/Process/IRuntimeProcessLauncher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/IRuntimeProcessLauncherFactory.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/LaunchSettingsProfile.cs (85%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/ProcessLaunchResult.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/ProcessRunner.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/ProcessSpec.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/ProjectLauncher.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/RunningProject.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Process/WebServerProcessStateObserver.cs (100%) create mode 100644 src/BuiltInTools/Watch/Properties/AssemblyInfo.cs create mode 100644 src/BuiltInTools/Watch/RuntimeDependencies.props rename src/BuiltInTools/{dotnet-watch => Watch}/UI/BuildOutput.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/UI/ConsoleInputReader.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/UI/ConsoleReporter.cs (100%) create mode 100644 src/BuiltInTools/Watch/UI/IConsole.cs rename src/BuiltInTools/{dotnet-watch => Watch}/UI/IReporter.cs (99%) rename src/BuiltInTools/{dotnet-watch => Watch}/UI/OutputLine.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/UI/PhysicalConsole.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/UI/RestartPrompt.cs (100%) create mode 100644 src/BuiltInTools/Watch/UI/ShutdownHandler.cs rename src/BuiltInTools/{dotnet-watch => Watch}/Utilities/CommandLineUtilities.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Utilities/Disposables.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Utilities/PathUtilities.cs (93%) rename src/BuiltInTools/{dotnet-watch => Watch}/Utilities/ProcessUtilities.cs (100%) rename src/BuiltInTools/{dotnet-watch => Watch}/Utilities/Versions.cs (100%) delete mode 100644 src/BuiltInTools/dotnet-watch/UI/IConsole.cs rename test/{dotnet-watch.Tests/TestUtilities => Microsoft.DotNet.HotReload.Test.Utilities}/AssertEx.cs (100%) rename test/{dotnet-watch.Tests/TestUtilities => Microsoft.DotNet.HotReload.Test.Utilities}/AwaitableProcess.cs (91%) rename test/{dotnet-watch.Tests/TestUtilities => Microsoft.DotNet.HotReload.Test.Utilities}/DebugTestOutputLogger.cs (100%) create mode 100644 test/Microsoft.DotNet.HotReload.Test.Utilities/Microsoft.DotNet.HotReload.Test.Utilities.csproj create mode 100644 test/Microsoft.DotNet.HotReload.Test.Utilities/Properties/AssemblyInfo.cs create mode 100644 test/Microsoft.DotNet.HotReload.Test.Utilities/TestAssetExtensions.cs rename test/{dotnet-watch.Tests/TestUtilities => Microsoft.DotNet.HotReload.Test.Utilities}/TestLogger.cs (92%) create mode 100644 test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchLauncherTests.cs create mode 100644 test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchOptionsTests.cs create mode 100644 test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/Microsoft.DotNet.HotReload.Watch.Aspire.Tests.csproj create mode 100644 test/dotnet-watch.Tests/Build/BuildUtilitiesTests.cs diff --git a/sdk.slnx b/sdk.slnx index c8592eeb1f7b..5077b0285a6c 100644 --- a/sdk.slnx +++ b/sdk.slnx @@ -59,6 +59,8 @@ + + @@ -325,6 +327,8 @@ + + diff --git a/src/BuiltInTools/Watch.Aspire/DotNetWatchLauncher.cs b/src/BuiltInTools/Watch.Aspire/DotNetWatchLauncher.cs new file mode 100644 index 000000000000..260b35c23042 --- /dev/null +++ b/src/BuiltInTools/Watch.Aspire/DotNetWatchLauncher.cs @@ -0,0 +1,84 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using Microsoft.Extensions.Logging; + +namespace Microsoft.DotNet.Watch; + +internal static class DotNetWatchLauncher +{ + public static async Task RunAsync(string workingDirectory, DotNetWatchOptions options) + { + var globalOptions = new GlobalOptions() + { + Quiet = options.IsQuiet, + Verbose = options.IsVerbose, + NoHotReload = false, + NonInteractive = true, + }; + + var commandArguments = new List(); + if (options.NoLaunchProfile) + { + commandArguments.Add("--no-launch-profile"); + } + + commandArguments.AddRange(options.ApplicationArguments); + + var rootProjectOptions = new ProjectOptions() + { + IsRootProject = true, + ProjectPath = options.ProjectPath, + WorkingDirectory = workingDirectory, + TargetFramework = null, + BuildArguments = [], + NoLaunchProfile = options.NoLaunchProfile, + LaunchProfileName = null, + Command = "run", + CommandArguments = [.. commandArguments], + LaunchEnvironmentVariables = [], + }; + + var muxerPath = Path.GetFullPath(Path.Combine(options.SdkDirectory, "..", "..", "dotnet" + PathUtilities.ExecutableExtension)); + + var console = new PhysicalConsole(TestFlags.None); + var reporter = new ConsoleReporter(console, globalOptions.Verbose, globalOptions.Quiet, suppressEmojis: false); + var environmentOptions = EnvironmentOptions.FromEnvironment(muxerPath); + var processRunner = new ProcessRunner(environmentOptions.GetProcessCleanupTimeout(isHotReloadEnabled: true)); + var loggerFactory = new LoggerFactory(reporter); + var logger = loggerFactory.CreateLogger(DotNetWatchContext.DefaultLogComponentName); + + using var context = new DotNetWatchContext() + { + ProcessOutputReporter = reporter, + LoggerFactory = loggerFactory, + Logger = logger, + BuildLogger = loggerFactory.CreateLogger(DotNetWatchContext.BuildLogComponentName), + ProcessRunner = processRunner, + Options = globalOptions, + EnvironmentOptions = environmentOptions, + RootProjectOptions = rootProjectOptions, + BrowserRefreshServerFactory = new BrowserRefreshServerFactory(), + BrowserLauncher = new BrowserLauncher(logger, reporter, environmentOptions), + }; + + using var shutdownHandler = new ShutdownHandler(console, logger); + + try + { + var watcher = new HotReloadDotNetWatcher(context, console, runtimeProcessLauncherFactory: null); + await watcher.WatchAsync(shutdownHandler.CancellationToken); + } + catch (OperationCanceledException) when (shutdownHandler.CancellationToken.IsCancellationRequested) + { + // Ctrl+C forced an exit + } + catch (Exception e) + { + logger.LogError("An unexpected error occurred: {Exception}", e.ToString()); + return false; + } + + return true; + } +} diff --git a/src/BuiltInTools/Watch.Aspire/DotNetWatchOptions.cs b/src/BuiltInTools/Watch.Aspire/DotNetWatchOptions.cs new file mode 100644 index 000000000000..2ccf84b885b5 --- /dev/null +++ b/src/BuiltInTools/Watch.Aspire/DotNetWatchOptions.cs @@ -0,0 +1,82 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Collections.Immutable; +using System.CommandLine; +using System.Diagnostics.CodeAnalysis; + +namespace Microsoft.DotNet.Watch; + +internal sealed class DotNetWatchOptions +{ + /// + /// The .NET SDK directory to load msbuild from (e.g. C:\Program Files\dotnet\sdk\10.0.100). + /// Also used to locate `dotnet` executable. + /// + public required string SdkDirectory { get; init; } + + public required string ProjectPath { get; init; } + public required ImmutableArray ApplicationArguments { get; init; } + public bool IsVerbose { get; init; } + public bool IsQuiet { get; init; } + public bool NoLaunchProfile { get; init; } + + public static bool TryParse(string[] args, [NotNullWhen(true)] out DotNetWatchOptions? options) + { + var sdkOption = new Option("--sdk") { Arity = ArgumentArity.ExactlyOne, Required = true, AllowMultipleArgumentsPerToken = false }; + var projectOption = new Option("--project") { Arity = ArgumentArity.ExactlyOne, Required = true, AllowMultipleArgumentsPerToken = false }; + var quietOption = new Option("--quiet") { Arity = ArgumentArity.Zero }; + var verboseOption = new Option("--verbose") { Arity = ArgumentArity.Zero }; + var noLaunchProfileOption = new Option("--no-launch-profile") { Arity = ArgumentArity.Zero }; + var applicationArguments = new Argument("arguments") { Arity = ArgumentArity.ZeroOrMore }; + + verboseOption.Validators.Add(v => + { + if (v.GetValue(quietOption) && v.GetValue(verboseOption)) + { + v.AddError("Cannot specify both '--quiet' and '--verbose' options."); + } + }); + + var rootCommand = new RootCommand() + { + Directives = { new EnvironmentVariablesDirective() }, + Options = + { + sdkOption, + projectOption, + quietOption, + verboseOption, + noLaunchProfileOption + }, + Arguments = + { + applicationArguments + } + }; + + var parseResult = rootCommand.Parse(args); + if (parseResult.Errors.Count > 0) + { + foreach (var error in parseResult.Errors) + { + Console.Error.WriteLine(error); + } + + options = null; + return false; + } + + options = new DotNetWatchOptions() + { + SdkDirectory = parseResult.GetRequiredValue(sdkOption), + ProjectPath = parseResult.GetRequiredValue(projectOption), + IsQuiet = parseResult.GetValue(quietOption), + IsVerbose = parseResult.GetValue(verboseOption), + ApplicationArguments = [.. parseResult.GetValue(applicationArguments) ?? []], + NoLaunchProfile = parseResult.GetValue(noLaunchProfileOption), + }; + + return true; + } +} diff --git a/src/BuiltInTools/Watch.Aspire/Microsoft.DotNet.HotReload.Watch.Aspire.csproj b/src/BuiltInTools/Watch.Aspire/Microsoft.DotNet.HotReload.Watch.Aspire.csproj new file mode 100644 index 000000000000..fb08c258b800 --- /dev/null +++ b/src/BuiltInTools/Watch.Aspire/Microsoft.DotNet.HotReload.Watch.Aspire.csproj @@ -0,0 +1,40 @@ + + + + + $(SdkTargetFramework) + MicrosoftAspNetCore + Exe + Microsoft.DotNet.Watch + true + + + true + true + true + Microsoft.DotNet.HotReload.Watch.Aspire + + A supporting package for Aspire CLI: + https://github.com/dotnet/aspire + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/BuiltInTools/Watch.Aspire/Program.cs b/src/BuiltInTools/Watch.Aspire/Program.cs new file mode 100644 index 000000000000..37de5ceca579 --- /dev/null +++ b/src/BuiltInTools/Watch.Aspire/Program.cs @@ -0,0 +1,12 @@ +using Microsoft.Build.Locator; +using Microsoft.DotNet.Watch; + +if (!DotNetWatchOptions.TryParse(args, out var options)) +{ + return -1; +} + +MSBuildLocator.RegisterMSBuildPath(options.SdkDirectory); + +var workingDirectory = Directory.GetCurrentDirectory(); +return await DotNetWatchLauncher.RunAsync(workingDirectory, options) ? 0 : 1; diff --git a/src/BuiltInTools/Watch.Aspire/Properties/AssemblyInfo.cs b/src/BuiltInTools/Watch.Aspire/Properties/AssemblyInfo.cs new file mode 100644 index 000000000000..74a1e15ab7a8 --- /dev/null +++ b/src/BuiltInTools/Watch.Aspire/Properties/AssemblyInfo.cs @@ -0,0 +1,7 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Runtime.CompilerServices; + +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Watch.Aspire.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")] diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/BlazorWebAssemblyAppModel.cs b/src/BuiltInTools/Watch/AppModels/BlazorWebAssemblyAppModel.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/BlazorWebAssemblyAppModel.cs rename to src/BuiltInTools/Watch/AppModels/BlazorWebAssemblyAppModel.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/BlazorWebAssemblyHostedAppModel.cs b/src/BuiltInTools/Watch/AppModels/BlazorWebAssemblyHostedAppModel.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/BlazorWebAssemblyHostedAppModel.cs rename to src/BuiltInTools/Watch/AppModels/BlazorWebAssemblyHostedAppModel.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/DefaultAppModel.cs b/src/BuiltInTools/Watch/AppModels/DefaultAppModel.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/DefaultAppModel.cs rename to src/BuiltInTools/Watch/AppModels/DefaultAppModel.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/HotReloadAppModel.cs b/src/BuiltInTools/Watch/AppModels/HotReloadAppModel.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/HotReloadAppModel.cs rename to src/BuiltInTools/Watch/AppModels/HotReloadAppModel.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/WebApplicationAppModel.cs b/src/BuiltInTools/Watch/AppModels/WebApplicationAppModel.cs similarity index 97% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/WebApplicationAppModel.cs rename to src/BuiltInTools/Watch/AppModels/WebApplicationAppModel.cs index 4ca515a862a6..cefcd43cf320 100644 --- a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/WebApplicationAppModel.cs +++ b/src/BuiltInTools/Watch/AppModels/WebApplicationAppModel.cs @@ -40,7 +40,7 @@ internal abstract class WebApplicationAppModel(DotNetWatchContext context) : Hot protected WebAssemblyHotReloadClient CreateWebAssemblyClient(ILogger clientLogger, ILogger agentLogger, BrowserRefreshServer browserRefreshServer, ProjectGraphNode clientProject) { var capabilities = clientProject.GetWebAssemblyCapabilities().ToImmutableArray(); - var targetFramework = clientProject.GetTargetFrameworkVersion() ?? throw new InvalidOperationException("Project doesn't define TargetFrameworkVersion"); + var targetFramework = clientProject.GetTargetFrameworkVersion() ?? throw new InvalidOperationException($"Project doesn't define {PropertyNames.TargetFrameworkMoniker}"); return new WebAssemblyHotReloadClient(clientLogger, agentLogger, browserRefreshServer, capabilities, targetFramework, context.EnvironmentOptions.TestFlags.HasFlag(TestFlags.MockBrowser)); } diff --git a/src/BuiltInTools/dotnet-watch/HotReload/AppModels/WebServerAppModel.cs b/src/BuiltInTools/Watch/AppModels/WebServerAppModel.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/AppModels/WebServerAppModel.cs rename to src/BuiltInTools/Watch/AppModels/WebServerAppModel.cs diff --git a/src/BuiltInTools/dotnet-watch/Aspire/AspireServiceFactory.cs b/src/BuiltInTools/Watch/Aspire/AspireServiceFactory.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Aspire/AspireServiceFactory.cs rename to src/BuiltInTools/Watch/Aspire/AspireServiceFactory.cs diff --git a/src/BuiltInTools/dotnet-watch/Browser/BrowserLauncher.cs b/src/BuiltInTools/Watch/Browser/BrowserLauncher.cs similarity index 98% rename from src/BuiltInTools/dotnet-watch/Browser/BrowserLauncher.cs rename to src/BuiltInTools/Watch/Browser/BrowserLauncher.cs index c841191e0208..de999b11e0a5 100644 --- a/src/BuiltInTools/dotnet-watch/Browser/BrowserLauncher.cs +++ b/src/BuiltInTools/Watch/Browser/BrowserLauncher.cs @@ -108,7 +108,7 @@ private bool CanLaunchBrowser(ProjectOptions projectOptions, [NotNullWhen(true)] return false; } - if (!CommandLineOptions.IsCodeExecutionCommand(projectOptions.Command)) + if (!projectOptions.IsCodeExecutionCommand) { logger.LogDebug("Command '{Command}' does not support launching browsers.", projectOptions.Command); return false; diff --git a/src/BuiltInTools/dotnet-watch/Browser/BrowserRefreshServerFactory.cs b/src/BuiltInTools/Watch/Browser/BrowserRefreshServerFactory.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Browser/BrowserRefreshServerFactory.cs rename to src/BuiltInTools/Watch/Browser/BrowserRefreshServerFactory.cs diff --git a/src/BuiltInTools/dotnet-watch/Build/BuildNames.cs b/src/BuiltInTools/Watch/Build/BuildNames.cs similarity index 97% rename from src/BuiltInTools/dotnet-watch/Build/BuildNames.cs rename to src/BuiltInTools/Watch/Build/BuildNames.cs index d92d5af86c14..f5f8c3463a3f 100644 --- a/src/BuiltInTools/dotnet-watch/Build/BuildNames.cs +++ b/src/BuiltInTools/Watch/Build/BuildNames.cs @@ -7,6 +7,7 @@ internal static class PropertyNames { public const string TargetFramework = nameof(TargetFramework); public const string TargetFrameworkIdentifier = nameof(TargetFrameworkIdentifier); + public const string TargetFrameworkMoniker = nameof(TargetFrameworkMoniker); public const string TargetPath = nameof(TargetPath); public const string EnableDefaultItems = nameof(EnableDefaultItems); public const string TargetFrameworks = nameof(TargetFrameworks); diff --git a/src/BuiltInTools/dotnet-watch/Build/BuildReporter.cs b/src/BuiltInTools/Watch/Build/BuildReporter.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/BuildReporter.cs rename to src/BuiltInTools/Watch/Build/BuildReporter.cs diff --git a/src/BuiltInTools/Watch/Build/BuildUtilities.cs b/src/BuiltInTools/Watch/Build/BuildUtilities.cs new file mode 100644 index 000000000000..1a336530697e --- /dev/null +++ b/src/BuiltInTools/Watch/Build/BuildUtilities.cs @@ -0,0 +1,19 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +namespace Microsoft.DotNet.Watch; + +internal static class BuildUtilities +{ + // Parses name=value pairs passed to --property. Skips invalid input. + public static IEnumerable<(string key, string value)> ParseBuildProperties(IEnumerable arguments) + => from argument in arguments + let colon = argument.IndexOf(':') + where colon >= 0 && argument[0..colon] is "--property" or "-property" or "/property" or "/p" or "-p" or "--p" + let eq = argument.IndexOf('=', colon) + where eq >= 0 + let name = argument[(colon + 1)..eq].Trim() + let value = argument[(eq + 1)..] + where name is not [] + select (name, value); +} diff --git a/src/BuiltInTools/dotnet-watch/Build/EvaluationResult.cs b/src/BuiltInTools/Watch/Build/EvaluationResult.cs similarity index 99% rename from src/BuiltInTools/dotnet-watch/Build/EvaluationResult.cs rename to src/BuiltInTools/Watch/Build/EvaluationResult.cs index d4090ce69840..bb04a3683a7e 100644 --- a/src/BuiltInTools/dotnet-watch/Build/EvaluationResult.cs +++ b/src/BuiltInTools/Watch/Build/EvaluationResult.cs @@ -36,7 +36,7 @@ public static ImmutableDictionary GetGlobalBuildOptions(IEnumera { // See https://github.com/dotnet/project-system/blob/main/docs/well-known-project-properties.md - return CommandLineOptions.ParseBuildProperties(buildArguments) + return BuildUtilities.ParseBuildProperties(buildArguments) .ToImmutableDictionary(keySelector: arg => arg.key, elementSelector: arg => arg.value) .SetItem(PropertyNames.DotNetWatchBuild, "true") .SetItem(PropertyNames.DesignTimeBuild, "true") diff --git a/src/BuiltInTools/dotnet-watch/Build/FileItem.cs b/src/BuiltInTools/Watch/Build/FileItem.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/FileItem.cs rename to src/BuiltInTools/Watch/Build/FileItem.cs diff --git a/src/BuiltInTools/dotnet-watch/Build/FilePathExclusions.cs b/src/BuiltInTools/Watch/Build/FilePathExclusions.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/FilePathExclusions.cs rename to src/BuiltInTools/Watch/Build/FilePathExclusions.cs diff --git a/src/BuiltInTools/dotnet-watch/Build/ProjectGraphFactory.cs b/src/BuiltInTools/Watch/Build/ProjectGraphFactory.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/ProjectGraphFactory.cs rename to src/BuiltInTools/Watch/Build/ProjectGraphFactory.cs diff --git a/src/BuiltInTools/dotnet-watch/Build/ProjectGraphUtilities.cs b/src/BuiltInTools/Watch/Build/ProjectGraphUtilities.cs similarity index 95% rename from src/BuiltInTools/dotnet-watch/Build/ProjectGraphUtilities.cs rename to src/BuiltInTools/Watch/Build/ProjectGraphUtilities.cs index 6cb4c6b57a04..40314297b76a 100644 --- a/src/BuiltInTools/dotnet-watch/Build/ProjectGraphUtilities.cs +++ b/src/BuiltInTools/Watch/Build/ProjectGraphUtilities.cs @@ -1,9 +1,9 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. +using System.Runtime.Versioning; using Microsoft.Build.Execution; using Microsoft.Build.Graph; -using Microsoft.DotNet.Cli; namespace Microsoft.DotNet.Watch; @@ -19,7 +19,16 @@ public static IEnumerable GetTargetFrameworks(this ProjectGraphNode proj => projectNode.GetStringListPropertyValue(PropertyNames.TargetFrameworks); public static Version? GetTargetFrameworkVersion(this ProjectGraphNode projectNode) - => EnvironmentVariableNames.TryParseTargetFrameworkVersion(projectNode.ProjectInstance.GetPropertyValue(PropertyNames.TargetFrameworkVersion)); + { + try + { + return new FrameworkName(projectNode.ProjectInstance.GetPropertyValue(PropertyNames.TargetFrameworkMoniker)).Version; + } + catch + { + return null; + } + } public static IEnumerable GetWebAssemblyCapabilities(this ProjectGraphNode projectNode) => projectNode.GetStringListPropertyValue(PropertyNames.WebAssemblyHotReloadCapabilities); diff --git a/src/BuiltInTools/dotnet-watch/Build/ProjectInstanceId.cs b/src/BuiltInTools/Watch/Build/ProjectInstanceId.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/ProjectInstanceId.cs rename to src/BuiltInTools/Watch/Build/ProjectInstanceId.cs diff --git a/src/BuiltInTools/dotnet-watch/Build/ProjectNodeMap.cs b/src/BuiltInTools/Watch/Build/ProjectNodeMap.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Build/ProjectNodeMap.cs rename to src/BuiltInTools/Watch/Build/ProjectNodeMap.cs diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/DotNetWatchContext.cs b/src/BuiltInTools/Watch/Context/DotNetWatchContext.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/CommandLine/DotNetWatchContext.cs rename to src/BuiltInTools/Watch/Context/DotNetWatchContext.cs diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/EnvironmentOptions.cs b/src/BuiltInTools/Watch/Context/EnvironmentOptions.cs similarity index 88% rename from src/BuiltInTools/dotnet-watch/CommandLine/EnvironmentOptions.cs rename to src/BuiltInTools/Watch/Context/EnvironmentOptions.cs index d0e84844de86..20b850688437 100644 --- a/src/BuiltInTools/dotnet-watch/CommandLine/EnvironmentOptions.cs +++ b/src/BuiltInTools/Watch/Context/EnvironmentOptions.cs @@ -41,10 +41,10 @@ internal sealed record EnvironmentOptions( TestFlags TestFlags = TestFlags.None, string TestOutput = "") { - public static EnvironmentOptions FromEnvironment() => new + public static EnvironmentOptions FromEnvironment(string muxerPath) => new ( WorkingDirectory: Directory.GetCurrentDirectory(), - MuxerPath: GetMuxerPathFromEnvironment(), + MuxerPath: ValidateMuxerPath(muxerPath), ProcessCleanupTimeout: EnvironmentVariables.ProcessCleanupTimeout, IsPollingEnabled: EnvironmentVariables.IsPollingEnabled, SuppressHandlingStaticContentFiles: EnvironmentVariables.SuppressHandlingStaticContentFiles, @@ -69,12 +69,10 @@ public TimeSpan GetProcessCleanupTimeout(bool isHotReloadEnabled) public bool RunningAsTest { get => (TestFlags & TestFlags.RunningAsTest) != TestFlags.None; } - private static string GetMuxerPathFromEnvironment() + private static string ValidateMuxerPath(string path) { - var muxerPath = Environment.ProcessPath; - Debug.Assert(muxerPath != null); - Debug.Assert(Path.GetFileNameWithoutExtension(muxerPath) == "dotnet", $"Invalid muxer path {muxerPath}"); - return muxerPath; + Debug.Assert(Path.GetFileNameWithoutExtension(path) == "dotnet"); + return path; } public string? GetBinLogPath(string projectPath, string operationName, GlobalOptions options) diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/EnvironmentVariables.cs b/src/BuiltInTools/Watch/Context/EnvironmentVariables.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/CommandLine/EnvironmentVariables.cs rename to src/BuiltInTools/Watch/Context/EnvironmentVariables.cs diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/GlobalOptions.cs b/src/BuiltInTools/Watch/Context/GlobalOptions.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/CommandLine/GlobalOptions.cs rename to src/BuiltInTools/Watch/Context/GlobalOptions.cs diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/ProjectOptions.cs b/src/BuiltInTools/Watch/Context/ProjectOptions.cs similarity index 85% rename from src/BuiltInTools/dotnet-watch/CommandLine/ProjectOptions.cs rename to src/BuiltInTools/Watch/Context/ProjectOptions.cs index 12b8b889f1f7..20eb2eed69eb 100644 --- a/src/BuiltInTools/dotnet-watch/CommandLine/ProjectOptions.cs +++ b/src/BuiltInTools/Watch/Context/ProjectOptions.cs @@ -27,4 +27,10 @@ internal sealed record ProjectOptions /// Additional environment variables to set to the running process. /// public required IReadOnlyList<(string name, string value)> LaunchEnvironmentVariables { get; init; } + + /// + /// Returns true if the command executes the code of the target project. + /// + public bool IsCodeExecutionCommand + => Command is "run" or "test"; } diff --git a/src/BuiltInTools/dotnet-watch/FileWatcher/ChangeKind.cs b/src/BuiltInTools/Watch/FileWatcher/ChangeKind.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/FileWatcher/ChangeKind.cs rename to src/BuiltInTools/Watch/FileWatcher/ChangeKind.cs diff --git a/src/BuiltInTools/dotnet-watch/FileWatcher/DirectoryWatcher.cs b/src/BuiltInTools/Watch/FileWatcher/DirectoryWatcher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/FileWatcher/DirectoryWatcher.cs rename to src/BuiltInTools/Watch/FileWatcher/DirectoryWatcher.cs diff --git a/src/BuiltInTools/dotnet-watch/FileWatcher/EventBasedDirectoryWatcher.cs b/src/BuiltInTools/Watch/FileWatcher/EventBasedDirectoryWatcher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/FileWatcher/EventBasedDirectoryWatcher.cs rename to src/BuiltInTools/Watch/FileWatcher/EventBasedDirectoryWatcher.cs diff --git a/src/BuiltInTools/dotnet-watch/FileWatcher/FileWatcher.cs b/src/BuiltInTools/Watch/FileWatcher/FileWatcher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/FileWatcher/FileWatcher.cs rename to src/BuiltInTools/Watch/FileWatcher/FileWatcher.cs diff --git a/src/BuiltInTools/dotnet-watch/FileWatcher/PollingDirectoryWatcher.cs b/src/BuiltInTools/Watch/FileWatcher/PollingDirectoryWatcher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/FileWatcher/PollingDirectoryWatcher.cs rename to src/BuiltInTools/Watch/FileWatcher/PollingDirectoryWatcher.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs b/src/BuiltInTools/Watch/HotReload/CompilationHandler.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/CompilationHandler.cs rename to src/BuiltInTools/Watch/HotReload/CompilationHandler.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/HotReloadDotNetWatcher.cs b/src/BuiltInTools/Watch/HotReload/HotReloadDotNetWatcher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/HotReloadDotNetWatcher.cs rename to src/BuiltInTools/Watch/HotReload/HotReloadDotNetWatcher.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/HotReloadEventSource.cs b/src/BuiltInTools/Watch/HotReload/HotReloadEventSource.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/HotReloadEventSource.cs rename to src/BuiltInTools/Watch/HotReload/HotReloadEventSource.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs b/src/BuiltInTools/Watch/HotReload/IncrementalMSBuildWorkspace.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/IncrementalMSBuildWorkspace.cs rename to src/BuiltInTools/Watch/HotReload/IncrementalMSBuildWorkspace.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/ScopedCssFileHandler.cs b/src/BuiltInTools/Watch/HotReload/ScopedCssFileHandler.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/ScopedCssFileHandler.cs rename to src/BuiltInTools/Watch/HotReload/ScopedCssFileHandler.cs diff --git a/src/BuiltInTools/dotnet-watch/HotReload/StaticFileHandler.cs b/src/BuiltInTools/Watch/HotReload/StaticFileHandler.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/HotReload/StaticFileHandler.cs rename to src/BuiltInTools/Watch/HotReload/StaticFileHandler.cs diff --git a/src/BuiltInTools/Watch/Microsoft.DotNet.HotReload.Watch.csproj b/src/BuiltInTools/Watch/Microsoft.DotNet.HotReload.Watch.csproj new file mode 100644 index 000000000000..48e96f316ba5 --- /dev/null +++ b/src/BuiltInTools/Watch/Microsoft.DotNet.HotReload.Watch.csproj @@ -0,0 +1,39 @@ + + + + + + + + + $(SdkTargetFramework) + Library + Hot Reload watch implementation + Microsoft.DotNet.Watch + MicrosoftAspNetCore + + + $(NoWarn);CS9057 + + + + + + + + + + + + + + + + diff --git a/src/BuiltInTools/dotnet-watch/Process/IRuntimeProcessLauncher.cs b/src/BuiltInTools/Watch/Process/IRuntimeProcessLauncher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/IRuntimeProcessLauncher.cs rename to src/BuiltInTools/Watch/Process/IRuntimeProcessLauncher.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/IRuntimeProcessLauncherFactory.cs b/src/BuiltInTools/Watch/Process/IRuntimeProcessLauncherFactory.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/IRuntimeProcessLauncherFactory.cs rename to src/BuiltInTools/Watch/Process/IRuntimeProcessLauncherFactory.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/LaunchSettingsProfile.cs b/src/BuiltInTools/Watch/Process/LaunchSettingsProfile.cs similarity index 85% rename from src/BuiltInTools/dotnet-watch/Process/LaunchSettingsProfile.cs rename to src/BuiltInTools/Watch/Process/LaunchSettingsProfile.cs index a1c6397bbf6f..1ec08ab04ea2 100644 --- a/src/BuiltInTools/dotnet-watch/Process/LaunchSettingsProfile.cs +++ b/src/BuiltInTools/Watch/Process/LaunchSettingsProfile.cs @@ -5,8 +5,6 @@ using System.Diagnostics; using System.Text.Json; using System.Text.Json.Serialization; -using Microsoft.DotNet.Cli.Commands; -using Microsoft.DotNet.Cli.Commands.Run; using Microsoft.Extensions.Logging; namespace Microsoft.DotNet.Watch @@ -31,18 +29,18 @@ internal sealed class LaunchSettingsProfile var projectDirectory = Path.GetDirectoryName(projectPath); Debug.Assert(projectDirectory != null); - var launchSettingsPath = CommonRunHelpers.GetPropertiesLaunchSettingsPath(projectDirectory, "Properties"); + var launchSettingsPath = GetPropertiesLaunchSettingsPath(projectDirectory, "Properties"); bool hasLaunchSettings = File.Exists(launchSettingsPath); var projectNameWithoutExtension = Path.GetFileNameWithoutExtension(projectPath); - var runJsonPath = CommonRunHelpers.GetFlatLaunchSettingsPath(projectDirectory, projectNameWithoutExtension); + var runJsonPath = GetFlatLaunchSettingsPath(projectDirectory, projectNameWithoutExtension); bool hasRunJson = File.Exists(runJsonPath); if (hasLaunchSettings) { if (hasRunJson) { - logger.LogWarning(CliCommandStrings.RunCommandWarningRunJsonNotUsed, runJsonPath, launchSettingsPath); + logger.LogWarning("Warning: Settings from '{JsonPath}' are not used because '{LaunchSettingsPath}' has precedence.", runJsonPath, launchSettingsPath); } } else if (hasRunJson) @@ -98,6 +96,12 @@ internal sealed class LaunchSettingsProfile return namedProfile; } + private static string GetPropertiesLaunchSettingsPath(string directoryPath, string propertiesDirectoryName) + => Path.Combine(directoryPath, propertiesDirectoryName, "launchSettings.json"); + + private static string GetFlatLaunchSettingsPath(string directoryPath, string projectNameWithoutExtension) + => Path.Join(directoryPath, $"{projectNameWithoutExtension}.run.json"); + private static LaunchSettingsProfile? ReadDefaultLaunchProfile(LaunchSettingsJson? launchSettings, ILogger logger) { if (launchSettings is null || launchSettings.Profiles is null) diff --git a/src/BuiltInTools/dotnet-watch/Process/ProcessLaunchResult.cs b/src/BuiltInTools/Watch/Process/ProcessLaunchResult.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/ProcessLaunchResult.cs rename to src/BuiltInTools/Watch/Process/ProcessLaunchResult.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/ProcessRunner.cs b/src/BuiltInTools/Watch/Process/ProcessRunner.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/ProcessRunner.cs rename to src/BuiltInTools/Watch/Process/ProcessRunner.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/ProcessSpec.cs b/src/BuiltInTools/Watch/Process/ProcessSpec.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/ProcessSpec.cs rename to src/BuiltInTools/Watch/Process/ProcessSpec.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/ProjectLauncher.cs b/src/BuiltInTools/Watch/Process/ProjectLauncher.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/ProjectLauncher.cs rename to src/BuiltInTools/Watch/Process/ProjectLauncher.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/RunningProject.cs b/src/BuiltInTools/Watch/Process/RunningProject.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/RunningProject.cs rename to src/BuiltInTools/Watch/Process/RunningProject.cs diff --git a/src/BuiltInTools/dotnet-watch/Process/WebServerProcessStateObserver.cs b/src/BuiltInTools/Watch/Process/WebServerProcessStateObserver.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Process/WebServerProcessStateObserver.cs rename to src/BuiltInTools/Watch/Process/WebServerProcessStateObserver.cs diff --git a/src/BuiltInTools/Watch/Properties/AssemblyInfo.cs b/src/BuiltInTools/Watch/Properties/AssemblyInfo.cs new file mode 100644 index 000000000000..b54564628dc0 --- /dev/null +++ b/src/BuiltInTools/Watch/Properties/AssemblyInfo.cs @@ -0,0 +1,11 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Runtime.CompilerServices; + +[assembly: InternalsVisibleTo("dotnet-watch, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("dotnet-watch.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Test.Utilities, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Watch.Aspire, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Watch.Aspire.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")] diff --git a/src/BuiltInTools/Watch/RuntimeDependencies.props b/src/BuiltInTools/Watch/RuntimeDependencies.props new file mode 100644 index 000000000000..7d4d40a9ab8d --- /dev/null +++ b/src/BuiltInTools/Watch/RuntimeDependencies.props @@ -0,0 +1,38 @@ + + + + None + true + false + TargetFramework;TargetFrameworks + hotreload\net6.0\Microsoft.AspNetCore.Watch.BrowserRefresh.dll + PreserveNewest + + + false + + + + None + true + false + TargetFramework=net10.0 + hotreload\net10.0\Microsoft.Extensions.DotNetDeltaApplier.dll + PreserveNewest + false + + + + None + true + false + TargetFramework=net6.0 + hotreload\net6.0\Microsoft.Extensions.DotNetDeltaApplier.dll + PreserveNewest + false + + + diff --git a/src/BuiltInTools/dotnet-watch/UI/BuildOutput.cs b/src/BuiltInTools/Watch/UI/BuildOutput.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/BuildOutput.cs rename to src/BuiltInTools/Watch/UI/BuildOutput.cs diff --git a/src/BuiltInTools/dotnet-watch/UI/ConsoleInputReader.cs b/src/BuiltInTools/Watch/UI/ConsoleInputReader.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/ConsoleInputReader.cs rename to src/BuiltInTools/Watch/UI/ConsoleInputReader.cs diff --git a/src/BuiltInTools/dotnet-watch/UI/ConsoleReporter.cs b/src/BuiltInTools/Watch/UI/ConsoleReporter.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/ConsoleReporter.cs rename to src/BuiltInTools/Watch/UI/ConsoleReporter.cs diff --git a/src/BuiltInTools/Watch/UI/IConsole.cs b/src/BuiltInTools/Watch/UI/IConsole.cs new file mode 100644 index 000000000000..54b1d8cfec76 --- /dev/null +++ b/src/BuiltInTools/Watch/UI/IConsole.cs @@ -0,0 +1,18 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +namespace Microsoft.DotNet.Watch; + +/// +/// This API supports infrastructure and is not intended to be used +/// directly from your code. This API may change or be removed in future releases. +/// +internal interface IConsole +{ + event Action KeyPressed; + TextWriter Out { get; } + TextWriter Error { get; } + ConsoleColor ForegroundColor { get; set; } + void ResetColor(); + void Clear(); +} diff --git a/src/BuiltInTools/dotnet-watch/UI/IReporter.cs b/src/BuiltInTools/Watch/UI/IReporter.cs similarity index 99% rename from src/BuiltInTools/dotnet-watch/UI/IReporter.cs rename to src/BuiltInTools/Watch/UI/IReporter.cs index 4224aefb4855..2a118db336ee 100644 --- a/src/BuiltInTools/dotnet-watch/UI/IReporter.cs +++ b/src/BuiltInTools/Watch/UI/IReporter.cs @@ -169,7 +169,6 @@ public MessageDescriptor WithSeverityWhen(MessageSeverity severity, bool conditi : this; public static readonly ImmutableDictionary ComponentEmojis = ImmutableDictionary.Empty - .Add(Program.LogComponentName, Emoji.Watch) .Add(DotNetWatchContext.DefaultLogComponentName, Emoji.Watch) .Add(DotNetWatchContext.BuildLogComponentName, Emoji.Build) .Add(HotReloadDotNetWatcher.ClientLogComponentName, Emoji.HotReload) diff --git a/src/BuiltInTools/dotnet-watch/UI/OutputLine.cs b/src/BuiltInTools/Watch/UI/OutputLine.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/OutputLine.cs rename to src/BuiltInTools/Watch/UI/OutputLine.cs diff --git a/src/BuiltInTools/dotnet-watch/UI/PhysicalConsole.cs b/src/BuiltInTools/Watch/UI/PhysicalConsole.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/PhysicalConsole.cs rename to src/BuiltInTools/Watch/UI/PhysicalConsole.cs diff --git a/src/BuiltInTools/dotnet-watch/UI/RestartPrompt.cs b/src/BuiltInTools/Watch/UI/RestartPrompt.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/UI/RestartPrompt.cs rename to src/BuiltInTools/Watch/UI/RestartPrompt.cs diff --git a/src/BuiltInTools/Watch/UI/ShutdownHandler.cs b/src/BuiltInTools/Watch/UI/ShutdownHandler.cs new file mode 100644 index 000000000000..70cc2355fe43 --- /dev/null +++ b/src/BuiltInTools/Watch/UI/ShutdownHandler.cs @@ -0,0 +1,44 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using Microsoft.Extensions.Logging; + +namespace Microsoft.DotNet.Watch; + +internal sealed class ShutdownHandler : IDisposable +{ + private readonly CancellationTokenSource _cancellationSource = new(); + public CancellationToken CancellationToken { get; } + + private volatile bool _disposed; + + public ShutdownHandler(IConsole console, ILogger logger) + { + CancellationToken = _cancellationSource.Token; + + console.KeyPressed += key => + { + if (!_disposed && key.Modifiers.HasFlag(ConsoleModifiers.Control) && key.Key == ConsoleKey.C) + { + // if we already canceled, we force immediate shutdown: + var forceShutdown = _cancellationSource.IsCancellationRequested; + + if (!forceShutdown) + { + logger.Log(MessageDescriptor.ShutdownRequested); + _cancellationSource.Cancel(); + } + else + { + Environment.Exit(0); + } + } + }; + } + + public void Dispose() + { + _disposed = true; + _cancellationSource.Dispose(); + } +} diff --git a/src/BuiltInTools/dotnet-watch/Utilities/CommandLineUtilities.cs b/src/BuiltInTools/Watch/Utilities/CommandLineUtilities.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Utilities/CommandLineUtilities.cs rename to src/BuiltInTools/Watch/Utilities/CommandLineUtilities.cs diff --git a/src/BuiltInTools/dotnet-watch/Utilities/Disposables.cs b/src/BuiltInTools/Watch/Utilities/Disposables.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Utilities/Disposables.cs rename to src/BuiltInTools/Watch/Utilities/Disposables.cs diff --git a/src/BuiltInTools/dotnet-watch/Utilities/PathUtilities.cs b/src/BuiltInTools/Watch/Utilities/PathUtilities.cs similarity index 93% rename from src/BuiltInTools/dotnet-watch/Utilities/PathUtilities.cs rename to src/BuiltInTools/Watch/Utilities/PathUtilities.cs index b3a1349ae8ca..e7f21ea13ac6 100644 --- a/src/BuiltInTools/dotnet-watch/Utilities/PathUtilities.cs +++ b/src/BuiltInTools/Watch/Utilities/PathUtilities.cs @@ -8,6 +8,9 @@ internal static class PathUtilities public static readonly IEqualityComparer OSSpecificPathComparer = Path.DirectorySeparatorChar == '\\' ? StringComparer.OrdinalIgnoreCase : StringComparer.Ordinal; public static readonly StringComparison OSSpecificPathComparison = Path.DirectorySeparatorChar == '\\' ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; + public static string ExecutableExtension + => RuntimeInformation.IsOSPlatform(OSPlatform.Windows) ? ".exe" : ""; + public static string EnsureTrailingSlash(string path) => (path is [.., var last] && last != Path.DirectorySeparatorChar) ? path + Path.DirectorySeparatorChar : path; diff --git a/src/BuiltInTools/dotnet-watch/Utilities/ProcessUtilities.cs b/src/BuiltInTools/Watch/Utilities/ProcessUtilities.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Utilities/ProcessUtilities.cs rename to src/BuiltInTools/Watch/Utilities/ProcessUtilities.cs diff --git a/src/BuiltInTools/dotnet-watch/Utilities/Versions.cs b/src/BuiltInTools/Watch/Utilities/Versions.cs similarity index 100% rename from src/BuiltInTools/dotnet-watch/Utilities/Versions.cs rename to src/BuiltInTools/Watch/Utilities/Versions.cs diff --git a/src/BuiltInTools/dotnet-watch.slnf b/src/BuiltInTools/dotnet-watch.slnf index a3cc85fc0d92..8e454226e0d0 100644 --- a/src/BuiltInTools/dotnet-watch.slnf +++ b/src/BuiltInTools/dotnet-watch.slnf @@ -20,6 +20,8 @@ "src\\BuiltInTools\\HotReloadClient\\Microsoft.DotNet.HotReload.Client.shproj", "src\\BuiltInTools\\Web.Middleware\\Microsoft.DotNet.HotReload.Web.Middleware.Package.csproj", "src\\BuiltInTools\\Web.Middleware\\Microsoft.DotNet.HotReload.Web.Middleware.shproj", + "src\\BuiltInTools\\Watch.Aspire\\Microsoft.DotNet.HotReload.Watch.Aspire.csproj", + "src\\BuiltInTools\\Watch\\Microsoft.DotNet.HotReload.Watch.csproj", "src\\BuiltInTools\\dotnet-watch\\dotnet-watch.csproj", "test\\Microsoft.AspNetCore.Watch.BrowserRefresh.Tests\\Microsoft.AspNetCore.Watch.BrowserRefresh.Tests.csproj", "test\\Microsoft.DotNet.HotReload.Client.Tests\\Microsoft.DotNet.HotReload.Client.Tests.csproj", @@ -27,6 +29,9 @@ "test\\Microsoft.NET.TestFramework\\Microsoft.NET.TestFramework.csproj", "test\\Microsoft.WebTools.AspireService.Tests\\Microsoft.WebTools.AspireService.Tests.csproj", "test\\dotnet-watch-test-browser\\dotnet-watch-test-browser.csproj", + "test\\Microsoft.DotNet.HotReload.Test.Utilities\\Microsoft.DotNet.HotReload.Test.Utilities.csproj", + "test\\Microsoft.DotNet.HotReload.Watch.Aspire.Tests\\Microsoft.DotNet.HotReload.Watch.Aspire.Tests.csproj", + "test\\Microsoft.Extensions.DotNetDeltaApplier.Tests\\Microsoft.Extensions.DotNetDeltaApplier.Tests.csproj", "test\\dotnet-watch.Tests\\dotnet-watch.Tests.csproj" ] } diff --git a/src/BuiltInTools/dotnet-watch/CommandLine/CommandLineOptions.cs b/src/BuiltInTools/dotnet-watch/CommandLine/CommandLineOptions.cs index 0679d27d6897..ba8e3317c62b 100644 --- a/src/BuiltInTools/dotnet-watch/CommandLine/CommandLineOptions.cs +++ b/src/BuiltInTools/dotnet-watch/CommandLine/CommandLineOptions.cs @@ -378,22 +378,4 @@ public ProjectOptions GetProjectOptions(string projectPath, string workingDirect BuildArguments = BuildArguments, TargetFramework = TargetFramework, }; - - // Parses name=value pairs passed to --property. Skips invalid input. - public static IEnumerable<(string key, string value)> ParseBuildProperties(IEnumerable arguments) - => from argument in arguments - let colon = argument.IndexOf(':') - where colon >= 0 && argument[0..colon] is "--property" or "-property" or "/property" or "/p" or "-p" or "--p" - let eq = argument.IndexOf('=', colon) - where eq >= 0 - let name = argument[(colon + 1)..eq].Trim() - let value = argument[(eq + 1)..] - where name is not [] - select (name, value); - - /// - /// Returns true if the command executes the code of the target project. - /// - public static bool IsCodeExecutionCommand(string commandName) - => commandName is "run" or "test"; } diff --git a/src/BuiltInTools/dotnet-watch/Program.cs b/src/BuiltInTools/dotnet-watch/Program.cs index f67a360a3a32..f4e531d02414 100644 --- a/src/BuiltInTools/dotnet-watch/Program.cs +++ b/src/BuiltInTools/dotnet-watch/Program.cs @@ -1,6 +1,7 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. +using System.Diagnostics; using System.Diagnostics.CodeAnalysis; using System.Globalization; using System.Runtime.Loader; @@ -40,7 +41,10 @@ public static async Task Main(string[] args) // Register listeners that load Roslyn-related assemblies from the `Roslyn/bincore` directory. RegisterAssemblyResolutionEvents(sdkRootDirectory); - var environmentOptions = EnvironmentOptions.FromEnvironment(); + var processPath = Environment.ProcessPath; + Debug.Assert(processPath != null); + + var environmentOptions = EnvironmentOptions.FromEnvironment(processPath); var program = TryCreate( args, @@ -67,7 +71,7 @@ public static async Task Main(string[] args) private static Program? TryCreate(IReadOnlyList args, IConsole console, EnvironmentOptions environmentOptions, bool verbose, out int errorCode) { var parsingLoggerFactory = new LoggerFactory(new ConsoleReporter(console, verbose, quiet: false, environmentOptions.SuppressEmojis)); - var options = CommandLineOptions.Parse(args, parsingLoggerFactory.CreateLogger(LogComponentName), console.Out, out errorCode); + var options = CommandLineOptions.Parse(args, parsingLoggerFactory.CreateLogger(DotNetWatchContext.DefaultLogComponentName), console.Out, out errorCode); if (options == null) { // an error reported or help printed: @@ -82,7 +86,7 @@ public static async Task Main(string[] args) // internal for testing internal static Program? TryCreate(CommandLineOptions options, IConsole console, EnvironmentOptions environmentOptions, LoggerFactory loggerFactory, IProcessOutputReporter processOutputReporter, out int errorCode) { - var logger = loggerFactory.CreateLogger(LogComponentName); + var logger = loggerFactory.CreateLogger(DotNetWatchContext.DefaultLogComponentName); var workingDirectory = environmentOptions.WorkingDirectory; logger.LogDebug("Working directory: '{Directory}'", workingDirectory); @@ -151,41 +155,21 @@ private static bool TryFindProject(string searchBase, CommandLineOptions options // internal for testing internal async Task RunAsync() { - var shutdownCancellationSourceDisposed = false; - var shutdownCancellationSource = new CancellationTokenSource(); - var shutdownCancellationToken = shutdownCancellationSource.Token; var isHotReloadEnabled = IsHotReloadEnabled(); var processRunner = new ProcessRunner(environmentOptions.GetProcessCleanupTimeout(isHotReloadEnabled)); - console.KeyPressed += key => - { - if (!shutdownCancellationSourceDisposed && key.Modifiers.HasFlag(ConsoleModifiers.Control) && key.Key == ConsoleKey.C) - { - // if we already canceled, we force immediate shutdown: - var forceShutdown = shutdownCancellationSource.IsCancellationRequested; - - if (!forceShutdown) - { - logger.Log(MessageDescriptor.ShutdownRequested); - shutdownCancellationSource.Cancel(); - } - else - { - Environment.Exit(0); - } - } - }; + using var shutdownHandler = new ShutdownHandler(console, logger); try { - if (shutdownCancellationToken.IsCancellationRequested) + if (shutdownHandler.CancellationToken.IsCancellationRequested) { return 1; } if (options.List) { - return await ListFilesAsync(processRunner, shutdownCancellationToken); + return await ListFilesAsync(processRunner, shutdownHandler.CancellationToken); } if (environmentOptions.IsPollingEnabled) @@ -198,16 +182,16 @@ internal async Task RunAsync() if (isHotReloadEnabled) { var watcher = new HotReloadDotNetWatcher(context, console, runtimeProcessLauncherFactory: null); - await watcher.WatchAsync(shutdownCancellationToken); + await watcher.WatchAsync(shutdownHandler.CancellationToken); } else { - await DotNetWatcher.WatchAsync(context, shutdownCancellationToken); + await DotNetWatcher.WatchAsync(context, shutdownHandler.CancellationToken); } return 0; } - catch (OperationCanceledException) when (shutdownCancellationToken.IsCancellationRequested) + catch (OperationCanceledException) when (shutdownHandler.CancellationToken.IsCancellationRequested) { // Ctrl+C forced an exit return 0; @@ -217,11 +201,6 @@ internal async Task RunAsync() logger.LogError("An unexpected error occurred: {Exception}", e.ToString()); return 1; } - finally - { - shutdownCancellationSourceDisposed = true; - shutdownCancellationSource.Dispose(); - } } // internal for testing diff --git a/src/BuiltInTools/dotnet-watch/UI/IConsole.cs b/src/BuiltInTools/dotnet-watch/UI/IConsole.cs deleted file mode 100644 index 0860a30eeae6..000000000000 --- a/src/BuiltInTools/dotnet-watch/UI/IConsole.cs +++ /dev/null @@ -1,19 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. - -namespace Microsoft.DotNet.Watch -{ - /// - /// This API supports infrastructure and is not intended to be used - /// directly from your code. This API may change or be removed in future releases. - /// - internal interface IConsole - { - event Action KeyPressed; - TextWriter Out { get; } - TextWriter Error { get; } - ConsoleColor ForegroundColor { get; set; } - void ResetColor(); - void Clear(); - } -} diff --git a/src/BuiltInTools/dotnet-watch/Watch/BuildEvaluator.cs b/src/BuiltInTools/dotnet-watch/Watch/BuildEvaluator.cs index ec3b10c8b235..756abbda6bc4 100644 --- a/src/BuiltInTools/dotnet-watch/Watch/BuildEvaluator.cs +++ b/src/BuiltInTools/dotnet-watch/Watch/BuildEvaluator.cs @@ -46,7 +46,7 @@ public IReadOnlyList GetProcessArguments(int iteration) { if (!_context.EnvironmentOptions.SuppressMSBuildIncrementalism && iteration > 0 && - CommandLineOptions.IsCodeExecutionCommand(_context.RootProjectOptions.Command)) + _context.RootProjectOptions.IsCodeExecutionCommand) { if (RequiresRevaluation) { diff --git a/src/BuiltInTools/dotnet-watch/Watch/MsBuildFileSetFactory.cs b/src/BuiltInTools/dotnet-watch/Watch/MsBuildFileSetFactory.cs index 50ce65d4e9a1..32f8f2a0d58d 100644 --- a/src/BuiltInTools/dotnet-watch/Watch/MsBuildFileSetFactory.cs +++ b/src/BuiltInTools/dotnet-watch/Watch/MsBuildFileSetFactory.cs @@ -31,7 +31,7 @@ internal class MSBuildFileSetFactory( private ILogger Logger => buildReporter.Logger; private readonly ProjectGraphFactory _buildGraphFactory = new( - globalOptions: CommandLineOptions.ParseBuildProperties(buildArguments).ToImmutableDictionary(keySelector: arg => arg.key, elementSelector: arg => arg.value)); + globalOptions: BuildUtilities.ParseBuildProperties(buildArguments).ToImmutableDictionary(keySelector: arg => arg.key, elementSelector: arg => arg.value)); internal sealed class EvaluationResult(IReadOnlyDictionary files, ProjectGraph? projectGraph) { diff --git a/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj b/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj index aab9d8b174dc..6ee14bf8ee71 100644 --- a/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj +++ b/src/BuiltInTools/dotnet-watch/dotnet-watch.csproj @@ -1,10 +1,4 @@  - - - - - - $(SdkTargetFramework) exe @@ -34,19 +28,9 @@ - - - - - - - - - - @@ -61,37 +45,11 @@ PreserveNewest - - all - Content - true - false - TargetFramework;TargetFrameworks - hotreload\net6.0\Microsoft.AspNetCore.Watch.BrowserRefresh.dll - PreserveNewest - - - - all - Content - true - false - TargetFramework=net10.0 - hotreload\net10.0\Microsoft.Extensions.DotNetDeltaApplier.dll - PreserveNewest - - - - all - Content - true - false - TargetFramework=net6.0 - hotreload\net6.0\Microsoft.Extensions.DotNetDeltaApplier.dll - PreserveNewest - + + + diff --git a/test/Common/Program.cs b/test/Common/Program.cs index 66044b224b5e..f2100b6811cf 100644 --- a/test/Common/Program.cs +++ b/test/Common/Program.cs @@ -1,9 +1,10 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using Microsoft.NET.TestFramework; using Microsoft.NET.TestFramework.Commands; +namespace Microsoft.NET.TestFramework; + #pragma warning disable SA1205 // Partial elements should declare access partial class Program #pragma warning restore SA1205 // Partial elements should declare access diff --git a/test/Microsoft.DotNet.HotReload.Client.Tests/Microsoft.DotNet.HotReload.Client.Tests.csproj b/test/Microsoft.DotNet.HotReload.Client.Tests/Microsoft.DotNet.HotReload.Client.Tests.csproj index b81c300e8c5c..19c3be5116f6 100644 --- a/test/Microsoft.DotNet.HotReload.Client.Tests/Microsoft.DotNet.HotReload.Client.Tests.csproj +++ b/test/Microsoft.DotNet.HotReload.Client.Tests/Microsoft.DotNet.HotReload.Client.Tests.csproj @@ -12,7 +12,7 @@ - + diff --git a/test/dotnet-watch.Tests/TestUtilities/AssertEx.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/AssertEx.cs similarity index 100% rename from test/dotnet-watch.Tests/TestUtilities/AssertEx.cs rename to test/Microsoft.DotNet.HotReload.Test.Utilities/AssertEx.cs diff --git a/test/dotnet-watch.Tests/TestUtilities/AwaitableProcess.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/AwaitableProcess.cs similarity index 91% rename from test/dotnet-watch.Tests/TestUtilities/AwaitableProcess.cs rename to test/Microsoft.DotNet.HotReload.Test.Utilities/AwaitableProcess.cs index fe40300cf7e4..d15b7ba6284c 100644 --- a/test/dotnet-watch.Tests/TestUtilities/AwaitableProcess.cs +++ b/test/Microsoft.DotNet.HotReload.Test.Utilities/AwaitableProcess.cs @@ -8,7 +8,7 @@ namespace Microsoft.DotNet.Watch.UnitTests { - internal class AwaitableProcess(DotnetCommand spec, ITestOutputHelper logger) : IDisposable + internal class AwaitableProcess(ITestOutputHelper logger) : IDisposable { // cancel just before we hit timeout used on CI (XUnitWorkItemTimeout value in sdk\test\UnitTests.proj) private static readonly TimeSpan s_timeout = Environment.GetEnvironmentVariable("HELIX_WORK_ITEM_TIMEOUT") is { } value @@ -16,7 +16,6 @@ internal class AwaitableProcess(DotnetCommand spec, ITestOutputHelper logger) : private readonly object _testOutputLock = new(); - private readonly DotnetCommand _spec = spec; private readonly List _lines = []; private readonly BufferBlock _source = new(); private Process _process; @@ -26,14 +25,22 @@ internal class AwaitableProcess(DotnetCommand spec, ITestOutputHelper logger) : public int Id => _process.Id; public Process Process => _process; - public void Start() + public void Start(ProcessStartInfo processStartInfo) { if (_process != null) { throw new InvalidOperationException("Already started"); } - var processStartInfo = _spec.GetProcessStartInfo(); + if (!processStartInfo.UseShellExecute && !RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + { + var flags = File.GetUnixFileMode(processStartInfo.FileName); + if (!flags.HasFlag(UnixFileMode.UserExecute)) + { + File.SetUnixFileMode(processStartInfo.FileName, flags | UnixFileMode.UserExecute); + } + } + processStartInfo.RedirectStandardOutput = true; processStartInfo.RedirectStandardError = true; processStartInfo.RedirectStandardInput = true; diff --git a/test/dotnet-watch.Tests/TestUtilities/DebugTestOutputLogger.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/DebugTestOutputLogger.cs similarity index 100% rename from test/dotnet-watch.Tests/TestUtilities/DebugTestOutputLogger.cs rename to test/Microsoft.DotNet.HotReload.Test.Utilities/DebugTestOutputLogger.cs diff --git a/test/Microsoft.DotNet.HotReload.Test.Utilities/Microsoft.DotNet.HotReload.Test.Utilities.csproj b/test/Microsoft.DotNet.HotReload.Test.Utilities/Microsoft.DotNet.HotReload.Test.Utilities.csproj new file mode 100644 index 000000000000..c27c0c1d9a25 --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Test.Utilities/Microsoft.DotNet.HotReload.Test.Utilities.csproj @@ -0,0 +1,19 @@ + + + + $(SdkTargetFramework) + Library + Microsoft.DotNet.Watch.UnitTests + MicrosoftAspNetCore + + + + + + + + + + + + diff --git a/test/Microsoft.DotNet.HotReload.Test.Utilities/Properties/AssemblyInfo.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/Properties/AssemblyInfo.cs new file mode 100644 index 000000000000..5737afe4811d --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Test.Utilities/Properties/AssemblyInfo.cs @@ -0,0 +1,9 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Runtime.CompilerServices; + +[assembly: InternalsVisibleTo("dotnet-watch.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Client.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.DotNet.HotReload.Watch.Aspire.Tests, PublicKey = 0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")] diff --git a/test/Microsoft.DotNet.HotReload.Test.Utilities/TestAssetExtensions.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/TestAssetExtensions.cs new file mode 100644 index 000000000000..bba89f12618b --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Test.Utilities/TestAssetExtensions.cs @@ -0,0 +1,12 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +namespace Microsoft.DotNet.Watch.UnitTests; + +internal static class TestAssetExtensions +{ + public static string GetWatchTestOutputPath(this TestAsset asset) + => Environment.GetEnvironmentVariable("HELIX_WORKITEM_UPLOAD_ROOT") is { } ciOutputRoot + ? Path.Combine(ciOutputRoot, ".hotreload", asset.Name) + : asset.Path + ".hotreload"; +} diff --git a/test/dotnet-watch.Tests/TestUtilities/TestLogger.cs b/test/Microsoft.DotNet.HotReload.Test.Utilities/TestLogger.cs similarity index 92% rename from test/dotnet-watch.Tests/TestUtilities/TestLogger.cs rename to test/Microsoft.DotNet.HotReload.Test.Utilities/TestLogger.cs index 5ae8e7dcd811..562d9e67bd0a 100644 --- a/test/dotnet-watch.Tests/TestUtilities/TestLogger.cs +++ b/test/Microsoft.DotNet.HotReload.Test.Utilities/TestLogger.cs @@ -11,7 +11,7 @@ internal class TestLogger(ITestOutputHelper? output = null) : ILogger public readonly Lock Guard = new(); private readonly List _messages = []; - public Func? IsEnabledImpl; + public Func IsEnabledImpl = _ => true; public void Log(LogLevel logLevel, EventId eventId, TState state, Exception? exception, Func formatter) { @@ -38,5 +38,5 @@ public ImmutableArray GetAndClearMessages() where TState : notnull => throw new NotImplementedException(); public bool IsEnabled(LogLevel logLevel) - => IsEnabledImpl?.Invoke(logLevel) ?? true; + => IsEnabledImpl(logLevel); } diff --git a/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchLauncherTests.cs b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchLauncherTests.cs new file mode 100644 index 000000000000..26e009bb1bae --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchLauncherTests.cs @@ -0,0 +1,37 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Diagnostics; + +namespace Microsoft.DotNet.Watch.UnitTests; + +public class DotNetWatchLauncherTests(ITestOutputHelper logger) +{ + private TestAssetsManager TestAssets { get; } = new(logger); + + [Fact] + public async Task AspireWatchLaunch() + { + var testAsset = TestAssets.CopyTestAsset("WatchAppWithProjectDeps") + .WithSource(); + + var path = Path.ChangeExtension(typeof(DotNetWatchLauncher).Assembly.Location, PathUtilities.ExecutableExtension).TrimEnd('.'); + var sdkRootDirectory = TestContext.Current.ToolsetUnderTest.SdkFolderUnderTest; + var projectDir = Path.Combine(testAsset.Path, "AppWithDeps"); + var projectPath = Path.Combine(projectDir, "App.WithDeps.csproj"); + + var startInfo = new ProcessStartInfo + { + FileName = path, + Arguments = $@"--sdk ""{sdkRootDirectory}"" --project ""{projectPath}"" --verbose", + UseShellExecute = false, + RedirectStandardInput = true, + WorkingDirectory = projectDir, + }; + + using var process = new AwaitableProcess(logger); + process.Start(startInfo); + + await process.GetOutputLineAsync(success: line => line.Contains("dotnet watch ⌚ Waiting for changes"), failure: _ => false); + } +} diff --git a/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchOptionsTests.cs b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchOptionsTests.cs new file mode 100644 index 000000000000..6f7d317fdc54 --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/DotNetWatchOptionsTests.cs @@ -0,0 +1,117 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +namespace Microsoft.DotNet.Watch.UnitTests; + +public class DotNetWatchOptionsTests +{ + [Fact] + public void TryParse_RequiredProjectOption() + { + // Project option is missing + var args = new[] { "--verbose", "a", "b" }; + Assert.False(DotNetWatchOptions.TryParse(args, out var options)); + Assert.Null(options); + } + + [Fact] + public void TryParse_RequiredSdkOption() + { + // Project option is missing + var args = new[] { "--project", "proj", "a", "b" }; + Assert.False(DotNetWatchOptions.TryParse(args, out var options)); + Assert.Null(options); + } + + [Fact] + public void TryParse_ProjectAndSdkPaths() + { + var args = new[] { "--sdk", "sdk", "--project", "myproject.csproj" }; + Assert.True(DotNetWatchOptions.TryParse(args, out var options)); + Assert.Equal("sdk", options.SdkDirectory); + Assert.Equal("myproject.csproj", options.ProjectPath); + Assert.Empty(options.ApplicationArguments); + } + + [Fact] + public void TryParse_ApplicationArguments() + { + var args = new[] { "--sdk", "sdk", "--project", "proj", "--verbose", "a", "b" }; + Assert.True(DotNetWatchOptions.TryParse(args, out var options)); + AssertEx.SequenceEqual(["a", "b"], options.ApplicationArguments); + } + + [Fact] + public void TryParse_VerboseOption() + { + // With verbose flag + var argsVerbose = new[] { "--sdk", "sdk", "--project", "proj", "--verbose" }; + Assert.True(DotNetWatchOptions.TryParse(argsVerbose, out var optionsVerbose)); + Assert.True(optionsVerbose.IsVerbose); + + // Without verbose flag + var argsNotVerbose = new[] { "--sdk", "sdk", "--project", "proj" }; + Assert.True(DotNetWatchOptions.TryParse(argsNotVerbose, out var optionsNotVerbose)); + Assert.False(optionsNotVerbose.IsVerbose); + } + + [Fact] + public void TryParse_QuietOption() + { + // With quiet flag + var argsQuiet = new[] { "--sdk", "sdk", "--project", "proj", "--quiet" }; + Assert.True(DotNetWatchOptions.TryParse(argsQuiet, out var optionsQuiet)); + Assert.True(optionsQuiet.IsQuiet); + + // Without quiet flag + var argsNotQuiet = new[] { "--sdk", "sdk", "--project", "proj" }; + Assert.True(DotNetWatchOptions.TryParse(argsNotQuiet, out var optionsNotQuiet)); + Assert.False(optionsNotQuiet.IsQuiet); + } + + [Fact] + public void TryParse_NoLaunchProfileOption() + { + // With no-launch-profile flag + var argsNoProfile = new[] { "--sdk", "sdk", "--project", "proj", "--no-launch-profile" }; + Assert.True(DotNetWatchOptions.TryParse(argsNoProfile, out var optionsNoProfile)); + Assert.True(optionsNoProfile.NoLaunchProfile); + + // Without no-launch-profile flag + var argsWithProfile = new[] { "--sdk", "sdk", "--project", "proj" }; + Assert.True(DotNetWatchOptions.TryParse(argsWithProfile, out var optionsWithProfile)); + Assert.False(optionsWithProfile.NoLaunchProfile); + } + + [Fact] + public void TryParse_ConflictingOptions() + { + // Cannot specify both --quiet and --verbose + var args = new[] { "--sdk", "sdk", "--project", "proj", "--quiet", "--verbose" }; + Assert.False(DotNetWatchOptions.TryParse(args, out var options)); + Assert.Null(options); + } + + [Fact] + public void TryParse_MultipleOptionValues() + { + // Project option should only accept one value + var args = new[] { "--sdk", "sdk", "--project", "proj1", "proj2" }; + Assert.True(DotNetWatchOptions.TryParse(args, out var options)); + Assert.Equal("proj1", options.ProjectPath); + AssertEx.SequenceEqual(["proj2"], options.ApplicationArguments); + } + + [Fact] + public void TryParse_AllOptionsSet() + { + var args = new[] { "--sdk", "sdk", "--project", "myapp.csproj", "--verbose", "--no-launch-profile", "arg1", "arg2", "arg3" }; + Assert.True(DotNetWatchOptions.TryParse(args, out var options)); + + Assert.Equal("myapp.csproj", options.ProjectPath); + Assert.True(options.IsVerbose); + Assert.False(options.IsQuiet); + Assert.True(options.NoLaunchProfile); + AssertEx.SequenceEqual(["arg1", "arg2", "arg3"], options.ApplicationArguments); + } +} diff --git a/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/Microsoft.DotNet.HotReload.Watch.Aspire.Tests.csproj b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/Microsoft.DotNet.HotReload.Watch.Aspire.Tests.csproj new file mode 100644 index 000000000000..a2e1cf8bf60a --- /dev/null +++ b/test/Microsoft.DotNet.HotReload.Watch.Aspire.Tests/Microsoft.DotNet.HotReload.Watch.Aspire.Tests.csproj @@ -0,0 +1,19 @@ + + + + $(SdkTargetFramework) + Exe + Microsoft.DotNet.Watch.Aspire.UnitTests + MicrosoftAspNetCore + + + + + + + + + + + + diff --git a/test/Microsoft.Extensions.DotNetDeltaApplier.Tests/Microsoft.Extensions.DotNetDeltaApplier.Tests.csproj b/test/Microsoft.Extensions.DotNetDeltaApplier.Tests/Microsoft.Extensions.DotNetDeltaApplier.Tests.csproj index 6ab22f97a92d..c86f821366d9 100644 --- a/test/Microsoft.Extensions.DotNetDeltaApplier.Tests/Microsoft.Extensions.DotNetDeltaApplier.Tests.csproj +++ b/test/Microsoft.Extensions.DotNetDeltaApplier.Tests/Microsoft.Extensions.DotNetDeltaApplier.Tests.csproj @@ -8,8 +8,8 @@ - - + + diff --git a/test/Microsoft.WebTools.AspireService.Tests/Microsoft.WebTools.AspireService.Tests.csproj b/test/Microsoft.WebTools.AspireService.Tests/Microsoft.WebTools.AspireService.Tests.csproj index 914af7b1e68d..3effab61b6ce 100644 --- a/test/Microsoft.WebTools.AspireService.Tests/Microsoft.WebTools.AspireService.Tests.csproj +++ b/test/Microsoft.WebTools.AspireService.Tests/Microsoft.WebTools.AspireService.Tests.csproj @@ -13,7 +13,7 @@ - + diff --git a/test/dotnet-watch.Tests/Build/BuildUtilitiesTests.cs b/test/dotnet-watch.Tests/Build/BuildUtilitiesTests.cs new file mode 100644 index 000000000000..03161ae09339 --- /dev/null +++ b/test/dotnet-watch.Tests/Build/BuildUtilitiesTests.cs @@ -0,0 +1,30 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +namespace Microsoft.DotNet.Watch.UnitTests.Build; + +public class BuildUtilitiesTests +{ + [Theory] + [InlineData("-p:P=V", "P", "V")] + [InlineData("-p:P==", "P", "=")] + [InlineData("-p:P=A=B", "P", "A=B")] + [InlineData("-p: P\t = V ", "P", " V ")] + [InlineData("-p:P=", "P", "")] + public void BuildProperties_Valid(string argValue, string name, string value) + { + var properties = BuildUtilities.ParseBuildProperties([argValue]); + AssertEx.SequenceEqual([(name, value)], properties); + } + + [Theory] + [InlineData("P")] + [InlineData("=P3")] + [InlineData("=")] + [InlineData("==")] + public void BuildProperties_Invalid(string argValue) + { + var properties = BuildUtilities.ParseBuildProperties([argValue]); + AssertEx.SequenceEqual([], properties); + } +} diff --git a/test/dotnet-watch.Tests/CommandLine/CommandLineOptionsTests.cs b/test/dotnet-watch.Tests/CommandLine/CommandLineOptionsTests.cs index d98140e48889..431736a83fe8 100644 --- a/test/dotnet-watch.Tests/CommandLine/CommandLineOptionsTests.cs +++ b/test/dotnet-watch.Tests/CommandLine/CommandLineOptionsTests.cs @@ -53,29 +53,6 @@ public void HelpArgs(string[] args) Assert.Contains("Usage:", output.ToString()); } - [Theory] - [InlineData("-p:P=V", "P", "V")] - [InlineData("-p:P==", "P", "=")] - [InlineData("-p:P=A=B", "P", "A=B")] - [InlineData("-p: P\t = V ", "P", " V ")] - [InlineData("-p:P=", "P", "")] - public void BuildProperties_Valid(string argValue, string name, string value) - { - var properties = CommandLineOptions.ParseBuildProperties([argValue]); - AssertEx.SequenceEqual([(name, value)], properties); - } - - [Theory] - [InlineData("P")] - [InlineData("=P3")] - [InlineData("=")] - [InlineData("==")] - public void BuildProperties_Invalid(string argValue) - { - var properties = CommandLineOptions.ParseBuildProperties([argValue]); - AssertEx.SequenceEqual([], properties); - } - [Fact] public void ImplicitCommand() { diff --git a/test/dotnet-watch.Tests/TestUtilities/TestOptions.cs b/test/dotnet-watch.Tests/TestUtilities/TestOptions.cs index 8b7ca9e70add..fd846476e25b 100644 --- a/test/dotnet-watch.Tests/TestUtilities/TestOptions.cs +++ b/test/dotnet-watch.Tests/TestUtilities/TestOptions.cs @@ -15,7 +15,7 @@ public static int GetTestPort() public static readonly ProjectOptions ProjectOptions = GetProjectOptions([]); public static EnvironmentOptions GetEnvironmentOptions(string workingDirectory = "", string muxerPath = "", TestAsset? asset = null) - => new(workingDirectory, muxerPath, TimeSpan.Zero, IsPollingEnabled: true, TestFlags: TestFlags.RunningAsTest, TestOutput: asset != null ? GetWatchTestOutputPath(asset) : ""); + => new(workingDirectory, muxerPath, TimeSpan.Zero, IsPollingEnabled: true, TestFlags: TestFlags.RunningAsTest, TestOutput: asset != null ? asset.GetWatchTestOutputPath() : ""); public static CommandLineOptions GetCommandLineOptions(string[] args) => CommandLineOptions.Parse(args, NullLogger.Instance, TextWriter.Null, out _) ?? throw new InvalidOperationException(); @@ -25,9 +25,4 @@ public static ProjectOptions GetProjectOptions(string[]? args = null) var options = GetCommandLineOptions(args ?? []); return options.GetProjectOptions(options.ProjectPath ?? "test.csproj", workingDirectory: ""); } - - public static string GetWatchTestOutputPath(this TestAsset asset) - => Environment.GetEnvironmentVariable("HELIX_WORKITEM_UPLOAD_ROOT") is { } ciOutputRoot - ? Path.Combine(ciOutputRoot, ".hotreload", asset.Name) - : asset.Path + ".hotreload"; } diff --git a/test/dotnet-watch.Tests/TestUtilities/WatchableApp.cs b/test/dotnet-watch.Tests/TestUtilities/WatchableApp.cs index 81bfd17aae20..fcdaad958607 100644 --- a/test/dotnet-watch.Tests/TestUtilities/WatchableApp.cs +++ b/test/dotnet-watch.Tests/TestUtilities/WatchableApp.cs @@ -185,8 +185,9 @@ public void Start(TestAsset asset, IEnumerable arguments, string relativ commandSpec.WithEnvironmentVariable(env.Key, env.Value); } - Process = new AwaitableProcess(commandSpec, Logger); - Process.Start(); + var processStartInfo = commandSpec.GetProcessStartInfo(); + Process = new AwaitableProcess(Logger); + Process.Start(processStartInfo); TestFlags = testFlags; } diff --git a/test/dotnet-watch.Tests/dotnet-watch.Tests.csproj b/test/dotnet-watch.Tests/dotnet-watch.Tests.csproj index 772d35b80517..9b1afe3702b4 100644 --- a/test/dotnet-watch.Tests/dotnet-watch.Tests.csproj +++ b/test/dotnet-watch.Tests/dotnet-watch.Tests.csproj @@ -17,11 +17,12 @@ + - + @@ -31,8 +32,10 @@ <_FileItem Include="$(_Files)" /> - + + + From cdcbd070b1df3ba6873a1129ce8f3bbe887fc0e6 Mon Sep 17 00:00:00 2001 From: Jan Jones Date: Thu, 13 Nov 2025 13:47:38 +0100 Subject: [PATCH 18/18] Remove more analyzer redirecting VSIX related stuff (#51692) --- Directory.Packages.props | 2 -- NuGet.config | 2 -- eng/Signing.props | 4 +--- eng/Versions.props | 1 - 4 files changed, 1 insertion(+), 8 deletions(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index 27339ff8be28..a2b0a46067b0 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -82,8 +82,6 @@ - - diff --git a/NuGet.config b/NuGet.config index ba324adba3b8..0c7505bf1ba0 100644 --- a/NuGet.config +++ b/NuGet.config @@ -29,8 +29,6 @@ - - diff --git a/eng/Signing.props b/eng/Signing.props index 872602d12f5c..0a8d0fdad4d7 100644 --- a/eng/Signing.props +++ b/eng/Signing.props @@ -81,10 +81,8 @@ - - - + diff --git a/eng/Versions.props b/eng/Versions.props index 6e9169c48801..96c38d63cecb 100644 --- a/eng/Versions.props +++ b/eng/Versions.props @@ -28,7 +28,6 @@ compiler API targeted by analyzer assemblies. This is mostly an issue on source-build as in that build mode analyzer assemblies always target the live compiler API. --> true - true true