172 lines
5.9 KiB
C#
172 lines
5.9 KiB
C#
using System;
|
|
using System.IO;
|
|
using System.Net;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
using WebDav;
|
|
|
|
namespace Ink_Canvas.Helpers
|
|
{
|
|
/// <summary>
|
|
/// WebDav上传工具类
|
|
/// </summary>
|
|
public static class WebDavUploader
|
|
{
|
|
/// <summary>
|
|
/// 上传文件到WebDav服务器
|
|
/// </summary>
|
|
/// <param name="filePath">文件路径</param>
|
|
/// <param name="cancellationToken">取消令牌</param>
|
|
/// <returns>是否上传成功</returns>
|
|
public static async Task<bool> UploadFileAsync(string filePath, CancellationToken cancellationToken = default)
|
|
{
|
|
try
|
|
{
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
|
|
// 检查文件是否存在
|
|
if (!File.Exists(filePath))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
// 获取WebDav设置
|
|
var webDavUrl = MainWindow.Settings?.Dlass?.WebDavUrl;
|
|
var username = MainWindow.Settings?.Dlass?.WebDavUsername;
|
|
var password = MainWindow.Settings?.Dlass?.WebDavPassword;
|
|
var rootDirectory = MainWindow.Settings?.Dlass?.WebDavRootDirectory;
|
|
|
|
// 验证设置
|
|
if (string.IsNullOrEmpty(webDavUrl))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
// 构建完整的目标路径
|
|
var fileName = Path.GetFileName(filePath);
|
|
var targetPath = Path.Combine(rootDirectory ?? string.Empty, fileName).Replace("\\", "/");
|
|
if (targetPath.StartsWith("/"))
|
|
{
|
|
targetPath = targetPath.Substring(1);
|
|
}
|
|
|
|
// 创建WebDav客户端
|
|
var clientParams = new WebDavClientParams
|
|
{
|
|
BaseAddress = new Uri(webDavUrl),
|
|
Credentials = new NetworkCredential(username ?? string.Empty, password ?? string.Empty)
|
|
};
|
|
|
|
using (var client = new WebDavClient(clientParams))
|
|
{
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
|
|
// 先直接尝试上传文件
|
|
using (var fileStream = File.OpenRead(filePath))
|
|
{
|
|
// 检查取消令牌
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
|
|
var result = await client.PutFile(targetPath, fileStream);
|
|
if (result.IsSuccessful)
|
|
{
|
|
return true;
|
|
}
|
|
else
|
|
{
|
|
// 上传失败,尝试创建目录
|
|
var directoryPath = Path.GetDirectoryName(targetPath);
|
|
if (!string.IsNullOrEmpty(directoryPath))
|
|
{
|
|
await EnsureDirectoryExistsAsync(client, directoryPath, cancellationToken);
|
|
|
|
// 再次尝试上传文件
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
using (var retryStream = File.OpenRead(filePath))
|
|
{
|
|
var retryResult = await client.PutFile(targetPath, retryStream);
|
|
return retryResult.IsSuccessful;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// 没有目录路径,直接返回失败
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
catch (OperationCanceledException)
|
|
{
|
|
throw;
|
|
}
|
|
catch (Exception)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 确保WebDav目录存在
|
|
/// </summary>
|
|
/// <param name="client">WebDav客户端</param>
|
|
/// <param name="directoryPath">目录路径</param>
|
|
/// <param name="cancellationToken">取消令牌</param>
|
|
private static async Task EnsureDirectoryExistsAsync(IWebDavClient client, string directoryPath, CancellationToken cancellationToken)
|
|
{
|
|
try
|
|
{
|
|
// 分割路径并逐级创建目录
|
|
var pathParts = directoryPath.Split('/');
|
|
var currentPath = string.Empty;
|
|
|
|
foreach (var part in pathParts)
|
|
{
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
|
|
if (string.IsNullOrEmpty(part))
|
|
continue;
|
|
|
|
currentPath = Path.Combine(currentPath, part).Replace("\\", "/");
|
|
|
|
// 检查取消令牌
|
|
cancellationToken.ThrowIfCancellationRequested();
|
|
|
|
// 尝试创建目录
|
|
await client.Mkcol(currentPath);
|
|
}
|
|
}
|
|
catch (Exception)
|
|
{
|
|
// 静默处理目录创建错误
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 检查WebDAV是否已启用
|
|
/// </summary>
|
|
/// <returns>是否启用</returns>
|
|
public static bool IsWebDavEnabled()
|
|
{
|
|
// 检查WebDav设置是否有效
|
|
var webDavUrl = MainWindow.Settings?.Dlass?.WebDavUrl;
|
|
if (string.IsNullOrEmpty(webDavUrl))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
// 尝试解析URL
|
|
try
|
|
{
|
|
new Uri(webDavUrl);
|
|
return true;
|
|
}
|
|
catch
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
}
|