From ba97bd3eb5e3471c4a067ce2fd05bebf8f4481df Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=A9=99=E5=AD=90?= <454313500@qq.com> Date: Fri, 15 Dec 2023 00:11:08 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=B7=BB=E5=8A=A0=E6=96=87=E4=BB=B6?= =?UTF-8?q?=E6=A8=A1=E5=9D=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Dtos/FileManager/FileGetListOutputDto.cs | 13 ++ .../IServices/IFileService.cs | 12 ++ .../Services/FileService.cs | 142 ++++++++++++++++++ .../Entities/FileAggregateRoot.cs | 48 ++++++ .../src/Yi.Abp.Web/Logs/log-20231215.txt | 84 +++++++++++ 5 files changed, 299 insertions(+) create mode 100644 Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/Dtos/FileManager/FileGetListOutputDto.cs create mode 100644 Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/IServices/IFileService.cs create mode 100644 Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application/Services/FileService.cs create mode 100644 Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Domain/Entities/FileAggregateRoot.cs create mode 100644 Yi.Abp.Net8/src/Yi.Abp.Web/Logs/log-20231215.txt diff --git a/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/Dtos/FileManager/FileGetListOutputDto.cs b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/Dtos/FileManager/FileGetListOutputDto.cs new file mode 100644 index 00000000..26bdd8f3 --- /dev/null +++ b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/Dtos/FileManager/FileGetListOutputDto.cs @@ -0,0 +1,13 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Volo.Abp.Application.Dtos; + +namespace Yi.Framework.Rbac.Application.FileManger +{ + public class FileGetListOutputDto:EntityDto + { + } +} diff --git a/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/IServices/IFileService.cs b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/IServices/IFileService.cs new file mode 100644 index 00000000..9653c305 --- /dev/null +++ b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application.Contracts/IServices/IFileService.cs @@ -0,0 +1,12 @@ +using Microsoft.AspNetCore.Http; +using Volo.Abp.Application.Services; +using Yi.Framework.Rbac.Application.FileManger; + +namespace Yi.Framework.Rbac.Application.Contracts.IServices +{ + public interface IFileService : IApplicationService + { + Task GetReturnPathAsync(Guid code, bool? isThumbnail); + Task> Post(IFormFileCollection file); + } +} diff --git a/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application/Services/FileService.cs b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application/Services/FileService.cs new file mode 100644 index 00000000..79c2dbf5 --- /dev/null +++ b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Application/Services/FileService.cs @@ -0,0 +1,142 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Mapster; +using Microsoft.AspNetCore.Http; +using Microsoft.AspNetCore.Mvc; +using Volo.Abp; +using Volo.Abp.Application.Services; +using Volo.Abp.Domain.Repositories; +using Volo.Abp.Guids; +using Yi.Framework.Core.Enums; +using Yi.Framework.Core.Helper; +using Yi.Framework.Rbac.Application.Contracts.IServices; +using Yi.Framework.Rbac.Application.FileManger; +using Yi.Framework.Rbac.Domain.Entities; + +namespace Yi.Framework.Rbac.Application.Services +{ + public class FileService : ApplicationService, IFileService + { + private readonly IRepository _repository; + private readonly HttpContext _httpContext; + private IGuidGenerator _guidGenerator; + public FileService(IRepository repository, IHttpContextAccessor httpContextAccessor, IGuidGenerator guidGenerator) + { + _guidGenerator = guidGenerator; + _repository = repository; + _httpContext = httpContextAccessor.HttpContext; + } + + /// + /// 下载文件,是否缩略图 + /// + /// + [Route("file/{code}/{isThumbnail?}")] + public async Task Get([FromRoute] Guid code, [FromRoute] bool? isThumbnail) + { + var path = await GetReturnPathAsync(code, isThumbnail); + + var steam = await File.ReadAllBytesAsync(path); + + //考虑从路径中获取 + var fileContentType = MimeHelper.GetMimeMapping(Path.GetFileName(path)); + //设置附件下载,下载名称 + //_httpContext.FileAttachmentHandle(file.FileName); + return new FileContentResult(steam, fileContentType ?? @"text/plain"); + } + + public async Task GetReturnPathAsync(Guid code, bool? isThumbnail) + { + var file = await _repository.GetAsync(x => x.Id == code); + if (file is null) + { + throw new UserFriendlyException("文件编号未匹配", "404"); + } + var path = file.FilePath; + //如果为缩略图,需要修改路径 + if (isThumbnail is true) + { + path = $"wwwroot/{FileTypeEnum.Thumbnail}/{file.Id}{Path.GetExtension(file.FileName)}"; + } + //路径为: 文件路径/文件id+文件扩展名 + + if (!File.Exists(path)) + { + throw new UserFriendlyException("本地文件不存在", "404"); + } + + return path; + } + + /// + /// 上传文件 + /// + /// + public async Task> Post([FromForm] IFormFileCollection file) + { + if (file.Count() == 0) + { + throw new ArgumentException("文件上传为空!"); + } + //批量插入 + List entities = new(); + + foreach (var f in file) + { + FileAggregateRoot data = new(_guidGenerator.Create()); + data.FileSize = (decimal)f.Length / 1024; + data.FileName = f.FileName; + + var type = MimeHelper.GetFileType(f.FileName); + + //落盘文件,文件名为雪花id+自己的扩展名 + string filename = data.Id.ToString() + Path.GetExtension(f.FileName); + string typePath = $"wwwroot/{type}"; + if (!Directory.Exists(typePath)) + { + Directory.CreateDirectory(typePath); + } + var filePath = Path.Combine(typePath, filename); + data.FilePath = filePath; + + + //生成文件 + using (var stream = new FileStream(filePath, FileMode.CreateNew, FileAccess.ReadWrite)) + { + await f.CopyToAsync(stream); + + //如果是图片类型,还需要生成缩略图,当然,如果图片很小,直接复制过去即可 + if (FileTypeEnum.Image.Equals(type)) + { + string thumbnailPath = $"wwwroot/{FileTypeEnum.Thumbnail}"; + if (!Directory.Exists(thumbnailPath)) + { + Directory.CreateDirectory(thumbnailPath); + } + string thumbnailFilePath = Path.Combine(thumbnailPath, filename); + try + { + // _imageSharpManager.ImageCompress(f.FileName, f.OpenReadStream(), thumbnailFilePath); + } + catch + { + var result = new byte[stream.Length]; + await stream.ReadAsync(result, 0, result.Length); + await File.WriteAllBytesAsync(thumbnailFilePath, result); + } + } + + + }; + entities.Add(data); + } + await _repository.InsertManyAsync(entities); + return entities.Adapt>(); + + + } + } +} diff --git a/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Domain/Entities/FileAggregateRoot.cs b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Domain/Entities/FileAggregateRoot.cs new file mode 100644 index 00000000..00f87f92 --- /dev/null +++ b/Yi.Abp.Net8/module/rbac/Yi.Framework.Rbac.Domain/Entities/FileAggregateRoot.cs @@ -0,0 +1,48 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using SqlSugar; +using Volo.Abp.Auditing; +using Volo.Abp.Domain.Entities; + +namespace Yi.Framework.Rbac.Domain.Entities +{ + public class FileAggregateRoot : AggregateRoot, IAuditedObject + { + public FileAggregateRoot() + { + } + + public FileAggregateRoot(Guid fileId) + { + this.Id = fileId; + } + + [SugarColumn(IsPrimaryKey = true)] + public override Guid Id { get; protected set; } + /// + /// 文件大小 + /// + [SugarColumn(ColumnName = "FileSize")] + public decimal FileSize { get; set; } + /// + /// 文件名 + /// + [SugarColumn(ColumnName = "FileName")] + public string FileName { get; set; } + /// + /// 文件路径 + /// + [SugarColumn(ColumnName = "FilePath")] + public string FilePath { get; set; } + + public DateTime CreationTime { get; set; } + public Guid? CreatorId { get; set; } + + public Guid? LastModifierId { get; set; } + + public DateTime? LastModificationTime { get; set; } + } +} diff --git a/Yi.Abp.Net8/src/Yi.Abp.Web/Logs/log-20231215.txt b/Yi.Abp.Net8/src/Yi.Abp.Web/Logs/log-20231215.txt new file mode 100644 index 00000000..b9ae1d97 --- /dev/null +++ b/Yi.Abp.Net8/src/Yi.Abp.Web/Logs/log-20231215.txt @@ -0,0 +1,84 @@ +2023-12-15 00:10:51.343 +08:00 [INF] Yi框架-Abp.vNext,启动! +2023-12-15 00:10:57.118 +08:00 [INF] Loaded ABP modules: +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.Web.YiAbpWebModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.SqlsugarCore.YiAbpSqlSugarCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.Domain.YiAbpDomainModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.Domain.Shared.YiAbpDomainSharedModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Rbac.Domain.Shared.YiFrameworkRbacDomainSharedModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Domain.AbpDddDomainSharedModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.MultiTenancy.AbpMultiTenancyAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.VirtualFileSystem.AbpVirtualFileSystemModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Localization.AbpLocalizationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Settings.AbpSettingsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Localization.AbpLocalizationAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Security.AbpSecurityModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Data.AbpDataModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.ObjectExtending.AbpObjectExtendingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Validation.AbpValidationAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Uow.AbpUnitOfWorkModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.EventBus.Abstractions.AbpEventBusAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Threading.AbpThreadingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Mapster.YiFrameworkMapsterModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Core.YiFrameworkCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.ObjectMapping.AbpObjectMappingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Bbs.Domain.Shared.YiFrameworkBbsDomainSharedModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Rbac.Domain.YiFrameworkRbacDomainModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.AspNetCore.SignalR.AbpAspNetCoreSignalRModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.AspNetCore.AbpAspNetCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Auditing.AbpAuditingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Json.AbpJsonModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Json.SystemTextJson.AbpJsonSystemTextJsonModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Json.AbpJsonAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Timing.AbpTimingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.MultiTenancy.AbpMultiTenancyModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Auditing.AbpAuditingContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Http.AbpHttpModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Http.AbpHttpAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Minify.AbpMinifyModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Authorization.AbpAuthorizationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Authorization.AbpAuthorizationAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Validation.AbpValidationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.ExceptionHandling.AbpExceptionHandlingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Domain.AbpDddDomainModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.EventBus.AbpEventBusModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Guids.AbpGuidsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.BackgroundWorkers.AbpBackgroundWorkersModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.DistributedLocking.AbpDistributedLockingAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Specifications.AbpSpecificationsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Caching.AbpCachingModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Serialization.AbpSerializationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Bbs.Domain.YiFrameworkBbsDomainModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Rbac.SqlSugarCore.YiFrameworkRbacSqlSugarCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.SqlSugarCore.YiFrameworkSqlSugarCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Bbs.SqlSugarCore.YiFrameworkBbsSqlSugarCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.Application.YiAbpApplicationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Abp.Application.Contracts.YiAbpApplicationContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Rbac.Application.Contracts.YiFrameworkRbacApplicationContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Ddd.Application.Contracts.YiFrameworkDddApplicationContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Application.AbpDddApplicationContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Bbs.Application.Contracts.YiFrameworkBbsApplicationContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Rbac.Application.YiFrameworkRbacApplicationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Ddd.Application.YiFrameworkDddApplicationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Application.AbpDddApplicationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Features.AbpFeaturesModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.GlobalFeatures.AbpGlobalFeaturesModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.BackgroundWorkers.Quartz.AbpBackgroundWorkersQuartzModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Quartz.AbpQuartzModule +2023-12-15 00:10:57.120 +08:00 [INF] - Yi.Framework.Bbs.Application.YiFrameworkBbsApplicationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.AspNetCore.Mvc.AbpAspNetCoreMvcModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.ApiVersioning.AbpApiVersioningAbstractionsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.AspNetCore.Mvc.AbpAspNetCoreMvcContractsModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.UI.Navigation.AbpUiNavigationModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.UI.AbpUiModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Autofac.AbpAutofacModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Castle.AbpCastleCoreModule +2023-12-15 00:10:57.120 +08:00 [INF] - Volo.Abp.Swashbuckle.AbpSwashbuckleModule +2023-12-15 00:10:57.121 +08:00 [INF] - Volo.Abp.AspNetCore.Serilog.AbpAspNetCoreSerilogModule +2023-12-15 00:10:57.121 +08:00 [INF] - Volo.Abp.AspNetCore.Authentication.JwtBearer.AbpAspNetCoreAuthenticationJwtBearerModule +2023-12-15 00:10:57.121 +08:00 [INF] - Yi.Framework.AspNetCore.YiFrameworkAspNetCoreModule +2023-12-15 00:10:58.044 +08:00 [INF] User profile is available. Using 'C:\Users\45431\AppData\Local\ASP.NET\DataProtection-Keys' as key repository and Windows DPAPI to encrypt keys at rest. +2023-12-15 00:10:58.208 +08:00 [INF] Initialized all ABP modules. +2023-12-15 00:10:58.431 +08:00 [INF] Now listening on: http://[::]:19001 +2023-12-15 00:10:58.431 +08:00 [INF] Application started. Press Ctrl+C to shut down. +2023-12-15 00:10:58.431 +08:00 [INF] Hosting environment: Development +2023-12-15 00:10:58.431 +08:00 [INF] Content root path: D:\CSharp\Yi\Yi.Abp.Net8\src\Yi.Abp.Web