添加IRootDirectory 接口,可通过注入IRootDirectory接口实现根据业务场景改变文件存储的位置
This commit is contained in:
12
FileService/Abstractions/IRootDirectory.cs
Normal file
12
FileService/Abstractions/IRootDirectory.cs
Normal file
@@ -0,0 +1,12 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Ufangx.FileServices.Abstractions
|
||||
{
|
||||
public interface IRootDirectory
|
||||
{
|
||||
Task<string> GetRoot();
|
||||
}
|
||||
}
|
||||
@@ -11,7 +11,7 @@ namespace Ufangx.FileServices.Abstractions
|
||||
{
|
||||
FileValidateResult Validate(IFormFile file, string schemeName=null);
|
||||
FileValidateResult Validate(IFormFileCollection files, string schemeName=null);
|
||||
Task<object> Handle(IFormFileCollection files, string schemeName = null);
|
||||
Task<object> Handle(IFormFileCollection files, string schemeName = null, string dir = null);
|
||||
Task<object> Handle(IFormFile file,string schemeName=null, string dir=null,string name=null);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
<RepositoryType>git</RepositoryType>
|
||||
<PackageTags>file service web uploader html5 uploader breakpoint renewal</PackageTags>
|
||||
<Copyright>Copyright (c) 2020-$([System.DateTime]::Now.Year) Jackson.Bruce</Copyright>
|
||||
<Version>1.0.2-beta</Version>
|
||||
<Version>1.0.5</Version>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(TargetFramework)|$(Platform)'=='netstandard2.0|AnyCPU'">
|
||||
@@ -41,4 +41,8 @@
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="2.1.1" />
|
||||
</ItemGroup>
|
||||
|
||||
<Target Name="PreBuild" BeforeTargets="PreBuildEvent">
|
||||
<Exec Command="del $(ProjectDir)$(OutDir)..\*.nupkg /s/q
exit 0" />
|
||||
</Target>
|
||||
|
||||
</Project>
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using Microsoft.Extensions.Options;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Options;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
@@ -6,23 +7,34 @@ using System.Text;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Ufangx.FileServices.Abstractions;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
namespace Ufangx.FileServices.Local
|
||||
{
|
||||
public class LocalFileService : IFileService
|
||||
{
|
||||
private readonly LocalFileOption option;
|
||||
private readonly IHttpContextAccessor httpContextAccessor;
|
||||
|
||||
public LocalFileService(IOptions<LocalFileOption> option) {
|
||||
public LocalFileService(IOptions<LocalFileOption> option,IHttpContextAccessor httpContextAccessor) {
|
||||
|
||||
this.option = option.Value; // option??new LocalFileOption();
|
||||
if (string.IsNullOrWhiteSpace(this.option.StorageRootDir)) {
|
||||
this.option.StorageRootDir = AppContext.BaseDirectory;
|
||||
}
|
||||
}
|
||||
protected string physicalPath(string path) {
|
||||
|
||||
return Path.Combine(option.StorageRootDir, path.Trim().Replace('\\', '/').TrimStart('/'));
|
||||
this.httpContextAccessor = httpContextAccessor;
|
||||
}
|
||||
protected async Task<string> physicalPath(string path) {
|
||||
string root;
|
||||
var rootService = httpContextAccessor.HttpContext.RequestServices.GetService<IRootDirectory>();
|
||||
if (rootService == null || string.IsNullOrWhiteSpace(root = await rootService.GetRoot()))
|
||||
{
|
||||
return Path.Combine(option.StorageRootDir, path.Trim().Replace('\\', '/').TrimStart('/')).Replace('\\', '/');
|
||||
}
|
||||
return Path.Combine(option.StorageRootDir,
|
||||
root.Trim().Replace('\\', '/').TrimStart('/'),
|
||||
path.Trim().Replace('\\', '/').TrimStart('/')).Replace('\\', '/');
|
||||
}
|
||||
protected bool CreateDirIfNonexistence(string path) {
|
||||
|
||||
@@ -34,7 +46,7 @@ namespace Ufangx.FileServices.Local
|
||||
}
|
||||
public async Task<bool> Delete(string path, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
string p = physicalPath(path);
|
||||
string p = await physicalPath(path);
|
||||
if (File.Exists(p))
|
||||
{
|
||||
File.Delete(p);
|
||||
@@ -45,12 +57,13 @@ namespace Ufangx.FileServices.Local
|
||||
|
||||
public async Task<bool> Exists(string path, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
return await Task.FromResult(File.Exists(physicalPath(path)));
|
||||
var filePath = await physicalPath(path);
|
||||
return File.Exists(filePath);
|
||||
}
|
||||
|
||||
public async Task<Stream> GetStream(string path, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p =await physicalPath(path);
|
||||
if (!File.Exists(p)) return null;
|
||||
return await Task.FromResult(new FileStream(p, FileMode.Open, FileAccess.Read,FileShare.ReadWrite| FileShare.Delete));
|
||||
|
||||
@@ -58,7 +71,7 @@ namespace Ufangx.FileServices.Local
|
||||
|
||||
public async Task<byte[]> GetFileData(string path, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p =await physicalPath(path);
|
||||
if (!File.Exists(p)) return null;
|
||||
#if netstandard20
|
||||
return await Task.FromResult(File.ReadAllBytes(p));
|
||||
@@ -70,7 +83,7 @@ namespace Ufangx.FileServices.Local
|
||||
|
||||
public async Task<bool> Save(string path, Stream stream, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p =await physicalPath(path);
|
||||
if (CreateDirIfNonexistence(p))
|
||||
{
|
||||
if (stream.CanSeek && stream.Position > 0) { stream.Position = 0; }
|
||||
@@ -95,7 +108,7 @@ namespace Ufangx.FileServices.Local
|
||||
|
||||
public async Task<bool> Save(string path, byte[] data, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p = await physicalPath(path);
|
||||
if (CreateDirIfNonexistence(p))
|
||||
{
|
||||
#if netstandard20
|
||||
@@ -110,19 +123,20 @@ namespace Ufangx.FileServices.Local
|
||||
return false;
|
||||
}
|
||||
public async Task Move(string sourceFileName,string destFileName) {
|
||||
sourceFileName = physicalPath(sourceFileName);
|
||||
destFileName = physicalPath(destFileName);
|
||||
sourceFileName = await physicalPath(sourceFileName);
|
||||
destFileName = await physicalPath(destFileName);
|
||||
File.Move(sourceFileName, destFileName);
|
||||
await Task.CompletedTask;
|
||||
}
|
||||
public async Task<DateTime> GetModifyDate(string path, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
return await Task.FromResult(File.GetLastWriteTime(physicalPath(path)));
|
||||
var filePath = await physicalPath(path);
|
||||
return File.GetLastWriteTime(filePath);
|
||||
}
|
||||
|
||||
public async Task<bool> Append(string path, Stream stream, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p = await physicalPath(path);
|
||||
if (CreateDirIfNonexistence(p))
|
||||
{
|
||||
if (stream.CanSeek && stream.Position > 0) { stream.Position = 0; }
|
||||
@@ -146,7 +160,7 @@ namespace Ufangx.FileServices.Local
|
||||
|
||||
public async Task<bool> Append(string path, byte[] data, CancellationToken token = default(CancellationToken))
|
||||
{
|
||||
var p = physicalPath(path);
|
||||
var p = await physicalPath(path);
|
||||
if (CreateDirIfNonexistence(p))
|
||||
{
|
||||
using (var fs = new FileStream(p, FileMode.Append, FileAccess.Write, FileShare.Read))
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using Microsoft.Extensions.Options;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Options;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
@@ -14,7 +15,7 @@ namespace Ufangx.FileServices.Local
|
||||
public class LocalResumableService : LocalFileService, IResumableService
|
||||
{
|
||||
private readonly IResumableInfoService resumableInfoService;
|
||||
public LocalResumableService(IResumableInfoService resumableInfoService, IOptions<LocalFileOption> option):base(option) {
|
||||
public LocalResumableService(IResumableInfoService resumableInfoService, IOptions<LocalFileOption> option, IHttpContextAccessor httpContextAccessor) :base(option, httpContextAccessor) {
|
||||
this.resumableInfoService = resumableInfoService;
|
||||
}
|
||||
FileStream GetFileStream(string path) {
|
||||
@@ -86,7 +87,7 @@ namespace Ufangx.FileServices.Local
|
||||
if (info == null) {
|
||||
throw new Exception($"无效的{nameof(blob.ResumableKey)}");
|
||||
}
|
||||
var p = physicalPath(info.StoreName);
|
||||
var p =await physicalPath(info.StoreName);
|
||||
string tempdir = GetTempDir(p,info.Key);
|
||||
var tmp = Path.Combine(tempdir, $"{blob.BlobIndex}").Replace('\\','/');
|
||||
if (CreateDirIfNonexistence(tmp))
|
||||
@@ -141,7 +142,7 @@ namespace Ufangx.FileServices.Local
|
||||
}
|
||||
|
||||
if (await resumableInfoService.Delete(info)) {
|
||||
string tempdir = GetTempDir(physicalPath(info.StoreName), info.Key);
|
||||
string tempdir = GetTempDir(await physicalPath(info.StoreName), info.Key);
|
||||
try
|
||||
{
|
||||
Directory.Delete(tempdir, true);
|
||||
|
||||
@@ -30,7 +30,7 @@ namespace Ufangx.FileServices.Middlewares
|
||||
//如果有文件验证失败则返回
|
||||
return;
|
||||
}
|
||||
await WriteJsonAsync(context, await uploader.Handle(context.Request.Form.Files, _scheme));
|
||||
await WriteJsonAsync(context, await uploader.Handle(context.Request.Form.Files, _scheme,dir));
|
||||
return;
|
||||
|
||||
}
|
||||
@@ -40,7 +40,7 @@ namespace Ufangx.FileServices.Middlewares
|
||||
{
|
||||
return;
|
||||
}
|
||||
await WriteJsonAsync(context, await uploader.Handle(context.Request.Form.Files[0], _scheme));
|
||||
await WriteJsonAsync(context, await uploader.Handle(context.Request.Form.Files[0], _scheme,dir,fileName));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -42,7 +42,7 @@ namespace Ufangx.FileServices.Models
|
||||
{
|
||||
|
||||
Services.Configure<FileServiceOptions>(opt => opt.AddScheme<THandler>(name, storeDirectory, supportExtensions, LimitedSize));
|
||||
Services.AddTransient<THandler>();
|
||||
//Services.AddTransient<THandler>();//外面注入
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -76,12 +76,12 @@ namespace Ufangx.FileServices.Services
|
||||
//否则生成文件名称
|
||||
return await GenerateFileName(scheme, originName, dir);
|
||||
}
|
||||
public async Task<object> Handle(IFormFileCollection files, string schemeName = null)
|
||||
public async Task<object> Handle(IFormFileCollection files, string schemeName = null, string dir = null)
|
||||
{
|
||||
List<object> results = new List<object>();
|
||||
foreach (var file in files)
|
||||
{
|
||||
var result = await Handle(file, schemeName);
|
||||
var result = await Handle(file, schemeName, dir);
|
||||
if (result != null){ results.Add(result); }
|
||||
}
|
||||
return results;
|
||||
|
||||
Reference in New Issue
Block a user