# CloudSystem **Repository Path**: half-intermediate-mangfu/cloud-system ## Basic Information - **Project Name**: CloudSystem - **Description**: 项目名称: 云备份 实现将本地特定目录中需要备份的文件进行上传至对应的服务器当中; 当用户运行客户端时客户端将在既定的路径中创建一个目录,该文件夹即为与云备份相连的文件夹,文件进入文件夹则视为上传至服务器; 通过服务器IP地址对应端口可以访问该服务的Html网页; 用户能够通过浏览器对文件进行下载与查看,下载过程中支持断点续传; 服务器对所上传文件进行热点管理; - **Primary Language**: C++ - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-01-09 - **Last Updated**: 2026-01-14 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 云备份系统 (Cloud Backup System) 一个基于 C++14 的分布式文件备份系统,实现本地文件自动备份至云端服务器,支持浏览器查看与下载、断点续传,以及智能热点文件管理。 ## 项目特性 - **自动备份**: 客户端自动监控指定目录,增量上传新增或修改的文件 - **断点续传**: 基于 ETag 机制实现下载中断后的续传功能 - **热点管理**: 服务端智能识别冷热数据,自动压缩长期未访问的文件以节省存储空间 - **Web 访问**: 通过浏览器即可查看文件列表并下载 - **跨平台**: 服务端支持 Linux,客户端支持 Windows - **高并发**: 采用读写锁机制保证多线程环境下的数据一致性 --- ## 技术栈 ### 开发环境 - **服务端**: Linux, GCC 7.3.1+, C++14 - **客户端**: Windows 11, Visual Studio 2017+, C++17 ### 核心依赖库 本项目基于以下第三方库构建: #### 1. httplib - HTTP 服务器/客户端库 - **用途**: 提供 HTTP 协议的服务端和客户端实现 - **特点**: C++11 单头文件库,跨平台,轻量级 - **在本项目中的使用**: - 服务端:使用 `httplib::Server` 搭建 HTTP 服务器,注册路由处理函数 - 客户端:使用 `httplib::Client` 发送文件上传请求 - 自动处理 HTTP 协议细节(请求解析、响应组装等) #### 2. jsoncpp - JSON 序列化/反序列化库 - **用途**: 处理 JSON 格式的数据交换 - **在本项目中的使用**: - 配置文件读取(`cloud.conf`) - 元数据持久化存储(`cloud.dat`) - 使用 `Json::Value` 存储结构化数据 - 使用 `Json::StreamWriter` 和 `Json::CharReader` 进行序列化/反序列化 #### 3. bundle - 多算法压缩库 - **用途**: 提供多种压缩算法的统一接口 - **支持算法**: LZIP, LZ4, ZSTD, BROTLI, LZMA 等 20+ 种算法 - **在本项目中的使用**: - 热点管理模块使用 LZIP 算法压缩冷数据 - 下载时自动解压缩 - 使用高级 API:`bundle::pack()` 和 `bundle::unpack()` #### 4. 其他依赖 - **pthread**: POSIX 线程库,用于多线程和读写锁 - **filesystem**: C++17 文件系统库,用于目录遍历和文件操作 ### 编译配置 ```cmake cmake_minimum_required(VERSION 3.10) project(CloudBackup) set(CMAKE_CXX_STANDARD 14) add_executable(cloud cloud.cpp bundle.cpp) target_link_libraries(cloud pthread stdc++fs jsoncpp) ``` --- ## 系统架构 ### 整体架构图 ```mermaid graph TD %% 定义样式类 classDef current fill:#e3f2fd,stroke:#2196f3,stroke-width:2px,color:black; classDef roadmap fill:#fff3e0,stroke:#ff9800,stroke-width:2px,stroke-dasharray: 5 5,color:black; classDef storage fill:#f3e5f5,stroke:#9c27b0,stroke-width:2px,color:black; classDef component fill:#ffffff,stroke:#607d8b,stroke-width:1px,color:black; %% --- 客户端层 --- subgraph Clients [Client Layer / 客户端层] direction LR CLI[CLI Client
Current]:::current Web[Browser Client
Current]:::current Qt[Qt GUI Client
Roadmap]:::roadmap end %% --- 协议层 --- Protocol((HTTP/HTTPS
Protocol)) Clients --> Protocol Protocol --> Server %% --- 服务端层 --- subgraph Server [Server Layer / 服务端层] direction TB %% 网络模块 subgraph NetModule [Network Service Module] Httplib[httplib Framework]:::component Endpoints[Endpoints:
/upload
/listshow
/download]:::component Httplib --- Endpoints end %% 业务逻辑 subgraph BizLayer [Business Logic Layer] UploadHand[Upload Handler]:::component DownloadHand[Download Handler]:::component end %% 数据管理 (核心亮点) subgraph DataModule [Data Management Module] direction TB Interface[Metadata Interface]:::component FS_Meta[Current: File System
Legacy]:::current MySQL[Target: MySQL DB
Active Integration]:::roadmap Interface --> FS_Meta Interface -.-> MySQL end NetModule --> BizLayer BizLayer --> DataModule end %% --- 存储层 --- subgraph StorageLayer [Storage Layer / 存储层] direction TB HotData[backdir/
Hot Data]:::storage ColdData[packdir/
Cold Data]:::storage end %% --- 后台线程 --- Thread([Hot Data Management Thread
Compression Task]):::storage %% 连线关系 FS_Meta --> HotData DataModule --> StorageLayer Thread -.->|Monitor & Compress| HotData Thread -.->|Move| ColdData ``` ### 服务端核心模块 #### 1. 配置管理模块 (Config Module) - **设计模式**: 线程安全单例(双检锁机制) - **职责**: 统一管理系统配置参数 - **实现**: 使用 jsoncpp 读取 `cloud.conf` 配置文件 #### 2. 数据管理模块 (Data Module) - **当前实现**: 基于文件系统的 JSON 持久化存储 - **数据结构**: ```cpp struct BackupInfo { bool pack_flag; // 压缩状态标识 size_t fsize; // 文件大小 time_t mtime; // 最后修改时间 time_t atime; // 最后访问时间(热点判断依据) string real_path; // 实际存储路径 string pack_path; // 压缩包路径 string url; // 下载 URL } ``` - **并发控制**: pthread 读写锁保证多线程安全 - **未来规划**: 迁移至 MySQL 以支持分布式部署和 ACID 特性 #### 3. 网络服务模块 (Service Module) 基于 httplib 库实现 HTTP 服务器,注册以下路由: - **文件上传**: `POST /upload` - 使用 httplib 的 `Server::Post()` 注册处理函数 - 通过 `Request::has_file()` 和 `Request::get_file_value()` 获取上传文件 - 保存至备份目录并更新元数据 - **文件列表**: `GET /listshow` 或 `GET /` - 使用 httplib 的 `Server::Get()` 注册处理函数 - 返回 HTML 页面展示所有备份文件 - 通过 `Response::set_content()` 设置响应内容 - **文件下载**: `GET /download/{filename}` - 支持 ETag 验证机制 - 实现断点续传(HTTP 206 Partial Content) - 自动解压缩冷数据 #### 4. 热点管理模块 (Hot Data Manager) - **工作机制**: 独立后台线程定期扫描 - **判断策略**: 基于文件最后访问时间(atime) - **压缩实现**: 使用 bundle 库的 LZIP 算法 - **处理流程**: 1. 遍历备份目录 2. 识别超过阈值未访问的文件 3. 调用 `bundle::pack(bundle::LZIP, data)` 压缩 4. 删除原文件,更新元数据 5. 下载时调用 `bundle::unpack(data)` 解压 #### 5. 工具类模块 (Utility Module) - **FileUtil**: 封装文件系统操作 - 文件属性获取(大小、时间戳) - 文件读写操作 - 目录遍历(使用 C++17 filesystem) - 压缩/解压缩接口(封装 bundle 库调用) - **JsonUtil**: 封装 jsoncpp 操作 - `Serialize()`: 使用 `Json::StreamWriter` 序列化 - `UnSerialize()`: 使用 `Json::CharReader` 反序列化 ### 客户端核心模块 #### 1. 数据管理模块 - **存储格式**: 文本格式(路径 + 文件标识) - **文件标识**: "文件名-大小-修改时间" - **用途**: 判断文件是否需要重新上传 #### 2. 文件监控模块 - **监控策略**: 定期扫描指定目录 - **上传判断**: - 新增文件(无备份记录) - 文件已修改(标识不匹配) - 排除正在写入的文件(修改时间 < 10秒) #### 3. 文件备份模块 - **上传实现**: 使用 httplib 的 `Client::Post()` 方法 - **数据封装**: 使用 `MultipartFormData` 结构体 - **字段约定**: 表单字段名必须为 "file" - **失败重试**: 下次扫描时自动重试 --- ## 快速开始 ### 服务端部署 1. **编译项目**: ```bash cd src mkdir Build && cd Build cmake .. make ``` 2. **配置服务**: 编辑 `cloud.conf`,设置服务器 IP 和端口: ```json { "hot_time": 30, "server_port": 8111, "server_ip": "0.0.0.0", "download_prefix": "/download/", "packfile_suffix": ".lz", "pack_dir": "./packdir/", "back_dir": "./backdir/", "backup_file": "./cloud.dat" } ``` 3. **启动服务**: ```bash ./cloud ``` 4. **访问服务**: 浏览器打开 `http://your-server-ip:8111/listshow` ### 客户端使用 1. **配置服务器地址**: 编辑 `ClientForWin/cloud.hpp`: ```cpp #define SERVER_ADDR "your-server-ip" #define SERVER_PORT 8111 ``` 2. **编译运行**: 使用 Visual Studio 2017+ 打开项目并编译 3. **自动备份**: 将需要备份的文件放入 `./backup/` 目录,客户端将自动上传 --- ## Known Issues & Limitations ### 当前架构的局限性 #### 1. 元数据存储瓶颈 - **现状**: 元数据存储依赖本地文件系统(JSON 格式) - **影响**: 在分布式部署场景下存在状态同步问题 - **解决方案**: 正在进行 MySQL 数据库集成(见 Roadmap) #### 2. 并发文件访问 - **现状**: 文件级别的并发控制尚未完全实现 - **影响**: 同时压缩和下载同一文件可能导致竞态条件 - **缓解措施**: 当前通过读写锁保护元数据访问 #### 3. 大文件内存占用 - **现状**: 文件内容一次性加载到内存 - **影响**: 处理大文件(>1GB)时内存占用较高 - **优化方向**: 实现流式传输机制 #### 4. 客户端交互体验 - **现状**: 仅提供命令行界面 - **影响**: 用户体验不够友好 - **改进计划**: 开发基于 Qt 的图形化客户端(见 Roadmap) --- ## Roadmap (路线图) ### Phase 1: 数据层重构 (Q1 2026) - [ ] **迁移至 MySQL 数据库** - 实现 ACID 事务保证数据一致性 - 支持分布式部署和主从复制 - 提升元数据查询性能 - 设计数据库 Schema 和索引优化 - [ ] **引入连接池机制** - 减少数据库连接开销 - 提升高并发场景下的性能 ### Phase 2: 性能优化 (Q2 2026) - [ ] **实现流式文件传输** - 降低大文件处理的内存占用 - 支持更大文件的备份(10GB+) - 利用 httplib 的流式 API - [ ] **文件级并发控制** - 实现文件锁机制 - 避免压缩和下载的竞态条件 - [ ] **压缩算法可配置** - 支持多种压缩算法切换(LZ4/ZSTD/LZIP) - 根据文件类型自动选择最优算法 - 充分利用 bundle 库的多算法支持 ### Phase 3: 客户端增强 (Q3 2026) - [ ] **开发 Qt 跨平台 GUI 客户端** - 可视化文件管理界面 - 实时备份进度显示 - 支持 Windows/Linux/macOS - [ ] **增量备份优化** - 实现文件块级别的差异检测 - 仅上传修改的文件块 ### Phase 4: 企业级特性 (Q4 2026) - [ ] **用户认证与权限管理** - 多用户支持 - 基于角色的访问控制(RBAC) - [ ] **文件版本管理** - 保留文件历史版本 - 支持版本回滚 - [ ] **数据加密** - 传输层加密(HTTPS,利用 httplib 的 SSL 支持) - 存储层加密(AES-256) - [ ] **监控与告警** - 系统健康度监控 - 存储空间告警 - 备份失败通知 --- ## 核心功能实现 ### 断点续传机制 基于 HTTP 标准协议实现的断点续传功能: **首次下载流程**: 1. 客户端发起 GET 请求 2. 服务端返回完整文件 + ETag 头部 3. ETag 格式: "文件名-大小-修改时间" **续传流程**: 1. 客户端携带 `If-Range` 头部(上次的 ETag) 2. 客户端携带 `Range` 头部(需要的字节范围) 3. 服务端验证 ETag: - 匹配: 返回 206 Partial Content + 部分数据 - 不匹配: 返回 200 OK + 完整文件(文件已修改) **技术细节**: - httplib 自动处理 Range 头部解析 - 使用 `Response::set_header()` 设置 ETag 和 Content-Range - 返回状态码 206 表示部分内容 ### 热点数据管理 **冷热数据分离策略**: - **热数据**: 存储在 `backdir/`,保持原始格式,快速访问 - **冷数据**: 压缩存储在 `packdir/`,节省空间 **自动压缩流程**: ``` 定期扫描 → 判断访问时间 → bundle::pack() 压缩 → 删除原文件 → 更新元数据 ``` **自动解压流程**: ``` 下载请求 → 检测压缩标志 → bundle::unpack() 解压 → 删除压缩包 → 返回文件 ``` **压缩算法**: LZIP(高压缩比,适合长期存储) --- ## API 接口文档 ### 1. 文件上传 ```http POST /upload HTTP/1.1 Content-Type: multipart/form-data 字段名: file 文件名: example.txt 内容: [二进制数据] ``` **响应**: - 200 OK: 上传成功 - 400 Bad Request: 缺少 file 字段 ### 2. 文件列表 ```http GET /listshow HTTP/1.1 ``` **响应**: ```html
file.txt 2025-01-14 10:30:00 1024k
``` ### 3. 文件下载 ```http GET /download/example.txt HTTP/1.1 ``` **响应**: ```http HTTP/1.1 200 OK Accept-Ranges: bytes ETag: "example.txt-1024-1705132800" Content-Type: application/octet-stream [文件内容] ``` ### 4. 断点续传 ```http GET /download/example.txt HTTP/1.1 If-Range: "example.txt-1024-1705132800" Range: bytes=512-1023 ``` **响应**: ```http HTTP/1.1 206 Partial Content Content-Range: bytes 512-1023/1024 ETag: "example.txt-1024-1705132800" [部分内容] ``` --- ## 第三方库使用指南 ### httplib 使用示例 #### 服务端:搭建 HTTP 服务器 ```cpp #include "httplib.h" void HandleUpload(const httplib::Request &req, httplib::Response &rsp) { // 检查是否有文件上传 if (!req.has_file("file")) { rsp.status = 400; return; } // 获取文件内容 const auto& file = req.get_file_value("file"); // 处理文件... rsp.status = 200; } int main() { httplib::Server server; // 注册路由 server.Post("/upload", HandleUpload); // 启动服务器 server.listen("0.0.0.0", 8111); return 0; } ``` #### 客户端:发送 HTTP 请求 ```cpp #include "httplib.h" int main() { // 创建客户端 httplib::Client client("192.168.1.100", 8111); // 准备上传数据 httplib::MultipartFormData item; item.name = "file"; item.filename = "example.txt"; item.content = "Hello World"; item.content_type = "text/plain"; httplib::MultipartFormDataItems items; items.push_back(item); // 发送 POST 请求 auto res = client.Post("/upload", items); if (res && res->status == 200) { std::cout << "上传成功" << std::endl; } return 0; } ``` ### jsoncpp 使用示例 #### 序列化 ```cpp #include // 创建 JSON 对象 Json::Value root; root["name"] = "张三"; root["age"] = 18; root["scores"].append(88); root["scores"].append(89); root["scores"].append(90); // 序列化为字符串 Json::StreamWriterBuilder builder; std::unique_ptr writer(builder.newStreamWriter()); std::stringstream ss; writer->write(root, &ss); std::string json_str = ss.str(); ``` #### 反序列化 ```cpp #include std::string json_str = "{\"name\":\"张三\",\"age\":18}"; // 反序列化 Json::Value root; Json::CharReaderBuilder builder; std::unique_ptr reader(builder.newCharReader()); std::string errors; bool success = reader->parse( json_str.c_str(), json_str.c_str() + json_str.size(), &root, &errors ); if (success) { std::string name = root["name"].asString(); int age = root["age"].asInt(); } ``` ### bundle 使用示例 #### 压缩文件 ```cpp #include "bundle.h" // 读取文件内容 std::ifstream ifs("input.txt", std::ios::binary); std::string original((std::istreambuf_iterator(ifs)), std::istreambuf_iterator()); // 压缩(使用 LZIP 算法) std::string compressed = bundle::pack(bundle::LZIP, original); // 写入压缩文件 std::ofstream ofs("output.lz", std::ios::binary); ofs.write(compressed.data(), compressed.size()); ``` #### 解压文件 ```cpp #include "bundle.h" // 读取压缩文件 std::ifstream ifs("output.lz", std::ios::binary); std::string compressed((std::istreambuf_iterator(ifs)), std::istreambuf_iterator()); // 解压 std::string original = bundle::unpack(compressed); // 写入原始文件 std::ofstream ofs("output.txt", std::ios::binary); ofs.write(original.data(), original.size()); ``` #### bundle 支持的压缩算法 ```cpp // 可用的压缩算法 vector algorithms { bundle::RAW, // 无压缩 bundle::SHOCO, // 短字符串压缩 bundle::LZ4F, // 快速压缩 bundle::LZ4, // 快速压缩(高压缩比版本) bundle::MINIZ, // DEFLATE 算法 bundle::LZIP, // 高压缩比(本项目使用) bundle::LZMA20, // LZMA 算法 bundle::LZMA25, // LZMA 算法(更高压缩比) bundle::ZSTD, // Facebook 的 Zstandard bundle::BROTLI9, // Google 的 Brotli bundle::BROTLI11, // Brotli(最高压缩比) bundle::BSC, // 块排序压缩 bundle::ZPAQ // 最高压缩比(最慢) }; // 使用示例 std::string packed = bundle::pack(bundle::ZSTD, data); std::string unpacked = bundle::unpack(packed); ``` --- ## 项目结构 ``` cloud-system/ ├── src/ # 服务端源码 │ ├── cloud.cpp # 主程序入口 │ ├── config.hpp # 配置管理模块 │ ├── data.hpp # 数据管理模块 │ ├── hot.hpp # 热点管理模块 │ ├── service.hpp # 网络服务模块 │ ├── util.hpp # 工具类模块 │ ├── bundle.h/cpp # bundle 压缩库 │ ├── httplib.h # httplib 网络库 │ ├── cloud.conf # 配置文件 │ └── CMakeLists.txt # 编译配置 │ ├── ClientForWin/ # Windows 客户端源码 │ ├── cloud.cpp # 客户端主程序 │ ├── cloud.hpp # 备份模块 │ ├── data.hpp # 数据管理模块 │ ├── util.hpp # 工具类模块 │ ├── httplib.h # httplib 网络库 │ └── integration.h # 集成头文件 │ ├── example/ # 示例代码 │ ├── BundleTest/ # bundle 库测试 │ ├── JsonTest/ # jsoncpp 库测试 │ ├── HttpLibTest/ # httplib 库测试 │ └── FileSystemTest/ # 文件系统测试 │ └── README.md # 项目文档 ``` --- ## 贡献指南 欢迎提交 Issue 和 Pull Request! ### 开发建议 1. 遵循 C++14/17 标准 2. 使用统一的代码风格 3. 添加必要的注释 4. 编写单元测试 ### 提交规范 - feat: 新功能 - fix: 修复 bug - docs: 文档更新 - refactor: 代码重构 - test: 测试相关 --- ## 许可证 本项目采用 MIT 许可证。 --- ## 联系方式 如有问题或建议,欢迎通过 Issue 联系。