修改在linux下路径的bug

This commit is contained in:
Jackson.Bruce
2020-07-13 14:02:58 +08:00
parent 61c39e1d3f
commit 6d148e9c25
13 changed files with 82 additions and 696 deletions

View File

@@ -7,7 +7,7 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "FileServices", "FileService
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TestWeb", "TestWeb\TestWeb.csproj", "{B64F2077-52A2-472F-883F-57EBE8805F8D}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "QiniuFileService", "Qiniu\QiniuFileService.csproj", "{218AEB0B-2C51-42D7-98E0-4C1FE7E09E69}"
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Qiniu.FileService", "Qiniu\Qiniu.FileService.csproj", "{218AEB0B-2C51-42D7-98E0-4C1FE7E09E69}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution

View File

@@ -4,6 +4,16 @@
<TargetFrameworks>netstandard2.0;netcoreapp2.0;netstandard2.1;netcoreapp3.0</TargetFrameworks>
<RootNamespace>Ufangx.FileServices</RootNamespace>
<AssemblyName>FileServices</AssemblyName>
<Authors>Jackson.bruce</Authors>
<Company>Ufangx</Company>
<Description>File management, super large file upload, breakpoint renewal</Description>
<PackageLicenseExpression>MIT</PackageLicenseExpression>
<RepositoryUrl>https://github.com/JacksonBruce/FileServices.git</RepositoryUrl>
<PackageProjectUrl>https://github.com/JacksonBruce/FileServices</PackageProjectUrl>
<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.0-beta.1</Version>
</PropertyGroup>
<PropertyGroup Condition="'$(TargetFramework)|$(Platform)'=='netstandard2.0|AnyCPU'">

View File

@@ -22,7 +22,7 @@ namespace Ufangx.FileServices.Local
}
protected string physicalPath(string path) {
return Path.Combine(option.StorageRootDir, path.Trim().Replace('/', '\\').TrimStart('\\'));
return Path.Combine(option.StorageRootDir, path.Trim().Replace('\\', '/').TrimStart('/'));
}
protected bool CreateDirIfNonexistence(string path) {

View File

@@ -22,14 +22,15 @@ namespace Ufangx.FileServices.Local
}
string GetTempDir(string path, string key)
{
return Path.Combine(Path.GetDirectoryName(path), $"_tmp{key}");
return Path.Combine(Path.GetDirectoryName(path), $"_tmp{key}").Replace('\\','/');
}
bool CheckFiles(string dir, long count) {
//Console.WriteLine("正在检查文件。。。");
//Stopwatch sw = Stopwatch.StartNew();
for (long i = 0; i < count; i++)
{
if (!File.Exists(Path.Combine(dir, $"{i}"))) { return false; }
string path = Path.Combine(dir, $"{i}").Replace('\\', '/');
if (!File.Exists(path)) { return false; }
}
//sw.Stop();
//Console.WriteLine($"检查{count}个文件,用时:{sw.Elapsed.TotalMilliseconds}毫秒");
@@ -51,8 +52,8 @@ namespace Ufangx.FileServices.Local
using (var fs = GetFileStream(path))
{
for (long i = 0; i < count; i++)
{
var blob = await GetBlob(Path.Combine(dir, $"{i}"), token);
{
var blob = await GetBlob(Path.Combine(dir, $"{i}").Replace('\\','/'), token);
await fs.WriteAsync(blob, 0, blob.Length, token);
}
await fs.FlushAsync(token);
@@ -87,7 +88,7 @@ namespace Ufangx.FileServices.Local
}
var p = physicalPath(info.StoreName);
string tempdir = GetTempDir(p,info.Key);
var tmp = Path.Combine(tempdir, $"{blob.BlobIndex}");
var tmp = Path.Combine(tempdir, $"{blob.BlobIndex}").Replace('\\','/');
if (CreateDirIfNonexistence(tmp))
{
var stream = blob.Data;

View File

@@ -41,26 +41,26 @@ namespace Ufangx.FileServices.Services
nameRule = FileNameRule.Ascending;
}
if (directory == null) { directory = string.Empty; }
directory = Path.Combine(scheme?.StoreDirectory ?? string.Empty, directory);
directory = Path.Combine(scheme?.StoreDirectory ?? string.Empty, directory).Replace('\\', '/');
string fileName;
switch (nameRule)
{
case FileNameRule.Ascending:
fileName = Path.Combine(directory, originName);
fileName = Path.Combine(directory, originName).Replace('\\', '/');
int index = 0;
while (await fileService.Exists(fileName))
{
fileName = Path.Combine(directory, $"{Path.GetFileNameWithoutExtension(originName)}({++index}){Path.GetExtension(originName)}");
fileName = Path.Combine(directory, $"{Path.GetFileNameWithoutExtension(originName)}({++index}){Path.GetExtension(originName)}").Replace('\\', '/');
}
break;
case FileNameRule.Date:
fileName = Path.Combine(directory, string.Format(fileNameRuleOptions?.Format ?? "{0:yyyyMMddHHmmss}", DateTime.Now) + Path.GetExtension(originName));
fileName = Path.Combine(directory, string.Format(fileNameRuleOptions?.Format ?? "{0:yyyyMMddHHmmss}", DateTime.Now) + Path.GetExtension(originName)).Replace('\\', '/');
break;
case FileNameRule.Custom:
fileName = Path.Combine(directory, fileNameRuleOptions.Custom(originName));
fileName = Path.Combine(directory, fileNameRuleOptions.Custom(originName)).Replace('\\', '/');
break;
default:
fileName = Path.Combine(directory, originName);
fileName = Path.Combine(directory, originName).Replace('\\', '/');
break;
}
return fileName.Replace('\\', '/');

View File

@@ -1,36 +0,0 @@
using System.Diagnostics.CodeAnalysis;
namespace Qiniu.Http
{
/// <summary>
/// HTTP 内容类型(Content-Type)
/// </summary>
[SuppressMessage("ReSharper", "InconsistentNaming")]
public class ContentType
{
/// <summary>
/// 资源类型:普通文本
/// </summary>
public static readonly string TEXT_PLAIN = "text/plain";
/// <summary>
/// 资源类型JSON字符串
/// </summary>
public static readonly string APPLICATION_JSON = "application/json";
/// <summary>
/// 资源类型:未知类型(数据流)
/// </summary>
public static readonly string APPLICATION_OCTET_STREAM = "application/octet-stream";
/// <summary>
/// 资源类型:表单数据(键值对)
/// </summary>
public static readonly string WWW_FORM_URLENC = "application/x-www-form-urlencoded";
/// <summary>
/// 资源类型:多分部数据
/// </summary>
public static readonly string MULTIPART_FORM_DATA = "multipart/form-data";
}
}

View File

@@ -1,169 +0,0 @@
using System.Diagnostics.CodeAnalysis;
namespace Qiniu.Http
{
/// <summary>
/// HTTP 状态码
/// </summary>
[SuppressMessage("ReSharper", "InconsistentNaming")]
public enum HttpCode
{
#region _PRE_
/// <summary>
/// 成功
/// </summary>
OK = 200,
/// <summary>
/// 部分OK
/// </summary>
PARTLY_OK = 298,
/// <summary>
/// 请求错误
/// </summary>
BAD_REQUEST = 400,
/// <summary>
/// 认证授权失败
/// </summary>
AUTHENTICATION_FAILED = 401,
/// <summary>
/// 拒绝访问
/// </summary>
ACCESS_DENIED = 403,
/// <summary>
/// 资源不存在
/// </summary>
OBJECT_NOT_FOUND = 404,
/// <summary>
/// CRC32校验失败
/// </summary>
CRC32_CHECK_FAILEd = 406,
/// <summary>
/// 上传文件大小超限
/// </summary>
FILE_SIZE_EXCEED = 413,
/// <summary>
/// 镜像回源失败
/// </summary>
PREFETCH_FAILED = 478,
/// <summary>
/// 错误网关
/// </summary>
BAD_GATEWAY = 502,
/// <summary>
/// 服务端不可用
/// </summary>
SERVER_UNAVAILABLE = 503,
/// <summary>
/// 服务端操作超时
/// </summary>
SERVER_TIME_EXCEED = 504,
/// <summary>
/// 单个资源访问频率过高
/// </summary>
TOO_FREQUENT_ACCESS = 573,
/// <summary>
/// 回调失败
/// </summary>
CALLBACK_FAILED = 579,
/// <summary>
/// 服务端操作失败
/// </summary>
SERVER_OPERATION_FAILED = 599,
/// <summary>
/// 资源内容被修改
/// </summary>
CONTENT_MODIFIED = 608,
/// <summary>
/// 文件不存在
/// </summary>
FILE_NOT_EXIST = 612,
/// <summary>
/// 文件已存在
/// </summary>
FILE_EXISTS = 614,
/// <summary>
/// 空间数量已达上限
/// </summary>
BUCKET_COUNT_LIMIT = 630,
/// <summary>
/// 空间或者文件不存在
/// </summary>
BUCKET_NOT_EXIST = 631,
/// <summary>
/// 列举资源(list)使用了非法的marker
/// </summary>
INVALID_MARKER = 640,
/// <summary>
/// 在断点续上传过程中后续上传接收地址不正确或ctx信息已过期。
/// </summary>
CONTEXT_EXPIRED = 701,
#endregion _PRE_
#region _USR_
/// <summary>
/// 自定义HTTP状态码 (默认值)
/// </summary>
USER_UNDEF = 0,
/// <summary>
/// 自定义HTTP状态码 (用户取消)
/// </summary>
USER_CANCELED = -2,
/// <summary>
/// 自定义HTTP状态码 (用户暂停)
/// </summary>
USER_PAUSED = 1,
/// <summary>
/// 自定义HTTP状态码 (用户继续)
/// </summary>
USER_RESUMED = 2,
/// <summary>
/// 自定义HTTP状态码 (需要重试)
/// </summary>
USER_NEED_RETRY = 3,
/// <summary>
/// 自定义HTTP状态码 (异常或错误)
/// </summary>
INVALID_ARGUMENT = -4,
/// <summary>
/// 自定义HTTP状态码文件不合法
/// </summary>
INVALID_FILE = -3,
/// <summary>
/// 自定义HTTP状态码凭证不合法
/// </summary>
INVALID_TOKEN = -5,
#endregion _USR_
}
}

View File

@@ -1,234 +0,0 @@
using System;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Text;
using System.Threading.Tasks;
using Qiniu.Util;
namespace Qiniu.Http
{
/// <summary>
/// HttpManager for .NET 4.5+
/// </summary>
public class HttpManager : IDisposable
{
public static readonly HttpManager SharedInstance = new HttpManager();
private readonly HttpClient _client;
private string _userAgent;
/// <summary>
/// 初始化
/// </summary>
/// <param name="allowAutoRedirect">是否允许HttpWebRequest的“重定向”默认禁止</param>
public HttpManager(bool allowAutoRedirect = false) : this(null, allowAutoRedirect)
{
}
/// <summary>
/// 初始化
/// </summary>
/// <param name="baseUrl">API Host可选</param>
/// <param name="allowAutoRedirect">是否允许HttpWebRequest的“重定向”默认禁止</param>
public HttpManager(string baseUrl, bool allowAutoRedirect = false)
{
_client = new HttpClient(new HttpClientHandler { AllowAutoRedirect = allowAutoRedirect });
if (!string.IsNullOrEmpty(baseUrl)) _client.BaseAddress = new Uri(baseUrl);
_client.DefaultRequestHeaders.ExpectContinue = false;
SetUserAgent(GetUserAgent());
}
public void Dispose()
{
_client?.Dispose();
}
/// <summary>
/// 客户端标识(UserAgent),示例:"SepcifiedClient/1.1 (Universal)"
/// </summary>
/// <returns>客户端标识UA</returns>
public static string GetUserAgent()
{
#if NETSTANDARD1_3
var osDesc = $"{System.Runtime.InteropServices.RuntimeInformation.OSDescription}";
#else
var osDesc = $"{Environment.OSVersion.Platform}; {Environment.OSVersion.Version}";
#endif
return $"{QiniuCSharpSdk.Alias}/{QiniuCSharpSdk.Version} ({QiniuCSharpSdk.RTFX}; {osDesc})";
}
/// <summary>
/// 设置自定义的客户端标识(UserAgent),示例:"SepcifiedClient/1.1 (Universal)"
/// 如果设置为空白或者不设置SDK会自动使用默认的UserAgent
/// </summary>
/// <param name="userAgent">用户自定义的UserAgent</param>
/// <returns>客户端标识UA</returns>
public void SetUserAgent(string userAgent)
{
_userAgent = userAgent;
_client.DefaultRequestHeaders.UserAgent.Clear();
if (!string.IsNullOrEmpty(userAgent))
{
_client.DefaultRequestHeaders.UserAgent.ParseAdd(userAgent);
}
}
/// <summary>
/// 多部分表单数据(multi-part form-data)的分界(boundary)标识
/// </summary>
/// <returns>分界(boundary)标识字符串</returns>
public static string CreateFormDataBoundary()
{
var now = DateTime.UtcNow.Ticks.ToString();
return $"-------{QiniuCSharpSdk.Alias}Boundary{Hashing.CalcMd5X(now)}";
}
/// <summary>
/// 发送HTTP请求
/// </summary>
/// <param name="request">请求消息</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP请求的响应结果</returns>
public async Task<HttpResult> SendAsync(HttpRequestMessage request, string token = null, bool binaryMode = false)
{
var result = new HttpResult();
HttpResponseMessage response = null;
if (!string.IsNullOrEmpty(token))
{
request.Headers.Add("Authorization", token);
}
try
{
response = await _client.SendAsync(request);
await result.ReadAsync(response, binaryMode);
}
catch (Exception exception)
{
var wrapper = new Exception($"[{DateTime.Now:yyyy-MM-dd HH:mm:ss.ffff}] [{_userAgent}] [HTTP-{request.Method.Method}] Error: ", exception);
await result.ReadErrorAsync(wrapper, response);
}
finally
{
response?.Dispose();
}
return result;
}
/// <summary>
/// HTTP-GET方法
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-GET的响应结果</returns>
public Task<HttpResult> GetAsync(string url, string token = null, bool binaryMode = false)
{
var request = new HttpRequestMessage(HttpMethod.Get, url);
return SendAsync(request, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(不包含body数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostAsync(string url, string token = null, bool binaryMode = false)
{
var request = new HttpRequestMessage(HttpMethod.Post, url);
return SendAsync(request, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="content">主体数据[可选]</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostAsync(string url, HttpContent content = null, string token = null, bool binaryMode = false)
{
var request = new HttpRequestMessage(HttpMethod.Post, url) { Content = content };
return SendAsync(request, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(包含body数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="data">主体数据(字节数据)</param>
/// <param name="mimeType">主体数据内容类型</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostDataAsync(string url, byte[] data, string mimeType = "application/octet-stream", string token = null, bool binaryMode = false)
{
var content = new ByteArrayContent(data);
content.Headers.ContentType = MediaTypeHeaderValue.Parse(mimeType);
return PostAsync(url, content, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(包含表单数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="data">表单数据</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostFormAsync(string url, string data, string token = null, bool binaryMode = false)
{
var content = new StringContent(data, Encoding.UTF8, ContentType.WWW_FORM_URLENC);
return PostAsync(url, content, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(包含表单数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="data">表单数据</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostFormAsync(string url, byte[] data, string token = null, bool binaryMode = false)
{
var content = new ByteArrayContent(data);
content.Headers.ContentType = MediaTypeHeaderValue.Parse(ContentType.WWW_FORM_URLENC);
return PostAsync(url, content, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(包含JSON文本的body数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="data">主体数据(JSON文本)</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostJsonAsync(string url, string data, string token = null, bool binaryMode = false)
{
var content = new StringContent(data, Encoding.UTF8, ContentType.APPLICATION_JSON);
return PostAsync(url, content, token, binaryMode);
}
/// <summary>
/// HTTP-POST方法(包含普通文本的body数据)
/// </summary>
/// <param name="url">请求目标URL</param>
/// <param name="data">主体数据(普通文本)</param>
/// <param name="token">令牌(凭证)[可选]</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容(默认:否,即表示以文本方式读取)</param>
/// <returns>HTTP-POST的响应结果</returns>
public Task<HttpResult> PostTextAsync(string url, string data, string token = null, bool binaryMode = false)
{
var content = new StringContent(data, Encoding.UTF8, ContentType.TEXT_PLAIN);
return PostAsync(url, content, token, binaryMode);
}
}
}

View File

@@ -1,215 +0,0 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Text;
using System.Threading.Tasks;
namespace Qiniu.Http
{
/// <summary>
/// HTTP请求(GET,POST等)的返回消息
/// </summary>
public class HttpResult
{
/// <summary>
/// 非法上传凭证错误
/// </summary>
public static readonly HttpResult InvalidToken = new HttpResult
{
Code = (int)HttpCode.INVALID_TOKEN,
Text = "invalid uptoken"
};
/// <summary>
/// 非法文件错误
/// </summary>
public static readonly HttpResult InvalidFile = new HttpResult
{
Code = (int)HttpCode.INVALID_FILE,
Text = "invalid file"
};
/// <summary>
/// 初始化(所有成员默认值,需要后续赋值)
/// </summary>
public HttpResult()
{
Code = (int)HttpCode.USER_UNDEF;
Text = null;
Data = null;
RefCode = (int)HttpCode.USER_UNDEF;
RefInfo = null;
}
/// <summary>
/// 状态码 (200表示OK)
/// </summary>
public int Code { get; set; }
/// <summary>
/// 消息或错误文本
/// </summary>
public string Text { get; set; }
/// <summary>
/// 消息或错误(二进制格式)
/// </summary>
public byte[] Data { get; set; }
/// <summary>
/// 参考代码(用户自定义)
/// </summary>
public int RefCode { get; set; }
/// <summary>
/// 附加信息(用户自定义,如Exception内容)
/// </summary>
public string RefText { get; set; }
/// <summary>
/// 参考信息(从返回消息WebResponse的头部获取)
/// </summary>
public Dictionary<string, string> RefInfo { get; set; }
/// <summary>
/// 对象复制
/// </summary>
/// <param name="source">要复制其内容的来源</param>
public void Shadow(HttpResult source)
{
Code = source.Code;
Text = source.Text;
Data = source.Data;
RefCode = source.RefCode;
RefText += source.RefText;
RefInfo = source.RefInfo;
}
/// <summary>
/// 读取 <see cref="HttpResponseMessage" /> 数据
/// </summary>
/// <param name="response">Http响应</param>
/// <param name="binaryMode">是否以二进制模式读取响应内容</param>
/// <exception cref="HttpRequestException"></exception>
internal async Task ReadAsync(HttpResponseMessage response, bool binaryMode)
{
ReadInfo(response);
if (binaryMode)
{
Data = await response.Content.ReadAsByteArrayAsync();
}
else
{
Text = await response.Content.ReadAsStringAsync();
}
}
internal async Task ReadErrorAsync(Exception exception, HttpResponseMessage response)
{
var sb = new StringBuilder();
var e = exception;
while (e != null)
{
sb.Append(e.Message + " ");
e = e.InnerException;
}
sb.AppendLine();
RefText += sb.ToString();
RefCode = (int)HttpCode.USER_UNDEF;
if (response != null)
{
ReadInfo(response);
Text = await response.Content.ReadAsStringAsync();
}
}
private void ReadInfo(HttpResponseMessage response)
{
Code = (int)response.StatusCode;
RefCode = (int)response.StatusCode;
if (RefInfo == null)
{
RefInfo = new Dictionary<string, string>();
}
RefInfo.Add("ProtocolVersion", response.Version.ToString());
if (!string.IsNullOrEmpty(response.Content.Headers.ContentType.CharSet))
{
RefInfo.Add("Characterset", response.Content.Headers.ContentType.CharSet);
}
if (!response.Content.Headers.ContentEncoding.Any())
{
RefInfo.Add("ContentEncoding", string.Join("; ", response.Content.Headers.ContentEncoding));
}
RefInfo.Add("ContentType", response.Content.Headers.ContentType.ToString());
RefInfo.Add("ContentLength", response.Content.Headers.ContentLength.ToString());
foreach (var header in response.Headers) RefInfo.Add(header.Key, string.Join("; ", header.Value));
}
/// <summary>
/// 转换为易读或便于打印的字符串格式
/// </summary>
/// <returns>便于打印和阅读的字符串</returns>
public override string ToString()
{
var sb = new StringBuilder();
sb.Append($"code:{Code}");
sb.AppendLine();
if (!string.IsNullOrEmpty(Text))
{
sb.AppendLine("text:");
sb.AppendLine(Text);
}
if (Data != null)
{
sb.AppendLine("data:");
const int n = 1024;
if (Data.Length <= n)
{
sb.AppendLine(Encoding.UTF8.GetString(Data));
}
else
{
sb.AppendLine(Encoding.UTF8.GetString(Data, 0, n));
sb.Append($"<--- TOO-LARGE-TO-DISPLAY --- TOTAL {Data.Length} BYTES --->");
sb.AppendLine();
}
}
sb.AppendLine();
sb.Append($"ref-code:{RefCode}");
sb.AppendLine();
if (!string.IsNullOrEmpty(RefText))
{
sb.AppendLine("ref-text:");
sb.AppendLine(RefText);
}
if (RefInfo != null)
{
sb.AppendLine("ref-info:");
foreach (var d in RefInfo) sb.AppendLine($"{d.Key}:{d.Value}");
}
sb.AppendLine();
return sb.ToString();
}
}
}

View File

@@ -0,0 +1,22 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFrameworks>netstandard2.0;netcoreapp2.0;netstandard2.1;netcoreapp3.0</TargetFrameworks>
<AssemblyName>Qiniu.FileService</AssemblyName>
<Authors>Jackson.bruce</Authors>
<Company>Ufangx</Company>
<Description>File management, super large file upload, breakpoint renewal</Description>
<licenseUrl>https://github.com/JacksonBruce/FileServices/blob/master/LICENSE</licenseUrl>
<RepositoryUrl>https://github.com/JacksonBruce/FileServices.git</RepositoryUrl>
<PackageProjectUrl>https://github.com/JacksonBruce/FileServices</PackageProjectUrl>
<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.0-beta.1</Version>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FileServices" Version="1.0.0" />
<PackageReference Include="Qiniu.SDK" Version="8.0.0" />
</ItemGroup>
</Project>

View File

@@ -1,22 +0,0 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp2.1</TargetFramework>
<AssemblyName>QiniuFileService</AssemblyName>
</PropertyGroup>
<ItemGroup>
<Compile Remove="Http\**" />
<EmbeddedResource Remove="Http\**" />
<None Remove="Http\**" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Qiniu.SDK" Version="8.0.0" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\FileService\FileServices.csproj" />
</ItemGroup>
</Project>

View File

@@ -2,6 +2,7 @@ using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Authentication.Cookies;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.HttpsPolicy;
@@ -27,8 +28,40 @@ namespace TestWeb
public void ConfigureServices(IServiceCollection services)
{
services.AddHttpContextAccessor();
services.AddFileServices(opt=>opt.DefaultScheme="")
.AddLocalServices(o => o.StorageRootDir = hostEnvironment.ContentRootPath);
services.AddFileServices(opt => {
opt.DefaultScheme = "documents";//Ĭ<><C4AC><EFBFBD><EFBFBD><EFBFBD>ĵ<EFBFBD><C4B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
opt.AddAuthenticationScheme(CookieAuthenticationDefaults.AuthenticationScheme);//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>֤<EFBFBD><D6A4><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//<2F>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD>ʱ<EFBFBD><CAB1><EFBFBD>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
opt.RuleOptions = new Ufangx.FileServices.Models.FileNameRuleOptions()
{
Rule = Ufangx.FileServices.Models.FileNameRule.Custom,//<2F>Զ<EFBFBD><D4B6><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>򣬱<EFBFBD><F2A3ACB1><EFBFBD><EFBFBD><EFBFBD>Զ<EFBFBD><D4B6><EFBFBD><E5B7BD>
Custom = originFileName => string.Format("{0:yyyyMMddHHmmss}_xx_{1}", DateTime.Now, originFileName),
Format = "xxx_{0:yyyyMMddHHmmss}"//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ú<EFBFBD>Rule=FileNameRule.Dateһ<65><D2BB>ʹ<EFBFBD>ã<EFBFBD>Ĭ<EFBFBD><C4AC><EFBFBD>ǣ<EFBFBD>{0:yyyyMMddHHmmss}
};
})
//<2F><>Ƭ<EFBFBD><C6AC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
.AddScheme("pictures", opt => {
opt.StoreDirectory = "wwwroot/pictures";//ͼƬ<CDBC><EFBFBD><E6B4A2>Ŀ¼
opt.SupportExtensions = new string[] { ".jpg", ".png" };//֧<>ֵ<EFBFBD><D6B5><EFBFBD>չ<EFBFBD><D5B9>
opt.HandlerType = null;//<2F>ϴ<EFBFBD><CFB4>ɹ<EFBFBD><C9B9><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͣ<EFBFBD><CDA3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͱ<EFBFBD><CDB1><EFBFBD>ʵ<EFBFBD><CAB5>IFileHandler<65>ӿ<EFBFBD>
opt.LimitedSize = 1024 * 1024 * 4;//<2F>ļ<EFBFBD><C4BC><EFBFBD>С<EFBFBD><D0A1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ֵ<EFBFBD><D6B5><EFBFBD>ֽ<EFBFBD>Ϊ<EFBFBD><CEAA>λ
})
.AddScheme("documents",opt => opt.StoreDirectory = "wwwroot/documents")//<2F>ĵ<EFBFBD><C4B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//.AddScheme<VideoService>(name:"videos",storeDirectory:"",supportExtensions:new string[] { },LimitedSize:1024*1024*500)//<2F><>Ƶ<EFBFBD><C6B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//.AddLocalServices(o => o.StorageRootDir = hostEnvironment.ContentRootPath)//<2F><><EFBFBD><EFBFBD><EFBFBD>ļ<EFBFBD>ϵͳ<CFB5><CDB3><EFBFBD>ļ<EFBFBD><C4BC><EFBFBD><EFBFBD>ڱ<EFBFBD><DAB1><EFBFBD>
//<2F><>ţ<EFBFBD><EFBFBD><E6B4A2><EFBFBD><EFBFBD>
.AddQiniuFileService(opt => {
opt.AccessKey = "";//
opt.SecretKey = "";
opt.BasePath = "";
opt.Bucket = "";
opt.Domain = "";
opt.ChunkUnit = Qiniu.Storage.ChunkUnit.U1024K;
opt.Zone = "ZoneCnEast";
});
services.AddControllersWithViews();
}

View File

@@ -12,11 +12,7 @@
<ItemGroup>
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.8" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\FileService\FileServices.csproj" />
<ProjectReference Include="..\Qiniu\QiniuFileService.csproj" />
<PackageReference Include="Qiniu.FileService" Version="1.0.0-beta.1" />
</ItemGroup>