diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs index 8421eb656b..ee0b6a90da 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs @@ -111,7 +111,7 @@ public class NewCommand : ProjectCreationCommandBase, IConsoleCommand, ITransien var skipBundling = commandLineArgs.Options.ContainsKey(Options.SkipBundling.Long) || commandLineArgs.Options.ContainsKey(Options.SkipBundling.Short); if (!skipBundling) { - await RunBundleForBlazorWasmTemplateAsync(projectArgs); + await RunBundleForBlazorWasmOrMauiBlazorTemplateAsync(projectArgs); } await ConfigurePwaSupportForAngular(projectArgs); diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs index 2d5c9856cf..e0cbfe7d07 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs @@ -118,7 +118,7 @@ public abstract class ProjectCreationCommandBase Logger.LogInformation("DBMS: " + databaseManagementSystem); } - var uiFramework = GetUiFramework(commandLineArgs); + var uiFramework = GetUiFramework(commandLineArgs, template); if (uiFramework != UiFramework.NotSpecified) { Logger.LogInformation("UI Framework: " + uiFramework); @@ -413,22 +413,24 @@ public abstract class ProjectCreationCommandBase } } - protected async Task RunBundleForBlazorWasmTemplateAsync(ProjectBuildArgs projectArgs) + protected async Task RunBundleForBlazorWasmOrMauiBlazorTemplateAsync(ProjectBuildArgs projectArgs) { - if (AppTemplateBase.IsAppTemplate(projectArgs.TemplateName) && projectArgs.UiFramework == UiFramework.Blazor) + if (AppTemplateBase.IsAppTemplate(projectArgs.TemplateName) && projectArgs.UiFramework is UiFramework.Blazor or UiFramework.MauiBlazor) { - Logger.LogInformation("Generating bundles for Blazor Wasm..."); + var isWebassembly = projectArgs.UiFramework == UiFramework.Blazor; + var message = isWebassembly ? "Generating bundles for Blazor Wasm" : "Generating bundles for MAUI Blazor"; + Logger.LogInformation($"{message}..."); await EventBus.PublishAsync(new ProjectCreationProgressEvent { - Message = "Generating bundles for Blazor Wasm" + Message = message }, false); var directory = Path.GetDirectoryName( - Directory.GetFiles(projectArgs.OutputFolder, "*.Blazor.csproj", SearchOption.AllDirectories).First() + Directory.GetFiles(projectArgs.OutputFolder, isWebassembly? "*.Blazor.csproj" :"*.MauiBlazor.csproj", SearchOption.AllDirectories).First() ); - await _bundlingService.BundleAsync(directory, true); + await _bundlingService.BundleAsync(directory, true, projectType: isWebassembly ? BundlingConsts.WebAssembly : BundlingConsts.MauiBlazor); } } @@ -531,7 +533,7 @@ public abstract class ProjectCreationCommandBase } } - protected virtual UiFramework GetUiFramework(CommandLineArgs commandLineArgs) + protected virtual UiFramework GetUiFramework(CommandLineArgs commandLineArgs, string template = "app") { if (commandLineArgs.Options.ContainsKey("no-ui")) { @@ -554,6 +556,8 @@ public abstract class ProjectCreationCommandBase return UiFramework.Blazor; case "blazor-server": return UiFramework.BlazorServer; + case "maui-blazor" when template == AppProTemplate.TemplateName: + return UiFramework.MauiBlazor; default: throw new CliUsageException(ExceptionMessageHelper.GetInvalidOptionExceptionMessage("UI Framework")); } diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Building/UiFramework.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Building/UiFramework.cs index b1ffe8cb11..5b1ebb56f4 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Building/UiFramework.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Building/UiFramework.cs @@ -7,5 +7,6 @@ public enum UiFramework Mvc = 2, Angular = 3, Blazor = 4, - BlazorServer = 5 + BlazorServer = 5, + MauiBlazor = 6 } diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/AppTemplateBase.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/AppTemplateBase.cs index 2ffa12bca7..b3bdf2d7e9 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/AppTemplateBase.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/AppTemplateBase.cs @@ -132,7 +132,11 @@ public abstract class AppTemplateBase : TemplateInfo case UiFramework.BlazorServer: ConfigureWithBlazorServerUi(context, steps); break; - + + case UiFramework.MauiBlazor: + ConfigureWithMauiBlazorUi(context, steps); + break; + case UiFramework.Mvc: case UiFramework.NotSpecified: ConfigureWithMvcUi(context, steps); @@ -510,6 +514,37 @@ public abstract class AppTemplateBase : TemplateInfo } } + protected void ConfigureWithMauiBlazorUi(ProjectBuildContext context, List steps) + { + context.Symbols.Add("ui:maui-blazor"); + + steps.Add(new MauiBlazorChangeApplicationIdGuidStep()); + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.Web")); + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.Web.Host")); + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.Web.Tests", projectFolderPath: "/aspnet-core/test/MyCompanyName.MyProjectName.Web.Tests")); + + if (context.BuildArgs.ExtraProperties.ContainsKey("separate-identity-server") || + context.BuildArgs.ExtraProperties.ContainsKey("separate-auth-server")) + { + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.HttpApi.HostWithIds")); + steps.Add(new MauiBlazorPortChangeForSeparatedAuthServersStep()); + steps.Add(new AppTemplateChangeDbMigratorPortSettingsStep("44300")); + + if (context.BuildArgs.MobileApp == MobileApp.ReactNative) + { + steps.Add(new ReactEnvironmentFilePortChangeForSeparatedAuthServersStep()); + } + } + else + { + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.HttpApi.Host")); + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.IdentityServer")); + steps.Add(new RemoveProjectFromSolutionStep("MyCompanyName.MyProjectName.AuthServer")); + steps.Add(new TemplateProjectRenameStep("MyCompanyName.MyProjectName.HttpApi.HostWithIds", "MyCompanyName.MyProjectName.HttpApi.Host")); + steps.Add(new AppTemplateChangeConsoleTestClientPortSettingsStep("44305")); + } + } + protected void RemoveUnnecessaryPorts(ProjectBuildContext context, List steps) { steps.Add(new RemoveUnnecessaryPortsStep()); @@ -599,7 +634,8 @@ public abstract class AppTemplateBase : TemplateInfo { if ((context.BuildArgs.UiFramework == UiFramework.Mvc || context.BuildArgs.UiFramework == UiFramework.Blazor - || context.BuildArgs.UiFramework == UiFramework.BlazorServer) && + || context.BuildArgs.UiFramework == UiFramework.BlazorServer + || context.BuildArgs.UiFramework == UiFramework.MauiBlazor) && context.BuildArgs.MobileApp == MobileApp.None) { steps.Add(new MoveFolderStep("/aspnet-core/", "/")); diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorChangeApplicationIdGuidStep.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorChangeApplicationIdGuidStep.cs new file mode 100644 index 0000000000..953447cfa5 --- /dev/null +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorChangeApplicationIdGuidStep.cs @@ -0,0 +1,34 @@ +using System; +using System.Linq; +using System.Xml; +using Volo.Abp.Cli.ProjectBuilding.Building; +using Volo.Abp.Cli.Utils; + +namespace Volo.Abp.Cli.ProjectBuilding.Templates.App; + +public class MauiBlazorChangeApplicationIdGuidStep: ProjectBuildPipelineStep +{ + public override void Execute(ProjectBuildContext context) + { + var projectFile = context.Files.FirstOrDefault(f => f.Name.EndsWith("MyCompanyName.MyProjectName.MauiBlazor.csproj")); + + if (projectFile == null) + { + return; + } + + using (var stream = StreamHelper.GenerateStreamFromString(projectFile.Content)) + { + var doc = new XmlDocument { PreserveWhitespace = true }; + doc.Load(stream); + + var node = doc.SelectSingleNode("/Project/PropertyGroup/ApplicationIdGuid"); + if (node != null) + { + node.InnerText = Guid.NewGuid().ToString(); + } + + projectFile.SetContent(doc.OuterXml); + } + } +} \ No newline at end of file diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorPortChangeForSeparatedAuthServersStep.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorPortChangeForSeparatedAuthServersStep.cs new file mode 100644 index 0000000000..92b59de7f3 --- /dev/null +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/App/MauiBlazorPortChangeForSeparatedAuthServersStep.cs @@ -0,0 +1,50 @@ +using System; +using System.Linq; +using Volo.Abp.Cli.ProjectBuilding.Building; + +namespace Volo.Abp.Cli.ProjectBuilding.Templates.App; + +public class MauiBlazorPortChangeForSeparatedAuthServersStep: ProjectBuildPipelineStep +{ + public override void Execute(ProjectBuildContext context) + { + + var appsettingsFile = context.Files.FirstOrDefault(x => + !x.IsDirectory && + x.Name.EndsWith("aspnet-core/src/MyCompanyName.MyProjectName.MauiBlazor/appsettings.json", + StringComparison.InvariantCultureIgnoreCase) + ); + + if(appsettingsFile == null) + { + return; + } + + appsettingsFile.NormalizeLineEndings(); + var lines = appsettingsFile.GetLines(); + + for (var i = 1; i < lines.Length; i++) + { + var line = lines[i]; + + var previousLine = lines[i-1]; + + if (line.Contains("Authority") && line.Contains("localhost")) + { + line = line.Replace("44305", "44301"); + } + else if (previousLine.Contains("AbpAccountPublic") && line.Contains("BaseUrl") && line.Contains("localhost")) + { + line = line.Replace("44305", "44301"); + } + else if (previousLine.Contains("Default") && line.Contains("BaseUrl") && line.Contains("localhost")) + { + line = line.Replace("44305", "44300"); + } + + lines[i] = line; + } + + appsettingsFile.SetLines(lines); + } +} \ No newline at end of file diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/Maui/MauiChangePortStep.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/Maui/MauiChangePortStep.cs index 2b45d64b19..41b9393573 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/Maui/MauiChangePortStep.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/Templates/Maui/MauiChangePortStep.cs @@ -53,6 +53,7 @@ public class MauiChangePortStep : ProjectBuildPipelineStep { case UiFramework.Angular: case UiFramework.Blazor: + case UiFramework.MauiBlazor: authServerPort = "44305"; apiHostPort = "44305"; break;