diff --git a/build/SourceFetcher.cs b/build/SourceFetcher.cs index 47d37783..2b544063 100644 --- a/build/SourceFetcher.cs +++ b/build/SourceFetcher.cs @@ -21,6 +21,38 @@ public static void GetSources(this AbsolutePath fileSystem, AbsolutePath rootDir FetchGitHubZip(fileSystem, rootDirectory, owner, repositories, "external", true, true); } + internal static void LogInfo(string message) + { + lock (_lockConsoleObject) + { + Console.ForegroundColor = ConsoleColor.Green; + Console.Write("[INFO] "); + Console.ResetColor(); + Console.Write($"{message}"); + Console.WriteLine(); + } + } + + internal static void LogRepositoryInfo(string owner, string repository, string message) => + LogInfo($"{message} {owner}/{repository}..."); + + internal static void LogRepositoryError(string owner, string repository, string message) + { + LogError($"{message} {owner}/{repository}..."); + } + + internal static void LogError(string message) + { + lock (_lockConsoleObject) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.Write("[ERROR] "); + Console.ResetColor(); + Console.Write(message); + Console.WriteLine(); + } + } + private static void FetchGitHubZip(AbsolutePath fileSystem, AbsolutePath rootDirectory, string owner, string[] repositories, string outputFolder, bool fetchNuGet, bool useSrc) { var zipCache = fileSystem / "zip"; @@ -37,7 +69,7 @@ private static void FetchGitHubZip(AbsolutePath fileSystem, AbsolutePath rootDir 6, // We can also do this with WaitAndRetryForever... but chose WaitAndRetry this time. attempt => TimeSpan.FromSeconds(0.1 * Math.Pow(2, attempt))); // Back off! 2, 4, 8, 16 etc times 1/4-second - Task.WaitAll(repositories.Select(repository => Task.Run(async () => + Task.WaitAll([.. repositories.Select(repository => Task.Run(async () => { await semaphore.WaitAsync(); try @@ -107,7 +139,7 @@ await waitAndRetry.ExecuteAsync(async () => { semaphore.Release(); } - })).ToArray()); + }))]); } private static void FetchNuGet(string owner, string repository, AbsolutePath finalPath, bool useSrc) @@ -116,53 +148,40 @@ private static void FetchNuGet(string owner, string repository, AbsolutePath fin var directory = useSrc ? finalPath / $"{repository}-main" / "src" : finalPath; + RunDotNetOnSolution(owner, repository, directory, "restore"); + } + + private static void WorkflowRestore(string owner, string repository, AbsolutePath finalPath, bool useSrc) + { + lock (_lockWorkloadObject) + { + LogRepositoryInfo(owner, repository, "Restoring workload for "); + + var directory = useSrc ? finalPath / $"{repository}-main" / "src" : finalPath; + + RunDotNetOnSolution(owner, repository, directory, "workload restore"); + } + } + + private static void RunDotNetOnSolution(string owner, string repository, AbsolutePath directory, string command) + { // Find any .sln or .slnx file and run dotnet restore on it var solutionFile = Directory.EnumerateFiles(directory.ToString(), "*.sln*").FirstOrDefault(); - if (File.Exists(directory / $"{repository}.sln")) { - RunDotNet(directory, $"restore {repository}.sln"); + RunDotNet(directory, $"{command} {repository}.sln"); } else if (File.Exists(directory / $"{repository}.slnx")) { - RunDotNet(directory, $"restore {repository}.slnx"); + RunDotNet(directory, $"{command} {repository}.slnx"); } else if (solutionFile != null) { - RunDotNet(directory, $"restore {Path.GetFileName(solutionFile)}"); + RunDotNet(directory, $"{command} {Path.GetFileName(solutionFile)}"); } else { - LogRepositoryError(owner, repository, "No solution file found to restore packages."); - } - } - - private static void WorkflowRestore(string owner, string repository, AbsolutePath finalPath, bool useSrc) - { - lock (_lockWorkloadObject) - { - LogRepositoryInfo(owner, repository, "Restoring workload for "); - - var directory = useSrc ? finalPath / $"{repository}-main" / "src" : finalPath; - - // Find any .sln or .slnx file and run dotnet restore on it - var solutionFile = Directory.EnumerateFiles(directory.ToString(), "*.sln*").FirstOrDefault(); - if (File.Exists(directory / $"{repository}.sln")) - { - RunDotNet(directory, $"workload restore {repository}.sln"); - } - else if (File.Exists(directory / $"{repository}.slnx")) - { - RunDotNet(directory, $"workload restore {repository}.slnx"); - } - else if (solutionFile != null) - { - RunDotNet(directory, $"workload restore {Path.GetFileName(solutionFile)}"); - } - else - { - LogRepositoryError(owner, repository, "No solution file found to restore workloads."); - } + LogRepositoryError(owner, repository, $"No solution file found to {command}."); } } @@ -183,36 +202,4 @@ private static void RunDotNet(AbsolutePath finalPath, string parameters) process.WaitForExit(); process.Dispose(); } - - internal static void LogInfo(string message) - { - lock (_lockConsoleObject) - { - Console.ForegroundColor = ConsoleColor.Green; - Console.Write("[INFO] "); - Console.ResetColor(); - Console.Write($"{message}"); - Console.WriteLine(); - } - } - - internal static void LogRepositoryInfo(string owner, string repository, string message) => - LogInfo($"{message} {owner}/{repository}..."); - - internal static void LogRepositoryError(string owner, string repository, string message) - { - LogError($"{message} {owner}/{repository}..."); - } - - internal static void LogError(string message) - { - lock (_lockConsoleObject) - { - Console.ForegroundColor = ConsoleColor.Red; - Console.Write("[ERROR] "); - Console.ResetColor(); - Console.Write(message); - Console.WriteLine(); - } - } } diff --git a/reactiveui/api/index.md b/reactiveui/api/index.md index cfa91820..b9040ad8 100644 --- a/reactiveui/api/index.md +++ b/reactiveui/api/index.md @@ -2,11 +2,40 @@ Browse the latest API documentation generated from the current ReactiveUI source code. This section provides reference material for all major ReactiveUI packages and related projects. -- [ReactiveUI API](api/ReactiveUI.html) -- [DynamicData API](api/DynamicData.html) -- [Splat API](api/Splat.html) -- [Akavache API](api/Akavache.html) -- [Fusillade API](api/Fusillade.html) -- [Punchclock API](Punchclock.html) +- [Akavache API](akavache.html) +- [DynamicData API](dynamicdata.html) +- [ReactiveUI API](reactiveui.html) +- [ReactiveUI.AndroidX API](reactiveui.androidx.html) +- [ReactiveUI.Blazor API](reactiveui.blazor.html) +- [ReactiveUI.Blend](reactiveui.blend.html) +- [ReactiveUI.Builder](reactiveui.builder.html) +- [ReactiveUI.Drawing API](reactiveui.drawing.html) +- [ReactiveUI.Extensions API](reactiveui.extensions.html) +- [ReactiveUI.Maui API](reactiveui.maui.html) +- [ReactiveUI.Maui.Plugins.Popup API](reactiveui.maui.plugins.popup.html) +- [ReactiveUI.Testing API](reactiveui.testing.html) +- [ReactiveUI.Validation API](reactiveui.validation.helpers.html) +- [ReactiveUI.WinUI API](reactiveui.winui.html) +- [ReactiveUI.WinForms API](reactiveui.winforms.html) +- [ReactiveUI.WPF API](reactiveui.wpf.html) +- [Splat API](splat.html) +- [Splat.ApplicationInsights API](splat.applicationinsights.html) +- [Splat.ApplicationPerformanceMonitoring API](splat.applicationperformancemonitoring.html) +- [Splat.AutoFac API](splat.autofac.html) +- [Splat.Builder API](splat.builder.html) +- [Splat.DryIoc API](splat.dryioc.html) +- [Splat.Exceptionless API](splat.exceptionless.html) +- [Splat.Log4Net API](splat.log4net.html) +- [Splat.Microsoft.Extensions.DependencyInjection API](splat.microsoft.extensions.dependencyinjection.html) +- [Splat.Microsoft.Extensions.Logging API](splat.microsoft.extensions.logging.html) +- [Splat.ModeDetection API](splat.modedetection.html) +- [Splat.NLog API](splat.nlog.html) +- [Splat.Ninject API](splat.ninject.html) +- [Splat.Prism API](splat.prism.html) +- [Splat.Prism.Forms API](splat.prism.forms.html) +- [Splat.Serilog API](splat.serilog.html) +- [Splat.SimpleInjector API](splat.simpleinjector.html) +- [Fusillade API](fusillade.html) +- [Punchclock API](punchclock.html) > The API documentation is generated from the latest source and reflects .NET 8 compatibility and current best practices. diff --git a/reactiveui/docs/guidelines/framework/command-names.md b/reactiveui/docs/guidelines/framework/command-names.md index 1d1875f7..6855b99e 100644 --- a/reactiveui/docs/guidelines/framework/command-names.md +++ b/reactiveui/docs/guidelines/framework/command-names.md @@ -86,9 +86,9 @@ public ReactiveCommand Save { get; } // Missing 'Command' suffix public ReactiveCommand PerformSave { get; } // Unclear naming ``` -### Implementation Method Names +### Using Legacy Implementation Method Names -When implementation is too complex for inline code, suffix the method with `Impl`: +When implementation is suffixed the method with `Impl` as per legacy conventions: ```csharp public partial class MyViewModel : ReactiveObject @@ -105,7 +105,7 @@ public partial class MyViewModel : ReactiveObject await DeleteImpl(); } - // Implementation methods + // Legacy Implementation methods private async Task SaveImpl() { /* ... */ } private async Task DeleteImpl() { /* ... */ } } @@ -125,15 +125,9 @@ public partial class MainViewModel : ReactiveObject [ReactiveCommand] private async Task Search() { - var results = await SearchImpl(SearchText); + var results = await _searchService.SearchAsync(searchText); Results = results; } - - private async Task> SearchImpl(string searchText) - { - // Actual search implementation - return await _searchService.SearchAsync(searchText); - } } ``` @@ -145,11 +139,6 @@ public partial class ItemViewModel : ReactiveObject // Generates: public ReactiveCommand DeleteItemCommand { get; } [ReactiveCommand] private async Task DeleteItem(Item item) - { - await DeleteItemImpl(item); - } - - private async Task DeleteItemImpl(Item item) { await _repository.DeleteAsync(item); } @@ -174,11 +163,6 @@ public partial class EditViewModel : ReactiveObject // Generates: public ReactiveCommand SaveCommand { get; } [ReactiveCommand(CanExecute = nameof(_canSave))] private async Task Save() - { - await SaveImpl(); - } - - private async Task SaveImpl() { await _dataService.SaveAsync(Data); } diff --git a/reactiveui/docs/guidelines/framework/commands.md b/reactiveui/docs/guidelines/framework/commands.md index 58d41655..99af341a 100644 --- a/reactiveui/docs/guidelines/framework/commands.md +++ b/reactiveui/docs/guidelines/framework/commands.md @@ -6,7 +6,7 @@ Prefer binding user interactions to commands rather than methods. ```csharp // In the view -this.BindCommand(ViewModel, vm => vm.Delete, v => v.deleteButton); +this.BindCommand(ViewModel, vm => vm.DeleteCommand, v => v.deleteButton); public class RepositoryViewModel : ReactiveObject { @@ -16,7 +16,7 @@ public class RepositoryViewModel : ReactiveObject Delete.ThrownExceptions.Subscribe(ex => /*...*/); } - public ReactiveAsyncCommand Delete { get; private set; } + public ReactiveAsyncCommand DeleteCommand { get; private set; } public IObservable DeleteImpl() {...} }