UNPKG

delta-sync

Version:

A lightweight framework for bi-directional database synchronization with automatic version tracking and conflict resolution.

285 lines (284 loc) 11.9 kB
/** * 适配器测试工具 - 用于测试任何实现了DatabaseAdapter接口的适配器 */ export class AdapterTester { constructor(adapter, testStoreName) { this.testStoreName = 'adapter_test'; this.testFileContent = 'Hello, this is a test file content!'; this.adapter = adapter; if (testStoreName) { this.testStoreName = testStoreName; } } /** * 运行所有测试 */ async runAllTests() { console.log('=== 开始适配器测试 ==='); const results = {}; let allSuccess = true; try { // 测试初始化 results.initialization = await this.testInitialization(); allSuccess = allSuccess && results.initialization.success; // 测试可用性 results.availability = await this.testAvailability(); allSuccess = allSuccess && results.availability.success; // 测试基本CRUD操作 results.basicCrud = await this.testBasicCrud(); allSuccess = allSuccess && results.basicCrud.success; // 测试批量操作 results.bulkOperations = await this.testBulkOperations(); allSuccess = allSuccess && results.bulkOperations.success; // 测试文件操作 results.fileOperations = await this.testFileOperations(); allSuccess = allSuccess && results.fileOperations.success; console.log('=== 适配器测试完成 ==='); if (allSuccess) { console.log('✅ 所有测试通过'); } else { console.log('❌ 部分测试失败'); } // 输出详细结果 Object.entries(results).forEach(([testName, result]) => { console.log(`${result.success ? '✅' : '❌'} ${testName}: ${result.message}`); }); return { success: allSuccess, results }; } catch (error) { console.error('测试过程中出现未捕获的错误:', error); return { success: false, results: { ...results, uncaughtError: { success: false, message: `未捕获错误: ${error instanceof Error ? error.message : String(error)}` } } }; } } /** * 测试初始化功能 */ async testInitialization() { try { console.log('测试初始化...'); await this.adapter.initSync(); return { success: true, message: '初始化成功' }; } catch (error) { console.error('初始化失败:', error); return { success: false, message: `初始化失败: ${error instanceof Error ? error.message : String(error)}` }; } } /** * 测试可用性检查 */ async testAvailability() { try { console.log('测试可用性...'); const available = await this.adapter.isAvailable(); if (available) { return { success: true, message: '适配器可用' }; } else { return { success: false, message: '适配器不可用' }; } } catch (error) { console.error('可用性检查失败:', error); return { success: false, message: `可用性检查失败: ${error instanceof Error ? error.message : String(error)}` }; } } /** * 测试基本的CRUD操作 */ async testBasicCrud() { try { console.log('测试基本CRUD操作...'); // 创建测试项目 const testItem = { _delta_id: `test_item_${Date.now()}`, _sync_status: 'pending', _store: this.testStoreName, _ver: Date.now() }; // 写入 console.log('测试写入操作...'); const writeResult = await this.adapter.putBulk(this.testStoreName, [testItem]); if (!writeResult || writeResult.length !== 1) { return { success: false, message: '写入操作失败' }; } // 读取 console.log('测试读取操作...'); const readResult = await this.adapter.readBulk(this.testStoreName, [testItem._delta_id]); if (!readResult || readResult.length !== 1 || readResult[0]._delta_id !== testItem._delta_id) { return { success: false, message: '读取操作失败' }; } // 删除 console.log('测试删除操作...'); await this.adapter.deleteBulk(this.testStoreName, [testItem._delta_id]); // 验证删除 const afterDeleteResult = await this.adapter.readBulk(this.testStoreName, [testItem._delta_id]); if (afterDeleteResult && afterDeleteResult.length > 0) { return { success: false, message: '删除操作失败' }; } return { success: true, message: '基本CRUD操作测试通过' }; } catch (error) { console.error('CRUD测试失败:', error); return { success: false, message: `CRUD测试失败: ${error instanceof Error ? error.message : String(error)}` }; } } /** * 测试批量操作 */ async testBulkOperations() { try { console.log('测试批量操作...'); // 创建多个测试项目 const testItems = Array(5).fill(0).map((_, index) => ({ _delta_id: `bulk_test_${Date.now()}_${index}`, _sync_status: 'pending', _store: this.testStoreName, _ver: Date.now(), testValue: `测试值 ${index}` })); // 批量写入 console.log('测试批量写入...'); const writeResult = await this.adapter.putBulk(this.testStoreName, testItems); if (!writeResult || writeResult.length !== testItems.length) { return { success: false, message: '批量写入失败' }; } // 批量读取 console.log('测试批量读取...'); const ids = testItems.map(item => item._delta_id); const readResult = await this.adapter.readBulk(this.testStoreName, ids); if (!readResult || readResult.length !== ids.length) { return { success: false, message: '批量读取失败' }; } // 测试分页读取 console.log('测试分页读取...'); const pageResult = await this.adapter.read(this.testStoreName, { limit: 3, offset: 0 }); if (!pageResult || !pageResult.items) { return { success: false, message: '分页读取失败' }; } // 批量删除 console.log('测试批量删除...'); await this.adapter.deleteBulk(this.testStoreName, ids); // 验证批量删除 const afterDeleteResult = await this.adapter.readBulk(this.testStoreName, ids); if (afterDeleteResult && afterDeleteResult.length > 0) { return { success: false, message: '批量删除失败' }; } return { success: true, message: '批量操作测试通过' }; } catch (error) { console.error('批量操作测试失败:', error); return { success: false, message: `批量操作测试失败: ${error instanceof Error ? error.message : String(error)}` }; } } /** * 测试文件操作 */ async testFileOperations() { try { console.log('测试文件操作...'); // 测试文件ID const testFileId = `test_file_${Date.now()}`; // 测试纯文本文件上传 console.log('测试文本文件上传...'); const textBlob = new Blob([this.testFileContent], { type: 'text/plain' }); const saveResult = await this.adapter.saveFile(textBlob, testFileId); if (!saveResult || saveResult.id !== testFileId) { return { success: false, message: `文件上传失败: ID不匹配,预期=${testFileId},实际=${saveResult?.id || '未返回ID'}` }; } // 测试文件下载 console.log('测试文件下载...'); const downloadResult = await this.adapter.readFile(testFileId); if (!downloadResult) { return { success: false, message: '文件下载失败: 未返回内容' }; } // 验证文件内容 console.log('验证文件内容...'); let contentMatch = false; if (downloadResult instanceof Blob) { const text = await downloadResult.text(); contentMatch = text === this.testFileContent; } else if (downloadResult instanceof ArrayBuffer) { const text = new TextDecoder().decode(downloadResult); contentMatch = text === this.testFileContent; } if (!contentMatch) { return { success: false, message: '文件内容验证失败: 内容不匹配' }; } // 测试文件删除 console.log('测试文件删除...'); await this.adapter.deleteFile(testFileId); // 验证文件是否已删除 let fileDeleted = false; try { await this.adapter.readFile(testFileId); } catch (error) { fileDeleted = true; } if (!fileDeleted) { return { success: false, message: '文件删除验证失败: 文件仍然存在' }; } // 测试二进制文件 console.log('测试二进制文件上传和下载...'); const binaryFileId = `binary_test_${Date.now()}`; const binaryData = new Uint8Array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); const binaryBlob = new Blob([binaryData], { type: 'application/octet-stream' }); await this.adapter.saveFile(binaryBlob, binaryFileId); const binaryResult = await this.adapter.readFile(binaryFileId); if (!binaryResult) { return { success: false, message: '二进制文件测试失败: 未能读取文件' }; } // 清理 await this.adapter.deleteFile(binaryFileId); // 测试Base64文件 console.log('测试Base64文件上传...'); const base64FileId = `base64_test_${Date.now()}`; const base64Content = 'data:text/plain;base64,SGVsbG8gV29ybGQh'; // "Hello World!" in base64 await this.adapter.saveFile(base64Content, base64FileId); const base64Result = await this.adapter.readFile(base64FileId); if (!base64Result) { return { success: false, message: 'Base64文件测试失败: 未能读取文件' }; } // 清理 await this.adapter.deleteFile(base64FileId); return { success: true, message: '文件操作测试通过' }; } catch (error) { console.error('文件操作测试失败:', error); return { success: false, message: `文件操作测试失败: ${error instanceof Error ? error.message : String(error)}` }; } } }