mirror of
https://github.com/Awuqing/BackupX.git
synced 2026-07-12 16:02:18 +08:00
功能: 集成 rclone 高级传输特性 + 全 70+ 后端支持
1. 失败自动重试:rclone Pacer 指数退避,默认 10 次底层 HTTP 重试 2. 带宽限制:配置 bandwidth_limit + Settings 运行时可调 3. 上传实时进度:progressReader + LogHub SSE 推送字节级进度/速率 4. 存储空间查询:StorageAbout 可选接口,GetUsage 返回远端真实空间 5. 全 rclone 后端:backend/all 引入 70+ 后端,新增 rclone 存储类型, API 驱动的可搜索后端选择器 + 动态配置表单
This commit is contained in:
@@ -110,6 +110,79 @@ func TestBuildS3Remote(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestRcloneFactoryCRUD(t *testing.T) {
|
||||
dir := t.TempDir()
|
||||
factory := NewRcloneFactory()
|
||||
// 使用 rclone 的 local 后端
|
||||
provider, err := factory.New(context.Background(), map[string]any{
|
||||
"backend": "local",
|
||||
"root": dir,
|
||||
})
|
||||
if err != nil {
|
||||
t.Fatalf("RcloneFactory.New returned error: %v", err)
|
||||
}
|
||||
if err := provider.Upload(context.Background(), "test.txt", strings.NewReader("rclone"), 6, nil); err != nil {
|
||||
t.Fatalf("Upload via rclone factory returned error: %v", err)
|
||||
}
|
||||
reader, err := provider.Download(context.Background(), "test.txt")
|
||||
if err != nil {
|
||||
t.Fatalf("Download returned error: %v", err)
|
||||
}
|
||||
defer reader.Close()
|
||||
content, _ := io.ReadAll(reader)
|
||||
if string(content) != "rclone" {
|
||||
t.Fatalf("expected 'rclone', got %q", string(content))
|
||||
}
|
||||
if err := provider.Delete(context.Background(), "test.txt"); err != nil {
|
||||
t.Fatalf("Delete returned error: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestRcloneFactoryRequiresBackend(t *testing.T) {
|
||||
_, err := NewRcloneFactory().New(context.Background(), map[string]any{"root": "/tmp"})
|
||||
if err == nil || !strings.Contains(err.Error(), "backend") {
|
||||
t.Fatalf("expected backend required error, got %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestListBackends(t *testing.T) {
|
||||
backends := ListBackends()
|
||||
if len(backends) < 30 {
|
||||
t.Fatalf("expected at least 30 backends, got %d", len(backends))
|
||||
}
|
||||
// 确认 sftp 在列表中
|
||||
found := false
|
||||
for _, b := range backends {
|
||||
if b.Name == "sftp" {
|
||||
found = true
|
||||
if len(b.Options) == 0 {
|
||||
t.Fatal("sftp backend should have options")
|
||||
}
|
||||
break
|
||||
}
|
||||
}
|
||||
if !found {
|
||||
t.Fatal("sftp backend not found in ListBackends()")
|
||||
}
|
||||
}
|
||||
|
||||
func TestProviderAbout(t *testing.T) {
|
||||
factory := NewLocalDiskFactory()
|
||||
provider, err := factory.New(context.Background(), map[string]any{"basePath": t.TempDir()})
|
||||
if err != nil {
|
||||
t.Fatalf("Factory.New returned error: %v", err)
|
||||
}
|
||||
// local 后端支持 About
|
||||
rcloneProvider := provider.(*Provider)
|
||||
usage, err := rcloneProvider.About(context.Background())
|
||||
if err != nil {
|
||||
t.Fatalf("About returned error: %v", err)
|
||||
}
|
||||
if usage.Total == nil || *usage.Total <= 0 {
|
||||
t.Fatalf("expected non-zero total disk space, got %v", usage.Total)
|
||||
}
|
||||
}
|
||||
|
||||
func TestPathDir(t *testing.T) {
|
||||
tests := []struct {
|
||||
input string
|
||||
|
||||
Reference in New Issue
Block a user