From d5ca8ddf1e2409b571ce88962264c206dd5af013 Mon Sep 17 00:00:00 2001 From: chenchun Date: Thu, 7 Nov 2024 17:35:22 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=AE=8C=E6=88=90=E6=A8=A1=E6=9D=BF?= =?UTF-8?q?=E4=BB=8Egitee=E4=B8=8A=E8=8E=B7=E5=8F=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 + .../Dtos/TemplateGenCreateInputDto.cs | 4 + .../ITemplateGenService.cs | 2 +- .../TemplateGenService.cs | 31 ++++--- .../Dtos/TemplateGenCreateDto.cs | 16 ++-- .../Options/ToolOptions.cs | 11 --- .../Yi.Abp.Tool.Domain.Shared.csproj | 3 + .../tool/Yi.Abp.Tool.Domain/GiteeManager.cs | 85 +++++++++++++++++++ .../Yi.Abp.Tool.Domain/TemplateGenManager.cs | 37 ++++++-- .../Yi.Abp.Tool.Web/YiAbpToolWebModule.cs | 14 ++- .../appsettings.Development.json | 7 +- .../tool/Yi.Abp.Tool.Web/appsettings.json | 3 +- .../tool/Yi.Abp.Tool/Commands/NewCommand.cs | 32 ++++++- Yi.Abp.Net8/tool/Yi.Abp.Tool/Program.cs | 4 +- .../tool/Yi.Abp.Tool/YiAbpToolModule.cs | 3 +- 15 files changed, 192 insertions(+), 61 deletions(-) create mode 100644 Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/GiteeManager.cs diff --git a/.gitignore b/.gitignore index 400cf6c1..89d8631b 100644 --- a/.gitignore +++ b/.gitignore @@ -269,6 +269,7 @@ dist /Yi.Abp.Net8/src/Yi.Abp.Web/appsettings.Production.json /Yi.Abp.Net8/test/Yi.Abp.Test/appsettings.Development.json /Yi.Abp.Net8/test/Yi.Abp.Test/appsettings.Production.json +/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.Development.json database_backup /Yi.Abp.Net8/src/Yi.Abp.Web/appsettings.Staging.json /Yi.Abp.Net8/src/Yi.Abp.Web/logs/ diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/Dtos/TemplateGenCreateInputDto.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/Dtos/TemplateGenCreateInputDto.cs index c65e1101..acb23d94 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/Dtos/TemplateGenCreateInputDto.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/Dtos/TemplateGenCreateInputDto.cs @@ -14,6 +14,10 @@ namespace Yi.Abp.Tool.Application.Contracts.Dtos /// public string Name { get; set; } + /// + /// 模块类型 + /// + public string ModuleSoure { get; set; } /// /// 数据库提供者 diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/ITemplateGenService.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/ITemplateGenService.cs index 09658494..3bd39e88 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/ITemplateGenService.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application.Contracts/ITemplateGenService.cs @@ -7,6 +7,6 @@ namespace Yi.Abp.Tool.Application.Contracts public interface ITemplateGenService: IApplicationService { Task CreateModuleAsync(TemplateGenCreateInputDto moduleCreateInputDto); - Task CreateProjectAsync(TemplateGenCreateInputDto moduleCreateInputDto); + Task> GetAllTemplatesAsync(); } } diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application/TemplateGenService.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application/TemplateGenService.cs index 7cd03b35..e80291f8 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application/TemplateGenService.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Application/TemplateGenService.cs @@ -16,10 +16,14 @@ using Yi.Framework.Core.Helper; namespace Yi.Abp.Tool.Application { - public class TemplateGenService : ApplicationService,ITemplateGenService + public class TemplateGenService : ApplicationService, ITemplateGenService { private readonly TemplateGenManager _templateGenManager; - public TemplateGenService(TemplateGenManager templateGenManager) { _templateGenManager = templateGenManager; } + + public TemplateGenService(TemplateGenManager templateGenManager) + { + _templateGenManager = templateGenManager; + } /// /// 下载模块文件 @@ -29,8 +33,10 @@ namespace Yi.Abp.Tool.Application { moduleCreateInputDto.SetNameReplace(); + //模块类型,就是分支小写 var input = moduleCreateInputDto.Adapt(); - input.SetTemplateFilePath(_templateGenManager._toolOptions.ModuleTemplateFilePath); + input.SetTemplateGiteeRef(moduleCreateInputDto.ModuleSoure); + var filePath = await _templateGenManager.CreateTemplateAsync(input); ////考虑从路径中获取 @@ -39,22 +45,15 @@ namespace Yi.Abp.Tool.Application return await File.ReadAllBytesAsync(filePath); } + /// - /// 下载模块文件 + /// 获取全部模板列表 /// /// - public async Task CreateProjectAsync(TemplateGenCreateInputDto moduleCreateInputDto) + [HttpGet("template-gen/template")] + public async Task> GetAllTemplatesAsync() { - moduleCreateInputDto.SetNameReplace(); - - var input = moduleCreateInputDto.Adapt(); - input.SetTemplateFilePath(_templateGenManager._toolOptions.ProjectTemplateFilePath); - var filePath = await _templateGenManager.CreateTemplateAsync(input); - - //考虑从路径中获取 - // var fileContentType = MimeHelper.GetMimeMapping(Path.GetFileName(filePath)); - //设置附件下载,下载名称 - return await File.ReadAllBytesAsync(filePath); + return await _templateGenManager.GetAllTemplatesAsync(); } } -} +} \ No newline at end of file diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Dtos/TemplateGenCreateDto.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Dtos/TemplateGenCreateDto.cs index 9259ae84..a52c7b07 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Dtos/TemplateGenCreateDto.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Dtos/TemplateGenCreateDto.cs @@ -9,21 +9,19 @@ namespace Yi.Abp.Tool.Domain.Shared.Dtos { public class TemplateGenCreateDto { - public void SetTemplateFilePath(string templateFilePath) + public void SetTemplateGiteeRef(string moduleType) { - this.TemplateFilePath = templateFilePath; + this.GiteeRef = moduleType.ToLower(); } - - - /// - /// 模板文件路径 - /// - public string TemplateFilePath { get; set; } + /// /// 模块名称 /// public string Name { get; set; } - + /// + /// 模块所属gitee分支 + /// + public string GiteeRef { get; set; } /// /// 数据库提供者 diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Options/ToolOptions.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Options/ToolOptions.cs index a2084956..02aa95e1 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Options/ToolOptions.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Options/ToolOptions.cs @@ -8,17 +8,6 @@ namespace Yi.Abp.Tool.Domain.Shared.Options { public class ToolOptions { - /// - /// 模块模板zip文件路径 - /// - public string ModuleTemplateFilePath { get; set; } - - /// - /// 项目模板zip文件路径 - /// - public string ProjectTemplateFilePath { get; set; } - - /// /// 临时文件目录 /// diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Yi.Abp.Tool.Domain.Shared.csproj b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Yi.Abp.Tool.Domain.Shared.csproj index eaf50bd2..15a3b560 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Yi.Abp.Tool.Domain.Shared.csproj +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain.Shared/Yi.Abp.Tool.Domain.Shared.csproj @@ -9,5 +9,8 @@ + + + diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/GiteeManager.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/GiteeManager.cs new file mode 100644 index 00000000..4deb9bef --- /dev/null +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/GiteeManager.cs @@ -0,0 +1,85 @@ +using System.Net; +using Microsoft.Extensions.Configuration; +using Newtonsoft.Json.Linq; +using Volo.Abp.DependencyInjection; + +namespace Yi.Abp.Tool.Domain; + +public class GiteeManager : ITransientDependency +{ + private readonly string _accessToken; + private readonly IHttpClientFactory _httpClientFactory; + private const string GiteeHost = "https://gitee.com/api/v5"; + private const string Owner = "ccnetcore"; + private const string Repo = "yi-template"; + + public GiteeManager(IConfiguration configuration, IHttpClientFactory httpClientFactory) + { + _httpClientFactory = httpClientFactory; + _accessToken = configuration.GetValue("GiteeAccession"); + } + + /// + /// 是否存在当前分支 + /// + /// + public async Task IsExsitBranchAsync(string branch) + { + using var client = _httpClientFactory.CreateClient(); + var response = + await client.GetAsync( + $"{GiteeHost}/repos/{Owner}/{Repo}/branches/{branch}?access_token={_accessToken}"); + if (response.StatusCode == HttpStatusCode.NotFound) + { + return false; + } + + return true; + } + + /// + /// 获取所有分支 + /// + /// + public async Task> GetAllBranchAsync() + { + using var client = _httpClientFactory.CreateClient(); + var response = + await client.GetAsync( + $"{GiteeHost}/repos/{Owner}/{Repo}/branches?access_token={_accessToken}&sort=name&direction=asc&page=1&per_page=100"); + response.EnsureSuccessStatusCode(); + var result= await response.Content.ReadAsStringAsync(); + JArray jsonArray= JArray.Parse(result); + // 创建一个列表来存储名字 + List names = new List(); + + // 遍历每个对象,获取 name 字段 + foreach (JObject obj in jsonArray) + { + // 获取 name 字段的值 + string name = obj["name"]?.ToString(); + if (name != null) + { + names.Add(name); + } + } + return names; + } + + + /// + /// 下载仓库分支代码 + /// + /// + /// + public async Task DownLoadFileAsync(string branch) + { + using var client = _httpClientFactory.CreateClient(); + var response = + await client.GetAsync( + $"{GiteeHost}/repos/{Owner}/{Repo}/zipball?access_token={_accessToken}&ref={branch}"); + response.EnsureSuccessStatusCode(); + return await response.Content.ReadAsStreamAsync(); + + } +} \ No newline at end of file diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/TemplateGenManager.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/TemplateGenManager.cs index b9edbe74..186d4b59 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/TemplateGenManager.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Domain/TemplateGenManager.cs @@ -13,13 +13,19 @@ namespace Yi.Abp.Tool.Domain { public class TemplateGenManager : ITransientDependency { - public readonly ToolOptions _toolOptions; - public TemplateGenManager(IOptionsMonitor toolOptions) { _toolOptions = toolOptions.CurrentValue; } + private readonly ToolOptions _toolOptions; + private readonly GiteeManager _giteeManager; + public TemplateGenManager(IOptionsMonitor toolOptions, GiteeManager giteeManager) + { + _giteeManager = giteeManager; + _toolOptions = toolOptions.CurrentValue; + } public async Task CreateTemplateAsync(TemplateGenCreateDto input) { - if (string.IsNullOrEmpty(input.TemplateFilePath)) + //这里判断gitee上是否有这个分支 + if (await _giteeManager.IsExsitBranchAsync(input.GiteeRef)) { - throw new UserFriendlyException($"模板路径无法找到,请检查,[{input.TemplateFilePath}]路径"); + throw new UserFriendlyException($"Gitee分支未找到{input.GiteeRef},请检查,[{input.GiteeRef}]分支是否存在"); } if (string.IsNullOrEmpty(_toolOptions.TempDirPath)) { @@ -33,8 +39,15 @@ namespace Yi.Abp.Tool.Domain Directory.CreateDirectory(tempFileDirPath); } - //文件解压覆盖 - ZipFile.ExtractToDirectory(input.TemplateFilePath, tempFileDirPath, true); + //下载的模板存放文件路径 + var downloadFilePath = Path.Combine(_toolOptions.TempDirPath,"download" ,$"{id}.zip"); + var gitSteam= await _giteeManager.DownLoadFileAsync(input.GiteeRef); + using (FileStream fileStream = new FileStream(downloadFilePath, FileMode.Create, FileAccess.Write)) + { + await gitSteam.CopyToAsync(fileStream); + } + //文件解压覆盖,将刚刚下载的模板,解压即可 + ZipFile.ExtractToDirectory(downloadFilePath, tempFileDirPath, true); await ReplaceContentAsync(tempFileDirPath, input.ReplaceStrData); var tempFilePath = Path.Combine(_toolOptions.TempDirPath, $"{id}.zip"); @@ -45,13 +58,22 @@ namespace Yi.Abp.Tool.Domain return tempFilePath; } + + /// + /// 获取全部模板列表 + /// + /// + public async Task> GetAllTemplatesAsync() + { + return await _giteeManager.GetAllBranchAsync(); + } + /// /// 替换内容,key为要替换的内容,value为替换成的内容 /// /// private async Task ReplaceContentAsync(string rootDirectory, Dictionary dic) { - foreach (var dicEntry in dic) { await ReplaceInDirectory(rootDirectory, dicEntry.Key, dicEntry.Value); @@ -110,5 +132,6 @@ namespace Yi.Abp.Tool.Domain return directoryPath; } } + } } diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/YiAbpToolWebModule.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/YiAbpToolWebModule.cs index dd4cc1c7..25cdd73a 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/YiAbpToolWebModule.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/YiAbpToolWebModule.cs @@ -1,6 +1,9 @@ using System.Globalization; +using System.Text.Json.Serialization; +using System.Text.Json.Serialization.Metadata; using System.Threading.RateLimiting; using Microsoft.AspNetCore.Cors; +using Microsoft.AspNetCore.Mvc; using Microsoft.Extensions.DependencyInjection; using Microsoft.OpenApi.Models; using Newtonsoft.Json.Converters; @@ -12,6 +15,7 @@ using Yi.Abp.Tool.Application; using Yi.Framework.AspNetCore; using Yi.Framework.AspNetCore.Microsoft.AspNetCore.Builder; using Yi.Framework.AspNetCore.Microsoft.Extensions.DependencyInjection; +using Yi.Framework.Core.Json; namespace Yi.Abp.Tool.Web { @@ -41,15 +45,17 @@ namespace Yi.Abp.Tool.Web }); //设置api格式 - service.AddControllers().AddNewtonsoftJson(options => + Configure(options => { - options.SerializerSettings.DateFormatString = "yyyy-MM-dd HH:mm:ss"; - options.SerializerSettings.Converters.Add(new StringEnumConverter()); + options.JsonSerializerOptions.TypeInfoResolver = new DefaultJsonTypeInfoResolver(); + options.JsonSerializerOptions.Converters.Add(new DatetimeJsonConverter()); + options.JsonSerializerOptions.Converters.Add(new JsonStringEnumConverter()); }); + Configure(options => { options.AutoValidate = false; @@ -81,7 +87,7 @@ namespace Yi.Abp.Tool.Web }); }); - + service.AddHttpClient(); //速率限制 //每60秒限制100个请求,滑块添加,分6段 service.AddRateLimiter(_ => diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.Development.json b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.Development.json index 0c208ae9..a3f18fbe 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.Development.json +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.Development.json @@ -1,8 +1,3 @@ { - "Logging": { - "LogLevel": { - "Default": "Information", - "Microsoft.AspNetCore": "Warning" - } - } + "GiteeAccession": "8d9f05faec154475f121079579a0abf0" } diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.json b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.json index bf712e51..1781452b 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.json +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool.Web/appsettings.json @@ -15,5 +15,6 @@ "TempDirPath": "wwwroot/temp", "ModuleTemplateFilePath": "wwwroot/ModuleTemplate.zip", "ProjectTemplateFilePath": "wwwroot/ProjectTemplate.zip" - } + }, + "GiteeAccession": "" } diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool/Commands/NewCommand.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool/Commands/NewCommand.cs index d7ef5acd..ba56780a 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool/Commands/NewCommand.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool/Commands/NewCommand.cs @@ -26,13 +26,34 @@ namespace Yi.Abp.Tool.Commands public void CommandLineApplication(CommandLineApplication application) { - var templateTypeOption = application.Option("-t|--moduleType", "模板类型:`module`|`porject`", + var templateTypeOption = application.Option("-t|--template", "模板类型:`module`|`porject`", CommandOptionType.SingleValue); var pathOption = application.Option("-p|--path", "创建路径", CommandOptionType.SingleValue); var csfOption = application.Option("-csf", "是否创建解决方案文件夹", CommandOptionType.NoValue); + + var soureOption = application.Option("-s|--soure", "模板来源,gitee模板库分支名称: 默认值`defualt`", + CommandOptionType.SingleValue); + var moduleNameArgument = application.Argument("moduleName", "模块名", (_) => { }); - + //子命令,new list + application.Command("list",(applicationlist) => + { + applicationlist.OnExecute(() => + { + Console.WriteLine("正在远程搜索中..."); + var list=_templateGenService.GetAllTemplatesAsync().Result; + var tip = $""" + 全部模板包括: + 模板名称 + ---------------- + {list.JoinAsString("\n")} + """; + Console.WriteLine(tip); + return 0; + }); + }); + application.OnExecute(() => { #region 处理生成类型 @@ -41,6 +62,8 @@ namespace Yi.Abp.Tool.Commands var zipPath = string.Empty; byte[] fileByteArray; + var soure= soureOption.HasValue() ? soureOption.Value() : "defualt"; + var templateType = templateTypeOption.HasValue() ? templateTypeOption.Value() : "module"; if (templateType == "module") { @@ -48,12 +71,13 @@ namespace Yi.Abp.Tool.Commands fileByteArray = (_templateGenService.CreateModuleAsync(new TemplateGenCreateInputDto { Name = moduleNameArgument.Value, + ModuleSoure = soure }).Result); } else { - //代表模块生成 - fileByteArray = _templateGenService.CreateProjectAsync(new TemplateGenCreateInputDto + //还是代表模块生成 + fileByteArray = _templateGenService.CreateModuleAsync(new TemplateGenCreateInputDto { Name = moduleNameArgument.Value, }).Result; diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool/Program.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool/Program.cs index 5918ae8a..1395c9c4 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool/Program.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool/Program.cs @@ -13,13 +13,15 @@ class Program //args = ["-h"]; //版本 - args = ["-v"]; + // args = ["-v"]; //清理 // args = ["clear"]; //创建模块 //args = ["new","oooo", "-t","module","-p","D:\\temp","-csf"]; + //查看模板列表 + args = ["new","list"]; //添加模块 //args = ["add-module", "kkk"]; diff --git a/Yi.Abp.Net8/tool/Yi.Abp.Tool/YiAbpToolModule.cs b/Yi.Abp.Net8/tool/Yi.Abp.Tool/YiAbpToolModule.cs index 3e5b25f9..7564d566 100644 --- a/Yi.Abp.Net8/tool/Yi.Abp.Tool/YiAbpToolModule.cs +++ b/Yi.Abp.Net8/tool/Yi.Abp.Tool/YiAbpToolModule.cs @@ -15,7 +15,8 @@ namespace Yi.Abp.Tool Configure(options => { options.RemoteServices.Default = - new RemoteServiceConfiguration("https://ccnetcore.com:19009"); + // new RemoteServiceConfiguration("https://ccnetcore.com:19009"); + new RemoteServiceConfiguration("http://localhost:19002"); }); } }