diff --git a/backend/build-docker-fixed.sh b/backend/build-docker-fixed.sh
deleted file mode 100644
index f316619..0000000
--- a/backend/build-docker-fixed.sh
+++ /dev/null
@@ -1,369 +0,0 @@
-#!/bin/bash
-
-# 云盘应用 Docker 构建和部署脚本 (修复权限问题版本)
-# 用于构建生产环境的 Docker 镜像并部署到 Linux 环境
-
-set -e
-
-# 配置变量
-APP_NAME="cloud-drive-backend"
-IMAGE_NAME="${APP_NAME}:latest"
-CONTAINER_NAME="${APP_NAME}"
-PORT="8002"
-USE_SUDO=false
-
-# Docker命令包装函数
-docker_cmd() {
- if [ "$USE_SUDO" = true ]; then
- sudo docker "$@"
- else
- docker "$@"
- fi
-}
-
-# Docker Compose命令包装函数
-docker_compose_cmd() {
- if [ "$USE_SUDO" = true ]; then
- sudo docker-compose "$@"
- else
- docker-compose "$@"
- fi
-}
-
-# 颜色输出
-RED='\033[0;31m'
-GREEN='\033[0;32m'
-YELLOW='\033[1;33m'
-BLUE='\033[0;34m'
-NC='\033[0m' # No Color
-
-# 日志函数
-log_info() {
- echo -e "${BLUE}[INFO]${NC} $1"
-}
-
-log_success() {
- echo -e "${GREEN}[SUCCESS]${NC} $1"
-}
-
-log_warning() {
- echo -e "${YELLOW}[WARNING]${NC} $1"
-}
-
-log_error() {
- echo -e "${RED}[ERROR]${NC} $1"
-}
-
-# 检查 Docker 是否安装
-check_docker() {
- if ! command -v docker &> /dev/null; then
- log_error "Docker 未安装,请先安装 Docker"
- exit 1
- fi
-
- # 检查Docker权限
- if ! docker info &> /dev/null; then
- log_warning "Docker权限不足,尝试修复..."
-
- # 检查当前用户是否在docker组中
- if ! groups $(whoami) | grep -q docker; then
- log_warning "当前用户不在docker组中"
-
- # 尝试将用户添加到docker组
- if command -v sudo &> /dev/null; then
- log_info "尝试将用户添加到docker组(需要sudo权限)..."
- sudo usermod -aG docker $(whoami) 2>/dev/null || {
- log_warning "无法自动添加用户到docker组"
- log_info "请手动执行: sudo usermod -aG docker $(whoami)"
- log_info "然后重新登录或执行: newgrp docker"
- }
- else
- log_error "sudo命令不可用,无法修复Docker权限"
- fi
- fi
-
- # 尝试使用sudo运行docker
- if command -v sudo &> /dev/null && sudo docker info &> /dev/null; then
- log_info "检测到可以使用sudo运行Docker"
- USE_SUDO=true
- else
- log_error "Docker权限不足且无法修复"
- log_info "解决方案:"
- log_info "1. 将用户添加到docker组: sudo usermod -aG docker $(whoami)"
- log_info "2. 重新登录或执行: newgrp docker"
- log_info "3. 或使用sudo运行此脚本"
- exit 1
- fi
- fi
-
- log_success "Docker 已安装并可访问"
-}
-
-# 检查 Docker Compose 是否安装
-check_docker_compose() {
- if ! command -v docker-compose &> /dev/null; then
- log_error "Docker Compose 未安装,请先安装 Docker Compose"
- exit 1
- fi
- log_success "Docker Compose 已安装"
-}
-
-# 停止并删除现有容器
-stop_existing_container() {
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- log_warning "停止现有容器 ${CONTAINER_NAME}"
- docker_cmd stop ${CONTAINER_NAME}
- fi
-
- if docker_cmd ps -aq -f name=${CONTAINER_NAME} | grep -q .; then
- log_warning "删除现有容器 ${CONTAINER_NAME}"
- docker_cmd rm ${CONTAINER_NAME}
- fi
-}
-
-# 构建镜像
-build_image() {
- log_info "开始构建 Docker 镜像..."
- docker_cmd build -t ${IMAGE_NAME} .
-
- if [ $? -eq 0 ]; then
- log_success "镜像构建成功: ${IMAGE_NAME}"
- else
- log_error "镜像构建失败"
- exit 1
- fi
-}
-
-# 运行容器
-run_container() {
- log_info "启动容器..."
-
- # 创建必要的目录
- mkdir -p uploads logs
-
- docker_cmd run -d \
- --name ${CONTAINER_NAME} \
- --restart unless-stopped \
- -p ${PORT}:${PORT} \
- -v $(pwd)/uploads:/app/uploads \
- -v $(pwd)/logs:/app/logs \
- -e ENVIRONMENT=production \
- -e TZ=Asia/Shanghai \
- ${IMAGE_NAME}
-
- if [ $? -eq 0 ]; then
- log_success "容器启动成功: ${CONTAINER_NAME}"
- else
- log_error "容器启动失败"
- exit 1
- fi
-}
-
-# 检查容器状态
-check_container() {
- log_info "检查容器状态..."
- sleep 5
-
- if docker_cmd ps | grep -q ${CONTAINER_NAME}; then
- log_success "容器运行正常"
-
- # 显示容器日志
- log_info "容器日志:"
- docker_cmd logs ${CONTAINER_NAME}
-
- # 测试健康检查
- log_info "测试健康检查..."
- sleep 10
- if curl -f http://localhost:${PORT}/api/v1/health &> /dev/null; then
- log_success "健康检查通过!"
- else
- log_warning "健康检查失败,但容器仍在运行"
- fi
- else
- log_error "容器未正常运行"
- log_error "容器日志:"
- docker_cmd logs ${CONTAINER_NAME}
- exit 1
- fi
-}
-
-# 使用 Docker Compose 部署
-deploy_with_compose() {
- log_info "使用 Docker Compose 部署..."
-
- # 创建 .env 文件(如果不存在)
- if [ ! -f .env ]; then
- log_warning "创建 .env 文件,请根据实际情况修改配置"
- cat > .env << EOF
-# 数据库配置
-DATABASE_URL=mysql://username:password@mysql:3306/mytest_db
-MYSQL_ROOT_PASSWORD=rootpassword
-MYSQL_DATABASE=mytest_db
-MYSQL_USER=username
-MYSQL_PASSWORD=password
-
-# Redis 配置
-REDIS_URL=redis://redis:6379/0
-
-# 应用配置
-SECRET_KEY=your-production-secret-key
-CORS_ORIGINS=http://localhost:3003,https://yourdomain.com
-ENVIRONMENT=production
-EOF
- log_warning "请编辑 .env 文件设置正确的配置"
- fi
-
- docker_compose_cmd down
- docker_compose_cmd up -d --build
-
- if [ $? -eq 0 ]; then
- log_success "Docker Compose 部署成功"
- log_info "等待服务启动..."
- sleep 15
-
- if curl -f http://localhost:${PORT}/api/v1/health &> /dev/null; then
- log_success "应用启动成功!"
- log_info "服务地址: http://localhost:${PORT}"
- log_info "API文档: http://localhost:${PORT}/docs"
- log_info "健康检查: http://localhost:${PORT}/api/v1/health"
- else
- log_warning "应用启动可能有问题,请检查日志"
- log_info "查看日志命令: docker-compose logs -f"
- docker_compose_cmd logs --tail=20
- fi
- else
- log_error "Docker Compose 部署失败"
- exit 1
- fi
-}
-
-# 清理镜像和容器
-cleanup() {
- log_info "清理旧的镜像和容器..."
-
- # 停止并删除容器
- stop_existing_container
-
- # 删除镜像
- if docker_cmd images -q ${IMAGE_NAME} | grep -q .; then
- log_warning "删除旧镜像: ${IMAGE_NAME}"
- docker_cmd rmi ${IMAGE_NAME} 2>/dev/null || true
- fi
-
- # 清理未使用的镜像和容器
- log_info "清理未使用的 Docker 资源..."
- docker_cmd system prune -f
-
- log_success "清理完成"
-}
-
-# 显示帮助信息
-show_help() {
- echo "云盘应用 Docker 部署脚本 (权限修复版)"
- echo ""
- echo "用法: $0 [选项]"
- echo ""
- echo "选项:"
- echo " build - 仅构建镜像"
- echo " run - 仅运行容器(需要先构建镜像)"
- echo " compose - 使用 Docker Compose 部署"
- echo " stop - 停止容器"
- echo " restart - 重启容器"
- echo " logs - 查看容器日志"
- echo " cleanup - 清理镜像和容器"
- echo " status - 查看容器状态"
- echo " help - 显示此帮助信息"
- echo ""
- echo "默认行为: 构建镜像并运行容器"
- echo ""
- echo "权限修复功能:"
- echo "- 自动检测Docker权限"
- echo "- 尝试自动修复权限问题"
- echo "- 支持sudo模式运行Docker"
-}
-
-# 主函数
-main() {
- case "${1:-}" in
- "build")
- check_docker
- build_image
- ;;
- "run")
- check_docker
- stop_existing_container
- run_container
- check_container
- ;;
- "compose")
- check_docker
- check_docker_compose
- deploy_with_compose
- ;;
- "stop")
- check_docker
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker_cmd stop ${CONTAINER_NAME}
- log_success "容器已停止"
- else
- log_warning "容器未运行"
- fi
- ;;
- "restart")
- check_docker
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker_cmd restart ${CONTAINER_NAME}
- log_success "容器已重启"
- sleep 5
- check_container
- else
- log_warning "容器未运行,尝试启动..."
- stop_existing_container
- build_image
- run_container
- check_container
- fi
- ;;
- "logs")
- check_docker
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker_cmd logs -f ${CONTAINER_NAME}
- else
- log_warning "容器未运行"
- fi
- ;;
- "cleanup")
- check_docker
- cleanup
- ;;
- "status")
- check_docker
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- log_success "容器正在运行"
- docker_cmd ps | grep ${CONTAINER_NAME}
- else
- log_warning "容器未运行"
- fi
- ;;
- "help"|"-h"|"--help")
- show_help
- ;;
- "")
- log_info "开始构建和部署云盘应用..."
- check_docker
- stop_existing_container
- build_image
- run_container
- check_container
- log_success "部署完成!应用正在运行中"
- ;;
- *)
- log_error "未知选项: $1"
- show_help
- exit 1
- ;;
- esac
-}
-
-# 执行主函数
-main "$@"
\ No newline at end of file
diff --git a/backend/build-docker.sh b/backend/build-docker.sh
deleted file mode 100644
index 0c0c16c..0000000
--- a/backend/build-docker.sh
+++ /dev/null
@@ -1,360 +0,0 @@
-#!/bin/bash
-
-# 云盘应用 Docker 构建和部署脚本
-# 用于构建生产环境的 Docker 镜像并部署到 Linux 环境
-
-set -e
-
-# 配置变量
-APP_NAME="cloud-drive-backend"
-IMAGE_NAME="${APP_NAME}:latest"
-CONTAINER_NAME="${APP_NAME}"
-PORT="8002"
-USE_SUDO=false
-
-# Docker命令包装函数
-docker_cmd() {
- if [ "$USE_SUDO" = true ]; then
- sudo docker "$@"
- else
- docker "$@"
- fi
-}
-
-# Docker Compose命令包装函数
-docker_compose_cmd() {
- if [ "$USE_SUDO" = true ]; then
- sudo docker-compose "$@"
- else
- docker-compose "$@"
- fi
-}
-
-# 颜色输出
-RED='\033[0;31m'
-GREEN='\033[0;32m'
-YELLOW='\033[1;33m'
-BLUE='\033[0;34m'
-NC='\033[0m' # No Color
-
-# 日志函数
-log_info() {
- echo -e "${BLUE}[INFO]${NC} $1"
-}
-
-log_success() {
- echo -e "${GREEN}[SUCCESS]${NC} $1"
-}
-
-log_warning() {
- echo -e "${YELLOW}[WARNING]${NC} $1"
-}
-
-log_error() {
- echo -e "${RED}[ERROR]${NC} $1"
-}
-
-# 检查 Docker 是否安装
-check_docker() {
- if ! command -v docker &> /dev/null; then
- log_error "Docker 未安装,请先安装 Docker"
- exit 1
- fi
-
- # 检查Docker权限
- if ! docker info &> /dev/null; then
- log_warning "Docker权限不足,尝试修复..."
-
- # 检查当前用户是否在docker组中
- if ! groups $(whoami) | grep -q docker; then
- log_warning "当前用户不在docker组中"
-
- # 尝试将用户添加到docker组
- if command -v sudo &> /dev/null; then
- log_info "尝试将用户添加到docker组(需要sudo权限)..."
- sudo usermod -aG docker $(whoami) 2>/dev/null || {
- log_warning "无法自动添加用户到docker组"
- log_info "请手动执行: sudo usermod -aG docker $(whoami)"
- log_info "然后重新登录或执行: newgrp docker"
- }
- else
- log_error "sudo命令不可用,无法修复Docker权限"
- fi
- fi
-
- # 尝试使用sudo运行docker
- if command -v sudo &> /dev/null && sudo docker info &> /dev/null; then
- log_info "检测到可以使用sudo运行Docker"
- USE_SUDO=true
- else
- log_error "Docker权限不足且无法修复"
- log_info "解决方案:"
- log_info "1. 将用户添加到docker组: sudo usermod -aG docker $(whoami)"
- log_info "2. 重新登录或执行: newgrp docker"
- log_info "3. 或使用sudo运行此脚本"
- exit 1
- fi
- fi
-
- log_success "Docker 已安装并可访问"
-}
-
-# 检查 Docker Compose 是否安装
-check_docker_compose() {
- if ! command -v docker-compose &> /dev/null; then
- log_error "Docker Compose 未安装,请先安装 Docker Compose"
- exit 1
- fi
- log_success "Docker Compose 已安装"
-}
-
-# 停止并删除现有容器
-stop_existing_container() {
- if docker_cmd ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- log_warning "停止现有容器 ${CONTAINER_NAME}"
- docker_cmd stop ${CONTAINER_NAME}
- fi
-
- if docker_cmd ps -aq -f name=${CONTAINER_NAME} | grep -q .; then
- log_warning "删除现有容器 ${CONTAINER_NAME}"
- docker_cmd rm ${CONTAINER_NAME}
- fi
-}
-
-# 构建镜像
-build_image() {
- log_info "开始构建 Docker 镜像..."
- docker_cmd build -t ${IMAGE_NAME} .
-
- if [ $? -eq 0 ]; then
- log_success "镜像构建成功: ${IMAGE_NAME}"
- else
- log_error "镜像构建失败"
- exit 1
- fi
-}
-
-# 运行容器
-run_container() {
- log_info "启动容器..."
-
- # 创建必要的目录
- mkdir -p uploads logs
-
- docker_cmd run -d \
- --name ${CONTAINER_NAME} \
- --restart unless-stopped \
- -p ${PORT}:${PORT} \
- -v $(pwd)/uploads:/app/uploads \
- -v $(pwd)/logs:/app/logs \
- -e ENVIRONMENT=production \
- -e TZ=Asia/Shanghai \
- ${IMAGE_NAME}
-
- if [ $? -eq 0 ]; then
- log_success "容器启动成功: ${CONTAINER_NAME}"
- else
- log_error "容器启动失败"
- exit 1
- fi
-}
-
-# 检查容器状态
-check_container() {
- log_info "检查容器状态..."
- sleep 5
-
- if docker_cmd ps | grep -q ${CONTAINER_NAME}; then
- log_success "容器运行正常"
-
- # 显示容器日志
- log_info "容器日志:"
- docker_cmd logs ${CONTAINER_NAME}
-
- # 测试健康检查
- log_info "测试健康检查..."
- sleep 10
- if curl -f http://localhost:${PORT}/api/v1/health &> /dev/null; then
- log_success "健康检查通过!"
- else
- log_warning "健康检查失败,但容器仍在运行"
- fi
- else
- log_error "容器未正常运行"
- log_error "容器日志:"
- docker_cmd logs ${CONTAINER_NAME}
- exit 1
- fi
-}
-
-# 使用 Docker Compose 部署
-deploy_with_compose() {
- log_info "使用 Docker Compose 部署..."
-
- # 创建 .env 文件(如果不存在)
- if [ ! -f .env ]; then
- log_warning "创建 .env 文件,请根据实际情况修改配置"
- cat > .env << EOF
-# 数据库配置
-DATABASE_URL=mysql://username:password@mysql:3306/mytest_db
-MYSQL_ROOT_PASSWORD=rootpassword
-MYSQL_DATABASE=mytest_db
-MYSQL_USER=username
-MYSQL_PASSWORD=password
-
-# Redis 配置
-REDIS_URL=redis://redis:6379/0
-
-# 应用配置
-SECRET_KEY=your-production-secret-key
-CORS_ORIGINS=http://localhost:3003,https://yourdomain.com
-ENVIRONMENT=production
-EOF
- log_warning "请编辑 .env 文件设置正确的配置"
- fi
-
- docker_compose_cmd down
- docker_compose_cmd up -d --build
-
- if [ $? -eq 0 ]; then
- log_success "Docker Compose 部署成功"
- log_info "等待服务启动..."
- sleep 15
-
- if curl -f http://localhost:${PORT}/api/v1/health &> /dev/null; then
- log_success "应用启动成功!"
- log_info "服务地址: http://localhost:${PORT}"
- log_info "API文档: http://localhost:${PORT}/docs"
- log_info "健康检查: http://localhost:${PORT}/api/v1/health"
- else
- log_warning "应用启动可能有问题,请检查日志"
- log_info "查看日志命令: docker-compose logs -f"
- docker_compose_cmd logs --tail=20
- fi
- else
- log_error "Docker Compose 部署失败"
- exit 1
- fi
-}
-
-# 清理镜像和容器
-cleanup() {
- log_info "清理旧的镜像和容器..."
-
- # 停止并删除容器
- stop_existing_container
-
- # 删除镜像
- if docker_cmd images -q ${IMAGE_NAME} | grep -q .; then
- log_warning "删除旧镜像: ${IMAGE_NAME}"
- docker_cmd rmi ${IMAGE_NAME} 2>/dev/null || true
- fi
-
- # 清理未使用的镜像和容器
- log_info "清理未使用的 Docker 资源..."
- docker_cmd system prune -f
-
- log_success "清理完成"
-}
-
-# 显示帮助信息
-show_help() {
- echo "云盘应用 Docker 部署脚本"
- echo ""
- echo "用法: $0 [选项]"
- echo ""
- echo "选项:"
- echo " build - 仅构建镜像"
- echo " run - 仅运行容器(需要先构建镜像)"
- echo " compose - 使用 Docker Compose 部署"
- echo " stop - 停止容器"
- echo " restart - 重启容器"
- echo " logs - 查看容器日志"
- echo " cleanup - 清理镜像和容器"
- echo " status - 查看容器状态"
- echo " help - 显示此帮助信息"
- echo ""
- echo "默认行为: 构建镜像并运行容器"
-}
-
-# 主函数
-main() {
- case "${1:-}" in
- "build")
- check_docker
- build_image
- ;;
- "run")
- check_docker
- stop_existing_container
- run_container
- check_container
- ;;
- "compose")
- check_docker
- check_docker_compose
- deploy_with_compose
- ;;
- "stop")
- if docker ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker stop ${CONTAINER_NAME}
- log_success "容器已停止"
- else
- log_warning "容器未运行"
- fi
- ;;
- "restart")
- if docker ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker restart ${CONTAINER_NAME}
- log_success "容器已重启"
- sleep 5
- check_container
- else
- log_warning "容器未运行,尝试启动..."
- check_docker
- stop_existing_container
- run_container
- check_container
- fi
- ;;
- "logs")
- if docker ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- docker logs -f ${CONTAINER_NAME}
- else
- log_warning "容器未运行"
- fi
- ;;
- "cleanup")
- check_docker
- cleanup
- ;;
- "status")
- if docker ps -q -f name=${CONTAINER_NAME} | grep -q .; then
- log_success "容器正在运行"
- docker ps | grep ${CONTAINER_NAME}
- else
- log_warning "容器未运行"
- fi
- ;;
- "help"|"-h"|"--help")
- show_help
- ;;
- "")
- log_info "开始构建和部署云盘应用..."
- check_docker
- stop_existing_container
- build_image
- run_container
- check_container
- log_success "部署完成!应用正在运行中"
- ;;
- *)
- log_error "未知选项: $1"
- show_help
- exit 1
- ;;
- esac
-}
-
-# 执行主函数
-main "$@"
\ No newline at end of file
diff --git a/backend/build.py b/backend/build.py
deleted file mode 100644
index ec8cee9..0000000
--- a/backend/build.py
+++ /dev/null
@@ -1,186 +0,0 @@
-#!/usr/bin/env python3
-"""
-云盘应用打包脚本
-用于将FastAPI应用打包为可执行文件
-"""
-
-import os
-import sys
-import shutil
-from pathlib import Path
-
-def clean_build():
- """清理之前的构建文件"""
- print("清理之前的构建文件...")
-
- # 清理PyInstaller生成的文件
- dirs_to_clean = ['build', 'dist', '__pycache__']
- for dir_name in dirs_to_clean:
- if os.path.exists(dir_name):
- shutil.rmtree(dir_name)
- print(f" ✅ 已删除: {dir_name}")
-
- # 清理.spec文件
- if os.path.exists('main.spec'):
- os.remove('main.spec')
- print(f" ✅ 已删除: main.spec")
-
-def check_dependencies():
- """检查依赖是否安装"""
- print("📦 检查依赖...")
-
- required_packages = ['fastapi', 'uvicorn', 'pydantic', 'sqlalchemy', 'loguru']
- missing_packages = []
-
- for package in required_packages:
- try:
- __import__(package)
- print(f" ✅ {package}")
- except ImportError:
- missing_packages.append(package)
- print(f" ❌ {package} (缺失)")
-
- if missing_packages:
- print(f"\n❌ 缺少以下依赖: {', '.join(missing_packages)}")
- print("请运行: pip install -r requirements.txt")
- return False
-
- print("✅ 所有依赖都已安装")
- return True
-
-def build_executable():
- """构建可执行文件"""
- print("🔨 开始构建可执行文件...")
-
- # 使用自定义的spec文件进行构建
- import subprocess
- result = subprocess.run([
- sys.executable, '-m', 'PyInstaller',
- 'build.spec',
- '--clean',
- '--noconfirm'
- ], capture_output=True, text=True)
-
- if result.returncode == 0:
- print("✅ 构建成功!")
- print(f"📁 可执行文件位置: {os.path.abspath('dist/cloud-drive-server.exe')}")
- return True
- else:
- print("❌ 构建失败!")
- print("错误信息:")
- print(result.stderr)
- return False
-
-def create_deployment_package():
- """创建部署包"""
- print("📦 创建部署包...")
-
- dist_dir = Path('dist')
- deploy_dir = Path('deploy')
-
- # 创建部署目录
- if deploy_dir.exists():
- shutil.rmtree(deploy_dir)
- deploy_dir.mkdir()
-
- # 复制可执行文件
- exe_path = dist_dir / 'cloud-drive-server.exe'
- if exe_path.exists():
- shutil.copy2(exe_path, deploy_dir / 'cloud-drive-server.exe')
- print(" ✅ 复制可执行文件")
-
- # 复制配置文件
- config_files = ['requirements.txt', '.env.example']
- for config_file in config_files:
- if os.path.exists(config_file):
- shutil.copy2(config_file, deploy_dir / config_file)
- print(f" ✅ 复制配置文件: {config_file}")
-
- # 创建启动脚本
- start_script = deploy_dir / 'start.bat'
- with open(start_script, 'w', encoding='utf-8') as f:
- f.write("""@echo off
-echo 🚀 启动云盘服务器...
-echo 📝 确保MySQL和Redis服务已启动
-echo.
-cloud-drive-server.exe
-pause
-""")
- print(" ✅ 创建启动脚本: start.bat")
-
- # 创建README
- readme_path = deploy_dir / 'README.md'
- with open(readme_path, 'w', encoding='utf-8') as f:
- f.write("""# 云盘应用部署包
-
-## 快速启动
-
-1. **确保数据库和缓存服务运行**
- - MySQL服务器已启动
- - Redis服务器已启动(可选)
-
-2. **配置环境变量**
- - 复制 `.env.example` 为 `.env`
- - 修改 `.env` 中的数据库连接信息
-
-3. **启动应用**
- - Windows: 双击 `start.bat` 或运行 `cloud-drive-server.exe`
- - 访问 http://localhost:8000
-
-## 配置说明
-
-在 `.env` 文件中配置以下参数:
-
-```env
-# 数据库配置
-DATABASE_URL=mysql+pymysql://username:password@localhost:3306/database_name
-
-# JWT密钥
-SECRET_KEY=your-secret-key-here
-
-# 其他配置...
-```
-
-## API文档
-
-启动后访问:
-- Swagger UI: http://localhost:8000/docs
-- ReDoc: http://localhost:8000/redoc
-
-## 故障排除
-
-1. **端口被占用**: 修改 `.env` 中的 `PORT` 配置
-2. **数据库连接失败**: 检查MySQL服务状态和连接配置
-3. **缺少依赖**: 确保所有依赖已正确安装
-""")
- print(" ✅ 创建README文档")
-
- print(f"📁 部署包位置: {deploy_dir.absolute()}")
- return True
-
-def main():
- """主函数"""
- print("🏗️ 云盘应用打包工具")
- print("=" * 50)
-
- # 1. 检查依赖
- if not check_dependencies():
- sys.exit(1)
-
- # 2. 清理之前的构建
- clean_build()
-
- # 3. 构建可执行文件
- if not build_executable():
- sys.exit(1)
-
- # 4. 创建部署包
- if not create_deployment_package():
- sys.exit(1)
-
- print("\n🎉 打包完成!")
- print("📁 部署包位于 'deploy' 目录")
- print("🚀 可以将整个 deploy 文件夹复制到目标服务器运行")
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/build_linux.bat b/backend/build_linux.bat
deleted file mode 100644
index d1f6b29..0000000
--- a/backend/build_linux.bat
+++ /dev/null
@@ -1,4 +0,0 @@
-@echo off
-echo 正在为Linux打包Python程序...
-docker run --rm -v "%cd%:/src" cdrx/pyinstaller-linux:python3-20231002 "pyinstaller --onefile main.py"
-echo 打包完成!检查 dist/ 目录
\ No newline at end of file
diff --git a/backend/build_linux.py b/backend/build_linux.py
deleted file mode 100644
index dd4c8ac..0000000
--- a/backend/build_linux.py
+++ /dev/null
@@ -1,332 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-云盘后端Linux打包脚本
-使用PyInstaller将后端应用打包成Linux可执行文件
-"""
-
-import os
-import sys
-import shutil
-import subprocess
-from pathlib import Path
-import argparse
-
-def check_python_version():
- """检查Python版本"""
- if sys.version_info < (3, 8):
- print("错误: 需要Python 3.8或更高版本")
- sys.exit(1)
- print(f"[OK] Python版本: {sys.version}")
-
-def check_dependencies():
- """检查必要的依赖"""
- try:
- import PyInstaller
- print(f"[OK] PyInstaller版本: {PyInstaller.__version__}")
- except ImportError:
- print("错误: 未安装PyInstaller")
- print("请运行: pip install pyinstaller")
- sys.exit(1)
-
-def clean_build_dirs():
- """清理之前的构建目录"""
- dirs_to_clean = ['build', 'dist', '__pycache__']
- for dir_name in dirs_to_clean:
- if os.path.exists(dir_name):
- print(f"清理目录: {dir_name}")
- shutil.rmtree(dir_name)
-
- # 清理Python缓存文件
- for root, dirs, files in os.walk('.'):
- for file in files:
- if file.endswith('.pyc') or file.endswith('.pyo'):
- os.remove(os.path.join(root, file))
- if '__pycache__' in dirs:
- shutil.rmtree(os.path.join(root, '__pycache__'))
-
-def create_spec_file():
- """创建或更新PyInstaller规格文件"""
- # 直接使用现有的build.spec文件
- print("[OK] build.spec 文件已存在,跳过创建")
-
-def run_pyinstaller():
- """运行PyInstaller进行打包"""
- print("开始打包...")
- try:
- # 使用spec文件进行打包
- cmd = ['pyinstaller', '--clean', 'build.spec']
- result = subprocess.run(cmd, check=True, capture_output=True, text=True)
- print("[OK] PyInstaller执行成功")
- if result.stdout:
- print("输出:", result.stdout)
- except subprocess.CalledProcessError as e:
- print(f"错误: PyInstaller执行失败: {e}")
- if e.stderr:
- print("错误输出:", e.stderr)
- sys.exit(1)
-
-def create_deployment_package():
- """创建部署包"""
- dist_dir = Path('dist')
- deploy_dir = Path('deploy')
-
- if deploy_dir.exists():
- shutil.rmtree(deploy_dir)
-
- deploy_dir.mkdir()
-
- # 复制可执行文件
- exe_file = dist_dir / 'cloud-drive-server'
- if exe_file.exists():
- shutil.copy2(exe_file, deploy_dir)
- print(f"[OK] 复制可执行文件到 {deploy_dir}")
-
- # 复制配置文件
- config_files = ['.env.example']
- for config_file in config_files:
- if os.path.exists(config_file):
- shutil.copy2(config_file, deploy_dir)
- print(f"[OK] 复制配置文件 {config_file}")
-
- # 复制安装脚本
- install_scripts = ['install.sh', 'install_user.sh']
- for script in install_scripts:
- if os.path.exists(script):
- shutil.copy2(script, deploy_dir)
- os.chmod(deploy_dir / script, 0o755)
- print(f"[OK] 复制安装脚本 {script}")
-
- # 创建部署目录结构
- (deploy_dir / 'logs').mkdir(exist_ok=True)
- (deploy_dir / 'uploads').mkdir(exist_ok=True)
-
- # 创建启动脚本
- create_startup_script(deploy_dir)
-
- # 创建README
- create_readme(deploy_dir)
-
- print(f"[OK] 部署包创建完成: {deploy_dir.absolute()}")
-
- deploy_dir.mkdir()
-
- # 复制可执行文件
- exe_file = dist_dir / 'cloud-drive-server'
- if exe_file.exists():
- shutil.copy2(exe_file, deploy_dir)
- print(f"[OK] 复制可执行文件到 {deploy_dir}")
-
- # 复制配置文件
- config_files = ['.env.example']
- for config_file in config_files:
- if os.path.exists(config_file):
- shutil.copy2(config_file, deploy_dir)
- print(f"[OK] 复制配置文件 {config_file}")
-
- # 创建部署目录结构
- (deploy_dir / 'logs').mkdir(exist_ok=True)
- (deploy_dir / 'uploads').mkdir(exist_ok=True)
-
- # 创建启动脚本
- create_startup_script(deploy_dir)
-
- # 创建README
- create_readme(deploy_dir)
-
- print(f"[OK] 部署包创建完成: {deploy_dir.absolute()}")
-
-def create_startup_script(deploy_dir):
- """创建启动脚本"""
- # Linux启动脚本
- startup_script = '''#!/bin/bash
-# 云盘后端服务启动脚本
-
-# 设置环境变量
-export PYTHONPATH=${PYTHONPATH}:$(dirname "$0")
-
-# 进入脚本所在目录
-cd "$(dirname "$0")"
-
-# 检查环境文件
-if [ ! -f ".env" ]; then
- echo "警告: .env 文件不存在,将使用默认配置"
- if [ -f ".env.example" ]; then
- cp .env.example .env
- echo "已复制 .env.example 为 .env,请根据需要修改配置"
- fi
-fi
-
-# 创建必要的目录
-mkdir -p logs uploads
-
-# 启动服务
-echo "启动云盘后端服务..."
-./cloud-drive-server
-'''
-
- script_path = deploy_dir / 'start.sh'
- with open(script_path, 'w', encoding='utf-8') as f:
- f.write(startup_script)
-
- # 设置执行权限
- os.chmod(script_path, 0o755)
- print("[OK] 创建启动脚本 start.sh")
-
-def create_readme(deploy_dir):
- """创建部署说明文档"""
- readme_content = '''# 云盘后端服务部署说明
-
-## 文件说明
-
-- `cloud-drive-server`: 主程序可执行文件
-- `start.sh`: 启动脚本
-- `.env.example`: 环境配置示例文件
-
-## 快速开始
-
-1. **配置环境变量**
- ```bash
- cp .env.example .env
- # 编辑 .env 文件,配置数据库和Redis连接信息
- nano .env
- ```
-
-2. **启动服务**
- ```bash
- chmod +x start.sh
- ./start.sh
- ```
-
- 或者直接运行:
- ```bash
- ./cloud-drive-server
- ```
-
-3. **访问服务**
- - API文档: http://localhost:8000/docs
- - 健康检查: http://localhost:8000/api/v1/health
-
-## 环境配置
-
-主要配置项(.env文件):
-
-```env
-# 数据库配置
-DATABASE_URL=mysql+pymysql://用户名:密码@主机:端口/数据库名
-
-# Redis配置
-REDIS_URL=redis://主机:端口
-
-# JWT配置
-JWT_SECRET_KEY=你的密钥
-JWT_EXPIRE_MINUTES=30
-
-# 文件上传配置
-UPLOAD_DIR=uploads
-MAX_FILE_SIZE=10485760 # 10MB
-```
-
-## 系统要求
-
-- Linux 64位系统
-- MySQL 5.7+ 或 8.0+
-- Redis (可选)
-- 至少512MB内存
-- 至少100MB磁盘空间
-
-## 日志
-
-日志文件位置:`logs/app.log`
-
-## 问题排查
-
-1. **端口占用**
- - 默认端口8000,如需修改请编辑.env文件
-
-2. **数据库连接失败**
- - 检查DATABASE_URL配置
- - 确保数据库服务正在运行
- - 检查防火墙设置
-
-3. **权限问题**
- - 确保程序有执行权限:`chmod +x cloud-drive-server`
- - 确保有写入logs和uploads目录的权限
-
-## 后台运行
-
-使用systemd或supervisor管理服务进程:
-
-### systemd 配置示例
-
-创建服务文件 `/etc/systemd/system/cloud-drive.service`:
-
-```ini
-[Unit]
-Description=Cloud Drive Backend Service
-After=network.target
-
-[Service]
-Type=simple
-User=www-data
-WorkingDirectory=/path/to/deploy/directory
-ExecStart=/path/to/deploy/directory/cloud-drive-server
-Restart=always
-RestartSec=10
-
-[Install]
-WantedBy=multi-user.target
-```
-
-启用和启动服务:
-```bash
-sudo systemctl daemon-reload
-sudo systemctl enable cloud-drive
-sudo systemctl start cloud-drive
-```
-'''
-
- readme_path = deploy_dir / 'README.md'
- with open(readme_path, 'w', encoding='utf-8') as f:
- f.write(readme_content)
- print("[OK] 创建部署说明文档 README.md")
-
-def main():
- """主函数"""
- parser = argparse.ArgumentParser(description='云盘后端Linux打包工具')
- parser.add_argument('--clean', action='store_true', help='仅清理构建目录')
- parser.add_argument('--no-clean', action='store_true', help='跳过清理步骤')
-
- args = parser.parse_args()
-
- print("=== 云盘后端Linux打包工具 ===")
- print(f"当前目录: {os.getcwd()}")
-
- # 检查环境
- check_python_version()
- check_dependencies()
-
- # 清理构建目录
- if args.clean:
- clean_build_dirs()
- print("[OK] 清理完成")
- return
-
- if not args.no_clean:
- clean_build_dirs()
-
- # 创建规格文件
- create_spec_file()
-
- # 运行打包
- run_pyinstaller()
-
- # 创建部署包
- create_deployment_package()
-
- print("\n=== 打包完成 ===")
- print("部署包位置: ./deploy/")
- print("请查看 ./deploy/README.md 了解部署说明")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/build_linux_fixed.py b/backend/build_linux_fixed.py
deleted file mode 100644
index 8d37462..0000000
--- a/backend/build_linux_fixed.py
+++ /dev/null
@@ -1,312 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-云盘后端Linux打包脚本
-使用PyInstaller将后端应用打包成Linux可执行文件
-"""
-
-import os
-import sys
-import shutil
-import subprocess
-from pathlib import Path
-import argparse
-
-def check_python_version():
- """检查Python版本"""
- if sys.version_info < (3, 8):
- print("错误: 需要Python 3.8或更高版本")
- sys.exit(1)
- print(f"[OK] Python版本: {sys.version}")
-
-def check_dependencies():
- """检查必要的依赖"""
- try:
- import PyInstaller
- print(f"[OK] PyInstaller版本: {PyInstaller.__version__}")
- except ImportError:
- print("错误: 未安装PyInstaller")
- print("请运行: pip install pyinstaller")
- sys.exit(1)
-
-def clean_build_dirs():
- """清理之前的构建目录"""
- dirs_to_clean = ['build', 'dist', '__pycache__']
- for dir_name in dirs_to_clean:
- if os.path.exists(dir_name):
- print(f"清理目录: {dir_name}")
- shutil.rmtree(dir_name)
-
- # 清理Python缓存文件
- for root, dirs, files in os.walk('.'):
- for file in files:
- if file.endswith('.pyc') or file.endswith('.pyo'):
- os.remove(os.path.join(root, file))
- if '__pycache__' in dirs:
- shutil.rmtree(os.path.join(root, '__pycache__'))
-
-def create_spec_file():
- """创建或更新PyInstaller规格文件"""
- # 直接使用现有的build.spec文件
- print("[OK] build.spec 文件已存在,跳过创建")
-
-def run_pyinstaller():
- """运行PyInstaller进行打包"""
- print("开始打包...")
- try:
- # 使用spec文件进行打包
- cmd = ['pyinstaller', '--clean', 'build.spec']
- result = subprocess.run(cmd, check=True, capture_output=True, text=True)
- print("[OK] PyInstaller执行成功")
- if result.stdout:
- print("输出:", result.stdout)
- except subprocess.CalledProcessError as e:
- print(f"错误: PyInstaller执行失败: {e}")
- if e.stderr:
- print("错误输出:", e.stderr)
- sys.exit(1)
-
-def create_deployment_package():
- """创建部署包"""
- dist_dir = Path('dist')
- deploy_dir = Path('deploy')
-
- if deploy_dir.exists():
- shutil.rmtree(deploy_dir)
-
- deploy_dir.mkdir()
-
- # 复制可执行文件
- exe_file = dist_dir / 'cloud-drive-server'
- if exe_file.exists():
- shutil.copy2(exe_file, deploy_dir)
- print(f"[OK] 复制可执行文件到 {deploy_dir}")
-
- # 复制配置文件
- config_files = ['.env.example']
- for config_file in config_files:
- if os.path.exists(config_file):
- shutil.copy2(config_file, deploy_dir)
- print(f"[OK] 复制配置文件 {config_file}")
-
- # 复制安装脚本
- install_scripts = ['install.sh', 'install_user.sh']
- for script in install_scripts:
- if os.path.exists(script):
- shutil.copy2(script, deploy_dir)
- os.chmod(deploy_dir / script, 0o755)
- print(f"[OK] 复制安装脚本 {script}")
-
- # 创建部署目录结构
- (deploy_dir / 'logs').mkdir(exist_ok=True)
- (deploy_dir / 'uploads').mkdir(exist_ok=True)
-
- # 创建启动脚本
- create_startup_script(deploy_dir)
-
- # 创建README
- create_readme(deploy_dir)
-
- print(f"[OK] 部署包创建完成: {deploy_dir.absolute()}")
-
-def create_startup_script(deploy_dir):
- """创建启动脚本"""
- # Linux启动脚本
- startup_script = '''#!/bin/bash
-# 云盘后端服务启动脚本
-
-# 设置环境变量
-export PYTHONPATH=${PYTHONPATH}:$(dirname "$0")
-
-# 进入脚本所在目录
-cd "$(dirname "$0")"
-
-# 检查环境文件
-if [ ! -f ".env" ]; then
- echo "警告: .env 文件不存在,将使用默认配置"
- if [ -f ".env.example" ]; then
- cp .env.example .env
- echo "已复制 .env.example 为 .env,请根据需要修改配置"
- fi
-fi
-
-# 创建必要的目录
-mkdir -p logs uploads
-
-# 启动服务
-echo "启动云盘后端服务..."
-./cloud-drive-server
-'''
-
- script_path = deploy_dir / 'start.sh'
- with open(script_path, 'w', encoding='utf-8') as f:
- f.write(startup_script)
-
- # 设置执行权限
- os.chmod(script_path, 0o755)
- print("[OK] 创建启动脚本 start.sh")
-
-def create_readme(deploy_dir):
- """创建部署说明文档"""
- readme_content = '''# 云盘后端服务部署说明
-
-## 文件说明
-
-- `cloud-drive-server`: 主程序可执行文件
-- `start.sh`: 启动脚本
-- `install.sh`: 系统级安装脚本(需要sudo权限)
-- `install_user.sh`: 用户级安装脚本(无需sudo权限)
-- `.env.example`: 环境配置示例文件
-
-## 快速开始
-
-### 方法一:用户级安装(推荐,无需sudo权限)
-
-```bash
-# 1. 运行用户级安装脚本
-./install_user.sh
-
-# 2. 配置环境变量
-cd ~/cloud-drive
-cp .env.example .env
-nano .env # 编辑配置文件
-
-# 3. 启动服务
-./start.sh
-
-# 4. 查看状态
-./status.sh
-```
-
-### 方法二:系统级安装(需要sudo权限)
-
-```bash
-# 1. 运行系统级安装脚本
-sudo ./install.sh
-
-# 2. 启动服务
-sudo systemctl start cloud-drive
-
-# 3. 查看状态
-sudo systemctl status cloud-drive
-```
-
-### 方法三:直接运行
-
-```bash
-# 1. 配置环境变量
-cp .env.example .env
-nano .env # 编辑配置文件
-
-# 2. 启动服务
-chmod +x cloud-drive-server
-./cloud-drive-server
-```
-
-## 环境配置
-
-主要配置项(.env文件):
-
-```env
-# 数据库配置
-DATABASE_URL=mysql+pymysql://用户名:密码@主机:端口/数据库名
-
-# Redis配置
-REDIS_URL=redis://主机:端口
-
-# JWT配置
-JWT_SECRET_KEY=你的密钥
-JWT_EXPIRE_MINUTES=30
-
-# 文件上传配置
-UPLOAD_DIR=uploads
-MAX_FILE_SIZE=10485760 # 10MB
-```
-
-## 访问服务
-
-- API文档: http://localhost:8000/docs
-- 健康检查: http://localhost:8000/api/v1/health
-- 根路径: http://localhost:8000/
-
-## 系统要求
-
-- Linux 64位系统
-- MySQL 5.7+ 或 8.0+
-- Redis (可选)
-- 至少512MB内存
-- 至少100MB磁盘空间
-
-## 问题排查
-
-1. **端口占用**
- - 默认端口8000,如需修改请编辑.env文件
-
-2. **数据库连接失败**
- - 检查DATABASE_URL配置
- - 确保数据库服务正在运行
-
-3. **权限问题**
- - 确保程序有执行权限:`chmod +x cloud-drive-server`
- - 确保有写入logs和uploads目录的权限
-
-4. **依赖缺失**
- - 如果出现模块缺失错误,请确保打包包含了所有依赖
- - 可以尝试重新运行打包脚本
-
-## 日志
-
-日志文件位置:
-- 用户级安装:`~/.local/share/cloud-drive/logs/app.log`
-- 系统级安装:`/opt/cloud-drive/logs/app.log`
-- 直接运行:`./logs/app.log`
-'''
-
- readme_path = deploy_dir / 'README.md'
- with open(readme_path, 'w', encoding='utf-8') as f:
- f.write(readme_content)
- print("[OK] 创建部署说明文档 README.md")
-
-def main():
- """主函数"""
- parser = argparse.ArgumentParser(description='云盘后端Linux打包工具')
- parser.add_argument('--clean', action='store_true', help='仅清理构建目录')
- parser.add_argument('--no-clean', action='store_true', help='跳过清理步骤')
-
- args = parser.parse_args()
-
- print("=== 云盘后端Linux打包工具 ===")
- print(f"当前目录: {os.getcwd()}")
-
- # 检查环境
- check_python_version()
- check_dependencies()
-
- # 清理构建目录
- if args.clean:
- clean_build_dirs()
- print("[OK] 清理完成")
- return
-
- if not args.no_clean:
- clean_build_dirs()
-
- # 创建规格文件
- create_spec_file()
-
- # 运行打包
- run_pyinstaller()
-
- # 创建部署包
- create_deployment_package()
-
- print("\n=== 打包完成 ===")
- print("部署包位置: ./deploy/")
- print("请查看 ./deploy/README.md 了解部署说明")
- print("\n安装方式:")
- print("1. 用户级安装(推荐):./install_user.sh")
- print("2. 系统级安装:sudo ./install.sh")
- print("3. 直接运行:./cloud-drive-server")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/build_noshared.py b/backend/build_noshared.py
deleted file mode 100644
index fca445f..0000000
--- a/backend/build_noshared.py
+++ /dev/null
@@ -1,242 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-适用于无共享库Python环境的打包脚本
-"""
-
-import os
-import sys
-import shutil
-import subprocess
-from pathlib import Path
-import argparse
-
-def check_python_version():
- """检查Python版本"""
- if sys.version_info < (3, 8):
- print("错误: 需要Python 3.8或更高版本")
- sys.exit(1)
- print(f"[OK] Python版本: {sys.version}")
-
-def check_dependencies():
- """检查必要的依赖"""
- try:
- import PyInstaller
- print(f"[OK] PyInstaller版本: {PyInstaller.__version__}")
- except ImportError:
- print("错误: 未安装PyInstaller")
- print("请运行: pip install pyinstaller")
- sys.exit(1)
-
-def clean_build_dirs():
- """清理之前的构建目录"""
- dirs_to_clean = ['build', 'dist', '__pycache__']
- for dir_name in dirs_to_clean:
- if os.path.exists(dir_name):
- print(f"清理目录: {dir_name}")
- shutil.rmtree(dir_name)
-
- # 清理Python缓存文件
- for root, dirs, files in os.walk('.'):
- for file in files:
- if file.endswith('.pyc') or file.endswith('.pyo'):
- os.remove(os.path.join(root, file))
- if '__pycache__' in dirs:
- shutil.rmtree(os.path.join(root, '__pycache__'))
-
-def run_pyinstaller_noshared():
- """运行PyInstaller进行打包(无共享库版本)"""
- print("开始打包(无共享库模式)...")
-
- # 尝试多种打包方式
- spec_files = ['build_noshared.spec', 'build.spec']
-
- for spec_file in spec_files:
- if os.path.exists(spec_file):
- print(f"使用规格文件: {spec_file}")
-
- # 构建命令
- cmd = ['pyinstaller', '--clean', '--noupx', spec_file]
-
- # 如果是build.spec,添加额外参数
- if spec_file == 'build.spec':
- cmd.extend(['--noupx', '--debug', 'imports'])
-
- try:
- result = subprocess.run(cmd, check=True, capture_output=True, text=True)
- print(f"[OK] PyInstaller执行成功 (使用 {spec_file})")
- if result.stdout:
- print("输出:", result.stdout)
- return True
- except subprocess.CalledProcessError as e:
- print(f"使用 {spec_file} 打包失败: {e}")
- if e.stderr:
- print("错误输出:", e.stderr)
- continue
-
- print("错误: 所有打包方式都失败了")
- return False
-
-def create_simple_package():
- """创建简单的部署包(不使用PyInstaller)"""
- print("创建简单部署包...")
-
- deploy_dir = Path('deploy')
- if deploy_dir.exists():
- shutil.rmtree(deploy_dir)
-
- deploy_dir.mkdir()
-
- # 复制源代码
- shutil.copytree('app', deploy_dir / 'app')
- shutil.copy2('main.py', deploy_dir)
- shutil.copy2('requirements.txt', deploy_dir)
- shutil.copy2('.env.example', deploy_dir)
-
- # 创建启动脚本
- startup_script = '''#!/bin/bash
-# 云盘后端服务启动脚本(Python模式)
-
-# 进入脚本所在目录
-cd "$(dirname "$0")"
-
-# 检查Python环境
-if ! command -v python3 &> /dev/null; then
- echo "错误: 未找到python3"
- exit 1
-fi
-
-# 检查虚拟环境
-if [ ! -d "venv" ]; then
- echo "创建虚拟环境..."
- python3 -m venv venv
- source venv/bin/activate
- pip install -r requirements.txt
-else
- echo "激活虚拟环境..."
- source venv/bin/activate
-fi
-
-# 检查环境文件
-if [ ! -f ".env" ]; then
- echo "警告: .env 文件不存在,将使用默认配置"
- if [ -f ".env.example" ]; then
- cp .env.example .env
- echo "已复制 .env.example 为 .env,请根据需要修改配置"
- fi
-fi
-
-# 启动服务
-echo "启动云盘后端服务..."
-python main.py
-'''
-
- script_path = deploy_dir / 'start.sh'
- with open(script_path, 'w', encoding='utf-8') as f:
- f.write(startup_script)
-
- os.chmod(script_path, 0o755)
-
- # 创建安装脚本
- install_script = '''#!/bin/bash
-# 简单安装脚本
-
-INSTALL_DIR="$HOME/cloud-drive"
-
-echo "=== 云盘后端服务安装(简单版本) ==="
-
-# 创建安装目录
-mkdir -p "$INSTALL_DIR"
-
-# 复制文件
-cp -r * "$INSTALL_DIR/"
-cd "$INSTALL_DIR"
-
-# 设置权限
-chmod +x start.sh
-
-echo "=== 安装完成 ==="
-echo "进入目录: cd $INSTALL_DIR"
-echo "启动服务: ./start.sh"
-'''
-
- install_path = deploy_dir / 'install_simple.sh'
- with open(install_path, 'w', encoding='utf-8') as f:
- f.write(install_script)
-
- os.chmod(install_path, 0o755)
-
- print(f"[OK] 简单部署包创建完成: {deploy_dir.absolute()}")
- return True
-
-def create_deployment_package():
- """创建部署包"""
- dist_dir = Path('dist')
- deploy_dir = Path('deploy')
-
- if deploy_dir.exists():
- shutil.rmtree(deploy_dir)
-
- deploy_dir.mkdir()
-
- # 尝试复制可执行文件
- exe_file = dist_dir / 'cloud-drive-server'
- if exe_file.exists():
- shutil.copy2(exe_file, deploy_dir)
- print(f"[OK] 复制可执行文件到 {deploy_dir}")
- return True
- else:
- print("警告: 未找到可执行文件,创建简单部署包")
- return create_simple_package()
-
-def main():
- """主函数"""
- parser = argparse.ArgumentParser(description='云盘后端Linux打包工具(无共享库版)')
- parser.add_argument('--clean', action='store_true', help='仅清理构建目录')
- parser.add_argument('--no-clean', action='store_true', help='跳过清理步骤')
- parser.add_argument('--simple', action='store_true', help='创建简单部署包(不使用PyInstaller)')
-
- args = parser.parse_args()
-
- print("=== 云盘后端Linux打包工具(无共享库版) ===")
- print(f"当前目录: {os.getcwd()}")
-
- # 检查环境
- check_python_version()
- check_dependencies()
-
- # 清理构建目录
- if args.clean:
- clean_build_dirs()
- print("[OK] 清理完成")
- return
-
- if not args.no_clean:
- clean_build_dirs()
-
- if args.simple:
- # 直接创建简单部署包
- create_simple_package()
- else:
- # 尝试PyInstaller打包
- if run_pyinstaller_noshared():
- create_deployment_package()
- else:
- print("PyInstaller打包失败,创建简单部署包...")
- create_simple_package()
-
- print("\n=== 打包完成 ===")
- print("部署包位置: ./deploy/")
-
- # 检查部署包内容
- deploy_dir = Path('deploy')
- if (deploy_dir / 'cloud-drive-server').exists():
- print("✓ 可执行文件: cloud-drive-server")
- print("运行方式: ./cloud-drive-server")
- else:
- print("✓ Python源代码包")
- print("运行方式: ./start.sh")
- print("安装方式: ./install_simple.sh")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/build_with_docker.sh b/backend/build_with_docker.sh
deleted file mode 100644
index 325e4ec..0000000
--- a/backend/build_with_docker.sh
+++ /dev/null
@@ -1,23 +0,0 @@
-#!/bin/bash
-# 使用Docker构建Linux可执行文件
-
-echo "=== 使用Docker构建Linux可执行文件 ==="
-
-# 构建Docker镜像
-echo "构建Docker镜像..."
-docker build -f Dockerfile.build -t cloud-drive-builder .
-
-# 运行构建容器并提取结果
-echo "运行构建..."
-docker run --rm -v $(pwd):/output cloud-drive-builder bash -c "cp -r /opt/cloud-drive/* /output/"
-
-echo "=== 构建完成 ==="
-echo "Linux可执行文件已生成到当前目录"
-echo "文件列表:"
-ls -la cloud-drive-server start.sh README.md .env.example
-
-echo ""
-echo "部署文件已准备就绪,可以上传到Linux服务器"
-echo "建议下一步:"
-echo "1. 将所有文件上传到Linux服务器"
-echo "2. 运行 sudo ./install.sh 进行安装"
\ No newline at end of file
diff --git a/backend/check_files_table.py b/backend/check_files_table.py
deleted file mode 100644
index 9f25155..0000000
--- a/backend/check_files_table.py
+++ /dev/null
@@ -1,219 +0,0 @@
-#!/usr/bin/env python3
-"""
-检查数据库files表和实际文件存储情况
-"""
-
-import mysql.connector
-import os
-import hashlib
-
-def check_database_files():
- """检查数据库中的文件记录"""
-
- try:
- # 连接数据库
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- # 查询files表中的所有记录
- cursor.execute("""
- SELECT id, user_id, original_filename, filename, file_path, file_size,
- file_hash, mime_type, created_at
- FROM files
- ORDER BY created_at DESC
- """)
-
- files = cursor.fetchall()
-
- print("=== 数据库 files 表中的记录 ===")
- if files:
- for file in files:
- (id, user_id, original_filename, filename, file_path,
- file_size, file_hash, mime_type, created_at) = file
-
- print(f"ID: {id}")
- print(f" 用户ID: {user_id}")
- print(f" 原始文件名: {original_filename}")
- print(f" 存储文件名: {filename}")
- print(f" 文件路径: {file_path}")
- print(f" 文件大小: {file_size} bytes")
- print(f" 文件哈希: {file_hash}")
- print(f" MIME类型: {mime_type}")
- print(f" 创建时间: {created_at}")
- print("-" * 50)
- else:
- print("files 表中没有记录")
-
- print(f"\n总记录数: {len(files)}")
-
- # 检查每个文件是否真实存在
- print("\n=== 文件存在性检查 ===")
- existing_count = 0
- missing_files = []
-
- for file in files:
- (id, user_id, original_filename, filename, file_path,
- file_size, file_hash, mime_type, created_at) = file
-
- full_path = os.path.join("uploads", filename)
- if os.path.exists(full_path):
- existing_count += 1
- print(f"✅ ID {id}: {original_filename} - 文件存在")
-
- # 检查文件大小
- actual_size = os.path.getsize(full_path)
- if actual_size != file_size:
- print(f" ⚠️ 文件大小不匹配! 数据库: {file_size}, 实际: {actual_size}")
-
- # 检查文件哈希
- try:
- with open(full_path, 'rb') as f:
- content = f.read()
- actual_hash = hashlib.sha256(content).hexdigest()
- if actual_hash != file_hash:
- print(f" ❌ 文件哈希不匹配! 数据库: {file_hash}")
- print(f" 实际: {actual_hash}")
- except Exception as e:
- print(f" ❌ 无法读取文件或计算哈希: {e}")
-
- else:
- missing_files.append((id, original_filename, filename))
- print(f"❌ ID {id}: {original_filename} - 文件不存在!")
-
- print(f"\n实际存在的文件: {existing_count}")
- print(f"缺失的文件: {len(missing_files)}")
-
- if missing_files:
- print("\n缺失文件详情:")
- for (id, original_filename, filename) in missing_files:
- print(f" ID {id}: {original_filename} (应存储为: {filename})")
-
- except Exception as e:
- print(f"数据库查询出错: {e}")
- finally:
- if 'conn' in locals() and conn.is_connected():
- cursor.close()
- conn.close()
-
-def check_uploads_directory():
- """检查uploads目录中的实际文件"""
-
- print("\n=== uploads 目录中的实际文件 ===")
-
- uploads_dir = "uploads"
- if os.path.exists(uploads_dir):
- files = os.listdir(uploads_dir)
- if files:
- print(f"目录: {uploads_dir}")
- print(f"文件数量: {len(files)}")
-
- for file in files:
- file_path = os.path.join(uploads_dir, file)
- file_size = os.path.getsize(file_path)
-
- # 计算文件哈希
- try:
- with open(file_path, 'rb') as f:
- content = f.read()
- file_hash = hashlib.sha256(content).hexdigest()
-
- # 尝试读取文本内容
- try:
- with open(file_path, 'r', encoding='utf-8') as f:
- text_content = f.read()
- content_preview = text_content[:100] + "..." if len(text_content) > 100 else text_content
- content_preview = repr(content_preview) # 显示引号和特殊字符
- except:
- content_preview = "(二进制文件)"
-
- except Exception as e:
- file_hash = f"无法计算哈希: {e}"
- content_preview = f"无法读取: {e}"
-
- print(f"\n📄 {file}")
- print(f" 大小: {file_size} bytes")
- print(f" 哈希: {file_hash}")
- print(f" 内容预览: {content_preview}")
- else:
- print(f"目录 {uploads_dir} 为空")
- else:
- print(f"目录 {uploads_dir} 不存在")
-
-def check_file_integrity():
- """检查文件完整性,对比数据库和实际文件"""
-
- print("\n=== 文件完整性检查 ===")
-
- try:
- # 连接数据库
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- # 查询所有文件
- cursor.execute("SELECT id, filename, file_hash, file_size FROM files")
- db_files = cursor.fetchall()
-
- integrity_issues = []
-
- for (id, filename, expected_hash, expected_size) in db_files:
- full_path = os.path.join("uploads", filename)
-
- if os.path.exists(full_path):
- # 检查大小
- actual_size = os.path.getsize(full_path)
- if actual_size != expected_size:
- integrity_issues.append(f"ID {id}: 文件大小不匹配 (期望: {expected_size}, 实际: {actual_size})")
- continue
-
- # 检查哈希
- try:
- with open(full_path, 'rb') as f:
- content = f.read()
- actual_hash = hashlib.sha256(content).hexdigest()
-
- if actual_hash != expected_hash:
- integrity_issues.append(f"ID {id}: 文件哈希不匹配")
- print(f" 期望哈希: {expected_hash}")
- print(f" 实际哈希: {actual_hash}")
-
- except Exception as e:
- integrity_issues.append(f"ID {id}: 无法计算文件哈希 - {e}")
- else:
- integrity_issues.append(f"ID {id}: 文件不存在")
-
- if integrity_issues:
- print(f"❌ 发现 {len(integrity_issues)} 个完整性问题:")
- for issue in integrity_issues:
- print(f" - {issue}")
- else:
- print("✅ 所有文件完整性检查通过!")
-
- except Exception as e:
- print(f"完整性检查出错: {e}")
- finally:
- if 'conn' in locals() and conn.is_connected():
- cursor.close()
- conn.close()
-
-if __name__ == "__main__":
- check_database_files()
- check_uploads_directory()
- check_file_integrity()
-
- print("\n=== 总结 ===")
- print("文件存储情况:")
- print("1. 数据库存储文件的元数据信息")
- print("2. 实际文件存储在 backend/uploads/ 目录")
- print("3. 文件名使用UUID格式确保唯一性")
- print("4. 通过file_hash确保文件完整性")
- print("5. 支持文件去重功能")
\ No newline at end of file
diff --git a/backend/check_tables.py b/backend/check_tables.py
deleted file mode 100644
index 1c96abd..0000000
--- a/backend/check_tables.py
+++ /dev/null
@@ -1,51 +0,0 @@
-import pymysql
-from app.core.config import settings
-
-def check_user_login_table():
- try:
- # 解析连接字符串
- import re
- pattern = r'mysql\+pymysql://([^:]+):([^@]+)@([^:]+):(\d+)/(.+)'
- match = re.match(pattern, settings.DATABASE_URL)
-
- if match:
- username, password, host, port, database = match.groups()
-
- connection = pymysql.connect(
- host=host,
- port=int(port),
- user=username,
- password=password,
- database=database,
- charset='utf8mb4'
- )
-
- with connection.cursor() as cursor:
- # 检查user_login表结构
- print("=== user_login表结构 ===")
- cursor.execute("DESCRIBE user_login")
- columns = cursor.fetchall()
- for column in columns:
- print(f"{column[0]}: {column[1]} {column[2]} {column[3]} {column[4]}")
-
- print("\n=== user_login表数据示例 ===")
- cursor.execute("SELECT * FROM user_login LIMIT 3")
- rows = cursor.fetchall()
- for row in rows:
- print(row)
-
- print("\n=== 检查是否有用户相关的表 ===")
- cursor.execute("SHOW TABLES LIKE '%user%'")
- user_tables = cursor.fetchall()
- for table in user_tables:
- print(f"- {table[0]}")
-
- connection.close()
- return True
-
- except Exception as e:
- print(f"检查表结构失败: {str(e)}")
- return False
-
-if __name__ == "__main__":
- check_user_login_table()
\ No newline at end of file
diff --git a/backend/clean_server.py b/backend/clean_server.py
deleted file mode 100644
index ac9c84c..0000000
--- a/backend/clean_server.py
+++ /dev/null
@@ -1,95 +0,0 @@
-#!/usr/bin/env python3
-print("Starting Cloud Drive Application Server...")
-
-import sys
-print(f"Python version: {sys.version}")
-
-try:
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
- print("FastAPI dependencies available")
-
- app = FastAPI(
- title="Cloud Drive API",
- description="Modern Cloud Storage Web Application Backend API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- @app.get("/")
- async def root():
- return {
- "message": "Cloud Drive API",
- "version": "1.0.1",
- "docs": "/docs",
- "health": "/api/v1/health"
- }
-
- @app.get("/health")
- async def health():
- return {"status": "healthy"}
-
- @app.get("/api/v1/health")
- async def api_health():
- import time
- return {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0"
- }
-
- @app.get("/test")
- async def test():
- return {"test": "ok", "server": "working"}
-
- try:
- from app.core.config import settings
- print("Full app module available")
- mode = "full"
- except ImportError:
- print("Using simplified mode")
- mode = "simplified"
-
- @app.get("/info")
- async def info():
- return {
- "mode": mode,
- "python_version": str(sys.version),
- "status": "running"
- }
-
- print("=" * 50)
- print("Server URLs:")
- print(" http://localhost:8080")
- print(" http://localhost:8080/docs")
- print(" http://localhost:8080/api/v1/health")
- print("=" * 50)
- print("Press Ctrl+C to stop server")
- print()
-
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8080,
- reload=False,
- access_log=True,
- log_level="info"
- )
-
-except ImportError as e:
- print(f"Dependency import failed: {e}")
- print("Please run: pip install fastapi uvicorn")
- sys.exit(1)
-except Exception as e:
- print(f"Startup failed: {e}")
- sys.exit(1)
\ No newline at end of file
diff --git a/backend/cleanup_test_user.py b/backend/cleanup_test_user.py
deleted file mode 100644
index e17ff41..0000000
--- a/backend/cleanup_test_user.py
+++ /dev/null
@@ -1,20 +0,0 @@
-from app.core.database import SessionLocal
-from app.models.user import User
-
-def cleanup_test_user():
- """清理测试用户"""
- db = SessionLocal()
- try:
- # 删除测试用户
- test_user = db.query(User).filter(User.username == "peng").first()
- if test_user:
- db.delete(test_user)
- db.commit()
- print("已删除测试用户 'peng'")
- else:
- print("未找到测试用户 'peng'")
- finally:
- db.close()
-
-if __name__ == "__main__":
- cleanup_test_user()
\ No newline at end of file
diff --git a/backend/create_tables.py b/backend/create_tables.py
deleted file mode 100644
index 98e1b99..0000000
--- a/backend/create_tables.py
+++ /dev/null
@@ -1,33 +0,0 @@
-from sqlalchemy import create_engine, text
-from app.core.config import settings
-from app.core.database import Base
-from app.models import User
-
-def create_user_table():
- try:
- print(f"连接数据库: {settings.DATABASE_URL}")
-
- # 创建数据库引擎
- engine = create_engine(settings.DATABASE_URL, echo=True)
-
- # 创建所有表
- Base.metadata.create_all(bind=engine)
- print("users表创建成功!")
-
- # 检查表是否创建成功
- with engine.connect() as conn:
- result = conn.execute(text("DESCRIBE users"))
- columns = result.fetchall()
- print("\nusers表结构:")
- for column in columns:
- print(f" {column[0]}: {column[1]} {column[2]} {column[3]} {column[4]}")
-
- print("\n数据库表创建完成!")
- return True
-
- except Exception as e:
- print(f"创建表失败: {str(e)}")
- return False
-
-if __name__ == "__main__":
- create_user_table()
\ No newline at end of file
diff --git a/backend/create_test_user.py b/backend/create_test_user.py
deleted file mode 100644
index 9bd4005..0000000
--- a/backend/create_test_user.py
+++ /dev/null
@@ -1,71 +0,0 @@
-#!/usr/bin/env python3
-"""
-创建测试用户的脚本
-"""
-
-import requests
-import hashlib
-import mysql.connector
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-def create_user_directly():
- """直接在数据库中创建用户"""
- try:
- # 连接数据库
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- # 检查用户是否已存在
- cursor.execute("SELECT id FROM users WHERE username = %s", ("testuser",))
- user = cursor.fetchone()
-
- if user:
- print(f"用户已存在,ID: {user[0]}")
- return user[0]
-
- # 创建密码哈希
- password = "TestPass123!"
- password_hash = hashlib.sha256(password.encode()).hexdigest()
-
- # 插入用户
- insert_query = """
- INSERT INTO users (username, email, password_hash, storage_quota, storage_used, is_active, is_verified)
- VALUES (%s, %s, %s, %s, %s, %s, %s)
- """
- cursor.execute(insert_query, (
- "testuser",
- "test@example.com",
- password_hash,
- 104857600, # 100MB
- 0,
- True,
- True
- ))
-
- user_id = cursor.lastrowid
- conn.commit()
-
- print(f"用户创建成功,ID: {user_id}")
- return user_id
-
- except Exception as e:
- print(f"创建用户出错: {e}")
- return None
- finally:
- if 'conn' in locals() and conn.is_connected():
- cursor.close()
- conn.close()
-
-if __name__ == "__main__":
- user_id = create_user_directly()
- if user_id:
- print(f"测试用户ID: {user_id}")
- else:
- print("创建用户失败")
\ No newline at end of file
diff --git a/backend/debug_download.py b/backend/debug_download.py
deleted file mode 100644
index b5d1f4e..0000000
--- a/backend/debug_download.py
+++ /dev/null
@@ -1,217 +0,0 @@
-#!/usr/bin/env python3
-"""
-调试文件下载接口的脚本
-"""
-
-import requests
-import mysql.connector
-import os
-import json
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-def debug_download_issue():
- """调试下载接口问题"""
-
- print("=== 调试文件下载接口 ===")
-
- # 检查数据库中的文件信息
- try:
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- # 查询所有文件
- cursor.execute("""
- SELECT id, user_id, original_filename, filename, file_path, file_size,
- file_hash, mime_type, created_at
- FROM files
- ORDER BY id
- """)
- files = cursor.fetchall()
-
- print("数据库中的文件记录:")
- for file in files:
- (id, user_id, original_filename, filename, file_path,
- file_size, file_hash, mime_type, created_at) = file
- print(f"ID: {id}, 用户ID: {user_id}, 文件名: {original_filename}")
- print(f" 存储路径: {file_path}")
- print(f" 文件大小: {file_size} bytes")
- print(f" 创建时间: {created_at}")
- print("-" * 50)
-
- cursor.close()
- conn.close()
-
- except Exception as e:
- print(f"数据库查询出错: {e}")
- return
-
- # 测试特定文件下载
- test_cases = [
- {"user_id": 3, "file_id": 2, "description": "用户3下载文件2(axurerp-48.png)"},
- {"user_id": 3, "file_id": 3, "description": "用户3下载文件3(axurerp-128.png)"},
- {"user_id": 8, "file_id": 4, "description": "用户8下载文件4(hash_demo.txt)"},
- {"user_id": 3, "file_id": 4, "description": "用户3下载文件4(权限测试)"},
- {"user_id": 1, "file_id": 2, "description": "用户1下载文件2(不存在用户)"},
- {"user_id": 3, "file_id": 999, "description": "用户3下载文件999(不存在文件)"},
- ]
-
- for test_case in test_cases:
- user_id = test_case["user_id"]
- file_id = test_case["file_id"]
- description = test_case["description"]
-
- print(f"\n=== 测试: {description} ===")
- print(f"入参: user_id={user_id}, file_id={file_id}")
-
- try:
- data = {
- "user_id": user_id,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/download",
- json=data
- )
-
- print(f"HTTP状态码: {response.status_code}")
-
- if response.status_code == 200:
- # 下载成功
- content_length = len(response.content)
- print(f"下载成功! 文件大小: {content_length} bytes")
-
- # 保存下载的文件用于检查
- save_filename = f"downloaded_user{user_id}_file{file_id}"
- if content_length > 0:
- with open(save_filename, 'wb') as f:
- f.write(response.content)
- print(f"文件已保存为: {save_filename}")
- else:
- print("警告: 下载的文件为空")
-
- # 显示内容预览
- try:
- if response.headers.get('content-type', '').startswith('text/'):
- text_content = response.content.decode('utf-8')
- preview = text_content[:100] + "..." if len(text_content) > 100 else text_content
- print(f"内容预览: {preview}")
- else:
- print("二进制文件,无法预览内容")
- except:
- print("无法预览文件内容")
-
- else:
- # 下载失败
- print(f"下载失败!")
- print(f"响应内容: {response.text}")
-
- # 尝试解析JSON错误信息
- try:
- error_data = response.json()
- print(f"错误详情: {json.dumps(error_data, indent=2, ensure_ascii=False)}")
- except:
- print("无法解析错误响应")
-
- except Exception as e:
- print(f"请求出错: {e}")
-
-def check_file_access_permission():
- """检查文件访问权限"""
-
- print("\n=== 检查文件访问权限 ===")
-
- # 检查uploads目录权限
- uploads_dir = "uploads"
- if os.path.exists(uploads_dir):
- print(f"uploads目录存在: {os.path.abspath(uploads_dir)}")
-
- # 检查目录权限
- try:
- test_file = os.path.join(uploads_dir, "test_permission.txt")
- with open(test_file, 'w') as f:
- f.write("test")
-
- if os.path.exists(test_file):
- os.remove(test_file)
- print("uploads目录读写权限正常")
- else:
- print("uploads目录权限异常")
- except Exception as e:
- print(f"无法在uploads目录写入文件: {e}")
- else:
- print("uploads目录不存在")
-
- # 检查数据库文件记录与实际文件的对应关系
- try:
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- cursor.execute("SELECT id, user_id, filename, file_path FROM files ORDER BY id")
- files = cursor.fetchall()
-
- print("\n文件记录与实际文件对应关系:")
- for (id, user_id, filename, file_path) in files:
- full_path = os.path.join("uploads", filename)
- exists = os.path.exists(full_path)
- if exists:
- size = os.path.getsize(full_path)
- print(f"ID {id}: 文件存在 ({size} bytes)")
- else:
- print(f"ID {id}: 文件不存在 - {full_path}")
-
- cursor.close()
- conn.close()
-
- except Exception as e:
- print(f"检查文件对应关系出错: {e}")
-
-def test_download_with_curl():
- """使用curl测试下载接口"""
-
- print("\n=== 使用curl测试下载接口 ===")
-
- test_cases = [
- {"user_id": 3, "file_id": 2},
- {"user_id": 3, "file_id": 3},
- ]
-
- for test_case in test_cases:
- user_id = test_case["user_id"]
- file_id = test_case["file_id"]
-
- print(f"\n测试 curl - 用户ID: {user_id}, 文件ID: {file_id}")
-
- curl_command = f'''curl -X POST "{BASE_URL}/files/download" \\
--H "Content-Type: application/json" \\
--d '{{"user_id": {user_id}, "file_id": {file_id}}}' \\
--v'''
-
- print("命令:")
- print(curl_command)
- print("(请在终端中手动执行此命令)")
-
-if __name__ == "__main__":
- debug_download_issue()
- check_file_access_permission()
- test_download_with_curl()
-
- print("\n=== 调试总结 ===")
- print("如果下载失败,可能的原因:")
- print("1. 文件不存在或已被删除")
- print("2. 用户ID与文件不匹配")
- print("3. uploads目录权限问题")
- print("4. 实际文件大小为0字节")
- print("5. 下载接口实现逻辑问题")
\ No newline at end of file
diff --git a/backend/debug_download_detailed.py b/backend/debug_download_detailed.py
deleted file mode 100644
index 37009f6..0000000
--- a/backend/debug_download_detailed.py
+++ /dev/null
@@ -1,150 +0,0 @@
-#!/usr/bin/env python3
-"""
-详细调试下载接口的每个步骤
-"""
-
-import requests
-import os
-import mysql.connector
-
-def debug_download_step_by_step():
- """逐步调试下载过程"""
-
- print("=== 详细下载接口调试 ===")
-
- # 测试参数
- user_id = 3
- file_id = 22
-
- print(f"测试参数: user_id={user_id}, file_id={file_id}")
-
- # 步骤1: 检查数据库中的文件记录
- print("\n--- 步骤1: 检查数据库记录 ---")
- try:
- conn = mysql.connector.connect(
- host='101.126.85.76',
- user='mytest_db',
- password='mytest_db',
- database='mytest_db'
- )
- cursor = conn.cursor()
-
- cursor.execute('''
- SELECT id, user_id, original_filename, filename, file_path, file_size, mime_type
- FROM files
- WHERE id = %s AND user_id = %s
- ''', (file_id, user_id))
-
- file_record = cursor.fetchone()
-
- if file_record:
- id, db_user_id, original_filename, filename, file_path, file_size, mime_type = file_record
- print(f"✅ 数据库记录找到:")
- print(f" 文件ID: {id}")
- print(f" 用户ID: {db_user_id}")
- print(f" 原始文件名: {original_filename}")
- print(f" 存储文件名: {filename}")
- print(f" 文件路径: {file_path}")
- print(f" 文件大小: {file_size} bytes")
- print(f" MIME类型: {mime_type}")
- else:
- print("❌ 数据库中没有找到匹配的记录")
- return
-
- cursor.close()
- conn.close()
-
- except Exception as e:
- print(f"❌ 数据库查询失败: {e}")
- return
-
- # 步骤2: 检查实际文件是否存在
- print("\n--- 步骤2: 检查实际文件 ---")
-
- if os.path.exists(file_path):
- actual_size = os.path.getsize(file_path)
- print(f"✅ 文件存在:")
- print(f" 路径: {os.path.abspath(file_path)}")
- print(f" 实际大小: {actual_size} bytes")
-
- if actual_size == file_size:
- print("✅ 文件大小匹配数据库记录")
- else:
- print(f"⚠️ 文件大小不匹配: 数据库{file_size} vs 实际{actual_size}")
-
- # 检查文件可读性
- if os.access(file_path, os.R_OK):
- print("✅ 文件可读")
-
- # 读取文件内容验证
- try:
- with open(file_path, 'r', encoding='utf-8') as f:
- content = f.read()
- print(f"✅ 文件内容可读,长度: {len(content)} 字符")
- print(f" 内容预览: {content[:50]}...")
- except Exception as e:
- print(f"❌ 读取文件内容失败: {e}")
- else:
- print("❌ 文件不可读 - 权限问题")
- else:
- print(f"❌ 文件不存在: {file_path}")
- return
-
- # 步骤3: 测试API下载请求
- print("\n--- 步骤3: 测试API下载请求 ---")
-
- try:
- download_data = {'user_id': user_id, 'file_id': file_id}
-
- print(f"发送请求: POST /api/v1/files/download")
- print(f"请求体: {download_data}")
-
- response = requests.post(
- 'http://localhost:8000/api/v1/files/download',
- json=download_data,
- timeout=10
- )
-
- print(f"响应状态码: {response.status_code}")
- print(f"响应头: {dict(response.headers)}")
-
- if response.status_code == 200:
- print("✅ 下载成功!")
-
- content_type = response.headers.get('content-type', '')
- content_length = len(response.content)
-
- print(f" 响应类型: {content_type}")
- print(f" 内容长度: {content_length} bytes")
-
- if content_type.startswith('text/'):
- text_content = response.text
- print(f" 文本内容长度: {len(text_content)} 字符")
- print(f" 文本内容预览: {text_content[:50]}...")
-
- # 验证内容
- if len(text_content) == file_size / 2: # 大约UTF-8字符数
- print("✅ 内容大小预期范围内")
- else:
- print(f"⚠️ 内容大小异常: 预期~{file_size//2}字符,实际{len(text_content)}字符")
- else:
- print(" 二进制内容,无法显示预览")
-
- else:
- print("❌ 下载失败!")
- print(f"错误响应: {response.text}")
-
- # 尝试解析JSON错误
- try:
- error_data = response.json()
- print(f"错误详情: {error_data}")
- except:
- print("无法解析错误响应")
-
- except Exception as e:
- print(f"❌ API请求失败: {e}")
- import traceback
- traceback.print_exc()
-
-if __name__ == "__main__":
- debug_download_step_by_step()
\ No newline at end of file
diff --git a/backend/debug_email_duplicate.py b/backend/debug_email_duplicate.py
deleted file mode 100644
index 3a13c78..0000000
--- a/backend/debug_email_duplicate.py
+++ /dev/null
@@ -1,48 +0,0 @@
-import sys
-import traceback
-from app.core.database import SessionLocal
-from app.services.user_service import UserService
-from app.schemas.auth import UserRegister
-
-def debug_email_duplicate():
- """调试邮箱重复问题"""
- try:
- print("=== 调试邮箱重复问题 ===")
-
- db = SessionLocal()
- user_service = UserService(db)
-
- # 先检查现有用户
- print("1. 检查现有用户...")
- existing_user = user_service.get_user_by_email("user@example.com")
- if existing_user:
- print(f" 找到现有用户: ID={existing_user.id}, 用户名={existing_user.username}, 邮箱={existing_user.email}")
- else:
- print(" 未找到现有用户")
-
- # 尝试创建重复邮箱的用户
- print("\n2. 尝试创建重复邮箱的用户...")
- user_data = UserRegister(
- username="test_duplicate",
- email="user@example.com", # 重复邮箱
- password="TestPass123!",
- confirm_password="TestPass123!"
- )
-
- try:
- user = user_service.create_user(user_data)
- print(f" 用户创建成功: {user.id}")
- except Exception as e:
- print(f" 用户创建失败: {e}")
- print(f" 异常类型: {type(e).__name__}")
- print(f" 异常详情: {e.detail if hasattr(e, 'detail') else '无详情'}")
- traceback.print_exc()
-
- db.close()
-
- except Exception as e:
- print(f"调试过程出错: {e}")
- traceback.print_exc()
-
-if __name__ == "__main__":
- debug_email_duplicate()
\ No newline at end of file
diff --git a/backend/debug_register.py b/backend/debug_register.py
deleted file mode 100644
index 3cae6e5..0000000
--- a/backend/debug_register.py
+++ /dev/null
@@ -1,78 +0,0 @@
-import sys
-import traceback
-from app.core.database import SessionLocal
-from app.core.security import get_password_hash
-from app.models.user import User
-
-def debug_password_hashing():
- """测试密码哈希功能"""
- try:
- print("测试密码哈希功能...")
- password = "Stringst1@"
- hashed = get_password_hash(password)
- print(f"密码哈希成功: {hashed[:50]}...")
- return True
- except Exception as e:
- print(f"密码哈希失败: {str(e)}")
- traceback.print_exc()
- return False
-
-def debug_user_creation():
- """测试用户创建"""
- try:
- print("\n测试用户创建...")
-
- db = SessionLocal()
-
- # 检查用户是否已存在
- existing_user = db.query(User).filter(User.username == "peng").first()
- if existing_user:
- print("用户 'peng' 已存在,删除旧记录...")
- db.delete(existing_user)
- db.commit()
-
- # 创建新用户
- password_hash = get_password_hash("Stringst1@")
- print(f"密码哈希生成成功")
-
- new_user = User(
- username="peng",
- email="user@example.com",
- password_hash=password_hash,
- is_active=True,
- is_verified=False
- )
-
- db.add(new_user)
- db.commit()
- db.refresh(new_user)
-
- print(f"用户创建成功! ID: {new_user.id}")
-
- # 验证用户
- user = db.query(User).filter(User.username == "peng").first()
- if user:
- print(f"用户验证成功: {user.username}, {user.email}")
-
- db.close()
- return True
-
- except Exception as e:
- print(f"用户创建失败: {str(e)}")
- traceback.print_exc()
- return False
-
-if __name__ == "__main__":
- print("=== 调试用户注册问题 ===")
-
- # 测试密码哈希
- if not debug_password_hashing():
- print("密码哈希有问题,退出")
- sys.exit(1)
-
- # 测试用户创建
- if not debug_user_creation():
- print("用户创建有问题,退出")
- sys.exit(1)
-
- print("\n=== 调试完成,一切正常 ===")
\ No newline at end of file
diff --git a/backend/debug_start.py b/backend/debug_start.py
deleted file mode 100644
index 0a57de5..0000000
--- a/backend/debug_start.py
+++ /dev/null
@@ -1,126 +0,0 @@
-#!/usr/bin/env python3
-# 带诊断信息的启动脚本
-
-import socket
-import sys
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-import uvicorn
-
-# 检查端口是否可用
-def check_port(port):
- try:
- with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
- s.bind(('0.0.0.0', port))
- return True
- except OSError:
- return False
-
-# 获取本机IP
-def get_local_ip():
- try:
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- ip = s.getsockname()[0]
- s.close()
- return ip
- except:
- return "127.0.0.1"
-
-app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-# 更宽松的CORS配置
-app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-@app.get("/")
-async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/health"
- }
-
-@app.get("/health")
-async def health():
- return {
- "status": "healthy",
- "message": "服务运行正常"
- }
-
-@app.get("/debug")
-async def debug_info():
- return {
- "python_version": sys.version,
- "working_directory": ".",
- "available_endpoints": [
- "/",
- "/health",
- "/debug",
- "/docs",
- "/redoc",
- "/openapi.json"
- ]
- }
-
-if __name__ == "__main__":
- port = 8000
-
- print("🔍 启动前诊断...")
- print(f"Python版本: {sys.version}")
- print(f"工作目录: {(await debug_info())['working_directory']}")
-
- # 检查端口
- if not check_port(port):
- print(f"❌ 端口 {port} 被占用,尝试使用端口 8001")
- port = 8001
-
- local_ip = get_local_ip()
-
- print(f"🚀 启动云盘后端服务...")
- print("=" * 60)
- print(f"📍 本地访问: http://localhost:{port}")
- print(f"📍 网络访问: http://{local_ip}:{port}")
- print(f"📚 API文档: http://localhost:{port}/docs")
- print(f"📚 网络文档: http://{local_ip}:{port}/docs")
- print(f"❤️ 健康检查: http://localhost:{port}/health")
- print(f"🔧 调试信息: http://localhost:{port}/debug")
- print(f"⏹️ 按 Ctrl+C 停止服务")
- print("=" * 60)
-
- # 启动时打印所有路由
- @app.on_event("startup")
- async def startup_event():
- print("\n📋 可用路由:")
- for route in app.routes:
- if hasattr(route, 'path') and hasattr(route, 'methods'):
- print(f" {list(route.methods)} {route.path}")
- print()
-
- try:
- uvicorn.run(
- app,
- host="0.0.0.0", # 允许外部访问
- port=port,
- reload=False,
- access_log=True, # 显示访问日志
- log_level="info"
- )
- except Exception as e:
- print(f"❌ 启动失败: {e}")
- print("\n💡 尝试的解决方案:")
- print("1. 检查防火墙设置")
- print("2. 尝试其他端口: python debug_start.py")
- print("3. 检查是否有其他程序占用端口")
\ No newline at end of file
diff --git a/backend/debug_upload_steps.py b/backend/debug_upload_steps.py
deleted file mode 100644
index b08ac9f..0000000
--- a/backend/debug_upload_steps.py
+++ /dev/null
@@ -1,126 +0,0 @@
-#!/usr/bin/env python3
-"""
-逐步调试文件上传过程的每个步骤
-"""
-
-import requests
-import io
-import os
-
-def debug_upload_step_by_step():
- """逐步调试上传过程"""
-
- print("=== 步骤1: 准备测试文件 ===")
- test_content = b"Debug upload content - step by step analysis"
- print(f"原始内容大小: {len(test_content)} bytes")
- print(f"原始内容: {test_content}")
- print()
-
- print("=== 步骤2: 创建模拟上传文件 ===")
- file_obj = io.BytesIO(test_content)
- file_obj.seek(0)
- print(f"BytesIO对象创建成功")
- print(f"当前位置: {file_obj.tell()}")
- print()
-
- print("=== 步骤3: 准备请求数据 ===")
- files = {
- 'file': ('debug_step_test.txt', file_obj, 'text/plain')
- }
- data = {
- 'user_id': 3,
- 'description': 'Step by step debug test',
- 'tags': 'debug,step',
- 'is_public': 'false'
- }
- print("请求数据准备完成")
- print()
-
- print("=== 步骤4: 发送上传请求 ===")
- try:
- response = requests.post('http://localhost:8000/api/v1/files/upload', files=files, data=data)
- print(f"响应状态码: {response.status_code}")
- print(f"响应头: {dict(response.headers)}")
-
- if response.status_code == 201:
- result = response.json()
- print("=== 步骤5: 上传成功分析 ===")
- if result.get('success'):
- file_info = result['data']['file']
- file_id = file_info['id']
- filename = file_info['filename']
- db_size = file_info['file_size']
-
- print(f"数据库记录:")
- print(f" 文件ID: {file_id}")
- print(f" 存储文件名: {filename}")
- print(f" 数据库大小: {db_size} bytes")
- print(f" 预期大小: {len(test_content)} bytes")
-
- # 检查磁盘文件
- print("\n=== 步骤6: 磁盘文件分析 ===")
- file_path = os.path.join('uploads', filename)
- print(f"预期路径: {file_path}")
-
- if os.path.exists(file_path):
- actual_size = os.path.getsize(file_path)
- print(f"实际文件大小: {actual_size} bytes")
-
- if actual_size == 0:
- print("❌ 文件损坏: 大小为0")
- elif actual_size == len(test_content):
- print("✅ 文件完整")
-
- # 验证内容
- with open(file_path, 'rb') as f:
- actual_content = f.read()
-
- if actual_content == test_content:
- print("✅ 内容完全匹配")
- else:
- print("❌ 内容不匹配")
- print(f"预期: {test_content}")
- print(f"实际: {actual_content}")
- else:
- print(f"⚠️ 大小不匹配: {actual_size} != {len(test_content)}")
-
- # 读取部分内容检查
- try:
- with open(file_path, 'rb') as f:
- actual_content = f.read(min(100, actual_size))
- print(f"实际内容预览: {actual_content}")
- except Exception as e:
- print(f"无法读取文件内容: {e}")
- else:
- print("❌ 文件不存在于磁盘")
-
- # 检查目录
- upload_dir = 'uploads'
- if os.path.exists(upload_dir):
- print(f"uploads目录存在")
- files_in_dir = os.listdir(upload_dir)
- print(f"目录中的文件: {files_in_dir}")
- else:
- print("uploads目录不存在")
-
- else:
- print("上传返回失败:", result)
- else:
- print("=== 步骤5: 上传失败分析 ===")
- print(f"HTTP状态码: {response.status_code}")
- print(f"响应内容: {response.text}")
-
- # 尝试解析错误
- try:
- error_data = response.json()
- print(f"错误详情: {error_data}")
- except:
- print("无法解析错误响应")
-
- except Exception as e:
- print(f"请求异常: {e}")
- import traceback
- traceback.print_exc()
-
-if __name__ == "__main__":
- debug_upload_step_by_step()
\ No newline at end of file
diff --git a/backend/demo_file_hash.py b/backend/demo_file_hash.py
deleted file mode 100644
index 8286e5b..0000000
--- a/backend/demo_file_hash.py
+++ /dev/null
@@ -1,227 +0,0 @@
-#!/usr/bin/env python3
-"""
-演示文件哈希原理和还原功能的脚本
-"""
-
-import hashlib
-import requests
-import os
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-USER_ID = 8
-
-def calculate_sha256_hash(file_content: bytes) -> str:
- """计算文件的SHA-256哈希值"""
- return hashlib.sha256(file_content).hexdigest()
-
-def upload_test_file_with_hash():
- """上传测试文件并展示哈希计算过程"""
-
- # 创建测试文件内容
- original_content = "Hello World! 这是演示文件哈希的测试内容。\n包含中文和English混合内容。"
-
- print(f"📄 原始文件内容:")
- print(f"'{original_content}'")
- print(f"📏 文件大小: {len(original_content.encode('utf-8'))} bytes")
- print()
-
- # 计算哈希值
- file_hash = calculate_sha256_hash(original_content.encode('utf-8'))
- print(f"🔒 计算SHA-256哈希值:")
- print(f"{file_hash}")
- print()
-
- # 上传文件
- try:
- files = {
- "file": ("demo_hash_test.txt", original_content.encode('utf-8'), "text/plain")
- }
- data = {
- "user_id": USER_ID,
- "description": "演示文件哈希功能",
- "tags": "demo,hash,test",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- files=files,
- data=data
- )
-
- if response.status_code == 201:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- server_hash = file_info["file_hash"]
- file_id = file_info["id"]
-
- print(f"✅ 文件上传成功!")
- print(f"📋 文件ID: {file_id}")
- print(f"📁 服务器存储的文件名: {file_info['filename']}")
- print(f"🔒 服务器计算的哈希值: {server_hash}")
- print()
-
- # 验证哈希值一致性
- if file_hash == server_hash:
- print(f"✅ 哈希值验证通过! 客户端和服务器计算结果一致")
- else:
- print(f"❌ 哈希值验证失败! 客户端和服务器计算结果不一致")
- print(f" 客户端: {file_hash}")
- print(f" 服务器: {server_hash}")
-
- return file_id, original_content, file_hash
- else:
- print(f"❌ 上传失败: {response.text}")
- return None, None, None
-
- except Exception as e:
- print(f"❌ 上传出错: {e}")
- return None, None, None
-
-def download_and_verify_file(file_id: int, original_content: str, original_hash: str):
- """下载文件并验证完整性"""
-
- print(f"\n📥 开始下载和验证文件...")
-
- try:
- # 下载文件
- data = {
- "user_id": USER_ID,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/download",
- json=data
- )
-
- if response.status_code == 200:
- downloaded_content = response.content.decode('utf-8')
-
- print(f"📄 下载的文件内容:")
- print(f"'{downloaded_content}'")
- print()
-
- # 验证内容完整性
- if downloaded_content == original_content:
- print(f"✅ 文件内容完整性验证通过!")
- else:
- print(f"❌ 文件内容完整性验证失败!")
- print(f" 原始内容: '{original_content}'")
- print(f" 下载内容: '{downloaded_content}'")
-
- # 计算下载文件的哈希值
- downloaded_hash = calculate_sha256_hash(downloaded_content.encode('utf-8'))
- print(f"🔒 下载文件的哈希值:")
- print(f"{downloaded_hash}")
- print()
-
- # 验证哈希值
- if downloaded_hash == original_hash:
- print(f"✅ 下载文件哈希验证通过! 文件完整性得到保证")
- else:
- print(f"❌ 下载文件哈希验证失败! 文件可能已损坏")
- print(f" 原始哈希: {original_hash}")
- print(f" 下载哈希: {downloaded_hash}")
-
- else:
- print(f"❌ 下载失败: {response.text}")
-
- except Exception as e:
- print(f"❌ 下载过程出错: {e}")
-
-def demonstrate_file_duplication():
- """演示文件去重功能"""
-
- print(f"\n🔄 演示文件去重功能...")
- print(f"尝试上传相同内容的文件,系统应该拒绝重复上传...")
-
- # 创建与之前相同内容的文件
- duplicate_content = "Hello World! 这是演示文件哈希的测试内容。\n包含中文和English混合内容。"
-
- try:
- files = {
- "file": ("duplicate_file.txt", duplicate_content.encode('utf-8'), "text/plain")
- }
- data = {
- "user_id": USER_ID,
- "description": "重复文件测试",
- "tags": "duplicate,test",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- files=files,
- data=data
- )
-
- if response.status_code == 409: # 409 Conflict 表示文件已存在
- result = response.json()
- print(f"✅ 文件去重功能正常工作!")
- print(f"📋 系统检测到文件已存在,拒绝重复上传")
- print(f"📄 原始文件名: {result.get('detail', {}).get('filename', 'Unknown')}")
- elif response.status_code == 201:
- print(f"⚠️ 文件去重功能可能未正常工作,重复上传成功了")
- else:
- print(f"❌ 测试失败: {response.text}")
-
- except Exception as e:
- print(f"❌ 测试过程出错: {e}")
-
-def show_file_location_on_server():
- """显示文件在服务器上的存储位置"""
-
- print(f"\n📁 文件在服务器上的存储位置:")
- print(f"后端上传目录: backend/uploads/")
-
- # 列出uploads目录中的文件
- try:
- if os.path.exists("backend/uploads"):
- files = os.listdir("backend/uploads")
- if files:
- print(f"当前存储的文件:")
- for file in files:
- file_path = os.path.join("backend/uploads", file)
- file_size = os.path.getsize(file_path)
- print(f" 📄 {file} ({file_size} bytes)")
-
- # 计算并显示文件的哈希值
- with open(file_path, 'rb') as f:
- content = f.read()
- file_hash = calculate_sha256_hash(content)
- print(f" 🔒 SHA-256: {file_hash}")
- else:
- print(f" (目录为空)")
- else:
- print(f" (uploads目录不存在)")
- except Exception as e:
- print(f" 无法读取目录: {e}")
-
-if __name__ == "__main__":
- print("🔐 文件哈希原理演示")
- print("=" * 50)
-
- # 1. 上传测试文件
- file_id, original_content, original_hash = upload_test_file_with_hash()
-
- if file_id:
- # 2. 下载并验证文件
- download_and_verify_file(file_id, original_content, original_hash)
-
- # 3. 演示文件去重
- demonstrate_file_duplication()
-
- # 4. 显示文件存储位置
- show_file_location_on_server()
-
- print(f"\n🎉 演示完成!")
- print(f"📚 关键知识点:")
- print(f" • SHA-256哈希值用于验证文件完整性")
- print(f" • 相同内容的文件具有相同的哈希值")
- print(f" • 系统通过哈希值检测重复文件")
- print(f" • 文件在上传、存储、下载过程中保持完整性")
- else:
- print(f"\n❌ 演示失败,无法上传测试文件")
\ No newline at end of file
diff --git a/backend/docs_fix.py b/backend/docs_fix.py
deleted file mode 100644
index de31582..0000000
--- a/backend/docs_fix.py
+++ /dev/null
@@ -1,236 +0,0 @@
-#!/usr/bin/env python3
-# 专门解决docs无法访问问题的脚本
-
-import subprocess
-import socket
-import sys
-from pathlib import Path
-
-def check_fastapi_docs():
- """检查FastAPI docs相关的常见问题"""
- print("🔍 FastAPI Docs 诊断工具")
- print("=" * 50)
-
- # 1. 检查FastAPI版本
- try:
- import fastapi
- print(f"✓ FastAPI版本: {fastapi.__version__}")
- except ImportError:
- print("❌ FastAPI未安装")
- return False
-
- # 2. 检查uvicorn版本
- try:
- import uvicorn
- print(f"✓ Uvicorn版本: {uvicorn.__version__}")
- except ImportError:
- print("❌ Uvicorn未安装")
- return False
-
- # 3. 检查端口占用
- print("\n📡 网络诊断:")
- for port in [8000, 8001, 8002]:
- sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
- sock.settimeout(1)
- result = sock.connect_ex(('127.0.0.1', port))
- if result == 0:
- print(f"❌ 端口 {port} 被占用")
- else:
- print(f"✓ 端口 {port} 可用")
- sock.close()
-
- # 4. 获取本机IP
- try:
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- local_ip = s.getsockname()[0]
- s.close()
- print(f"✓ 本机IP: {local_ip}")
- except:
- local_ip = "127.0.0.1"
- print(f"⚠️ 使用回环地址: {local_ip}")
-
- # 5. 测试不同的host配置
- print("\n🧪 测试不同配置:")
-
- test_configs = [
- ("127.0.0.1", "仅本地访问"),
- ("0.0.0.0", "允许外部访问"),
- ("localhost", "主机名访问")
- ]
-
- for host, desc in test_configs:
- print(f" {host} - {desc}")
-
- return True, local_ip
-
-def create_working_server():
- """创建可以正常访问docs的服务器"""
- print("\n🔧 创建可用的服务器配置...")
-
- server_content = '''#!/usr/bin/env python3
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-import uvicorn
-import socket
-
-app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc",
- openapi_url="/openapi.json"
-)
-
-# 确保CORS配置正确
-app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-@app.get("/")
-async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.0",
- "docs": "/docs",
- "redoc": "/redoc",
- "openapi": "/openapi.json"
- }
-
-@app.get("/health")
-async def health():
- return {
- "status": "healthy",
- "docs_available": True
- }
-
-@app.get("/test-docs")
-async def test_docs():
- """测试docs是否可用"""
- return {
- "docs_url": "/docs",
- "redoc_url": "/redoc",
- "openapi_url": "/openapi.json",
- "message": "如果看到这个页面,说明服务正常运行,请尝试访问 /docs"
- }
-
-def get_available_port():
- """获取可用端口"""
- for port in range(8000, 8010):
- try:
- with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
- s.bind(('0.0.0.0', port))
- return port
- except OSError:
- continue
- return None
-
-if __name__ == "__main__":
- port = get_available_port()
- if port is None:
- print("❌ 无法找到可用端口")
- sys.exit(1)
-
- # 获取本机IP
- try:
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- local_ip = s.getsockname()[0]
- s.close()
- except:
- local_ip = "127.0.0.1"
-
- print(f"🚀 启动服务在端口 {port}")
- print("=" * 60)
- print(f"📍 本地访问:")
- print(f" 根路径: http://localhost:{port}")
- print(f" API文档: http://localhost:{port}/docs")
- print(f" ReDoc: http://localhost:{port}/redoc")
- print(f" 测试页面: http://localhost:{port}/test-docs")
- print("")
- print(f"📍 网络访问:")
- print(f" 根路径: http://{local_ip}:{port}")
- print(f" API文档: http://{local_ip}:{port}/docs")
- print(f" ReDoc: http://{local_ip}:{port}/redoc")
- print("=" * 60)
- print("💡 如果无法访问,请检查:")
- print(" 1. 防火墙设置")
- print(" 2. 网络连接")
- print(" 3. 浏览器是否阻止访问")
- print(" 4. 尝试不同的浏览器")
- print("⏹️ 按 Ctrl+C 停止服务")
- print("=" * 60)
-
- try:
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=port,
- reload=False,
- access_log=True,
- log_level="info"
- )
- except KeyboardInterrupt:
- print("\\n服务已停止")
- except Exception as e:
- print(f"❌ 启动失败: {e}")
-'''
-
- with open('working_server.py', 'w', encoding='utf-8') as f:
- f.write(server_content)
-
- print("✓ 已创建 working_server.py")
- return True
-
-def test_curl_commands():
- """提供curl测试命令"""
- print("\n🌐 提供测试命令:")
-
- print("\\n1. 测试根路径:")
- print("curl http://localhost:8000")
-
- print("\\n2. 测试健康检查:")
- print("curl http://localhost:8000/health")
-
- print("\\n3. 测试API文档端点:")
- print("curl http://localhost:8000/docs")
-
- print("\\n4. 测试OpenAPI JSON:")
- print("curl http://localhost:8000/openapi.json")
-
- print("\\n5. 测试ReDoc:")
- print("curl http://localhost:8000/redoc")
-
-def main():
- """主函数"""
- # 检查环境
- success, local_ip = check_fastapi_docs()
-
- if not success:
- print("\\n❌ 环境检查失败,请安装必要的依赖")
- print("pip install fastapi uvicorn")
- return
-
- # 创建可用服务器
- create_working_server()
-
- # 提供测试命令
- test_curl_commands()
-
- print("\\n" + "=" * 60)
- print("🎯 解决方案:")
- print("1. 运行: python working_server.py")
- print("2. 在浏览器中访问显示的URL")
- print("3. 如果仍然无法访问,请检查:")
- print(" - 防火墙设置")
- print(" - 浏览器阻止")
- print(" - 网络代理设置")
- print("=" * 60)
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/fix_cors.sh b/backend/fix_cors.sh
deleted file mode 100644
index 2edfc9b..0000000
--- a/backend/fix_cors.sh
+++ /dev/null
@@ -1,118 +0,0 @@
-#!/bin/bash
-
-# CORS跨域问题快速修复脚本
-
-echo "=== CORS跨域问题修复工具 ==="
-
-# 检查当前目录
-if [ ! -f "main.py" ]; then
- echo "错误: 请在包含main.py的项目根目录下运行此脚本"
- exit 1
-fi
-
-echo "当前目录: $(pwd)"
-
-# 1. 更新配置文件
-echo ""
-echo "1. 更新CORS配置..."
-
-# 更新config.py
-echo "更新 app/core/config.py..."
-sed -i 's/ALLOWED_HOSTS: List\[str\] = \[.*\]/ALLOWED_HOSTS: List[str] = ["*"] # 允许所有域名访问/' app/core/config.py
-
-if [ $? -eq 0 ]; then
- echo "✓ config.py 更新成功"
-else
- echo "✗ config.py 更新失败,请手动检查"
-fi
-
-# 2. 更新.env文件
-echo ""
-echo "2. 更新环境配置..."
-if [ -f ".env" ]; then
- # 备份原始文件
- cp .env .env.backup.$(date +%Y%m%d_%H%M%S)
-
- # 更新CORS配置
- sed -i 's/ALLOWED_HOSTS=\[.*\]/ALLOWED_HOSTS=["*"]/' .env
-
- if grep -q 'ALLOWED_HOSTS=\["\*"\]' .env; then
- echo "✓ .env 文件更新成功"
- else
- echo "✗ .env 文件更新失败,请手动检查"
- fi
-else
- echo ".env 文件不存在,创建新的配置..."
- cat > .env << EOF
-# 基础配置
-ENVIRONMENT=production
-DEBUG=false
-
-# 数据库配置
-DATABASE_URL=mysql+pymysql://用户名:密码@localhost:3306/数据库名
-
-# Redis配置
-REDIS_URL=redis://localhost:6379
-
-# JWT配置
-JWT_SECRET_KEY=your-super-secret-jwt-key-change-in-production-$(date +%s)
-JWT_ALGORITHM=HS256
-JWT_EXPIRE_MINUTES=30
-
-# 文件上传配置
-UPLOAD_DIR=uploads
-MAX_FILE_SIZE=10485760
-
-# CORS配置
-ALLOWED_HOSTS=["*"]
-EOF
- echo "✓ .env 文件创建成功"
-fi
-
-# 3. 验证配置
-echo ""
-echo "3. 验证CORS配置..."
-
-# 检查config.py
-if grep -q 'ALLOWED_HOSTS: List\[str\] = \["\*"\]' app/core/config.py; then
- echo "✓ config.py CORS配置正确"
-else
- echo "✗ config.py CORS配置可能有问题"
-fi
-
-# 检查.env文件
-if grep -q 'ALLOWED_HOSTS=\["\*"\]' .env; then
- echo "✓ .env CORS配置正确"
-else
- echo "✗ .env CORS配置可能有问题"
-fi
-
-# 4. 重启服务提示
-echo ""
-echo "4. 重启服务..."
-echo "配置更新完成,请重启应用以使配置生效"
-echo ""
-echo "重启方式:"
-echo "1. 如果应用正在运行,请按 Ctrl+C 停止"
-echo "2. 然后重新启动: python main.py"
-echo "3. 或者使用启动脚本: ./start_app.sh"
-echo ""
-echo "如果使用Docker部署:"
-echo "1. 重新构建镜像: docker build -t cloud-drive-backend:latest ."
-echo "2. 重新运行容器: docker run -d -p 8002:8002 cloud-drive-backend:latest"
-
-# 5. 测试CORS
-echo ""
-echo "5. CORS测试建议..."
-echo "重启后,可以通过以下方式测试CORS:"
-echo "1. 浏览器开发者工具 -> Network -> 查看请求头"
-echo "2. 检查是否有 'Access-Control-Allow-Origin: *' 头"
-echo "3. 使用curl测试: curl -H 'Origin: http://example.com' -H 'Access-Control-Request-Method: POST' -H 'Access-Control-Request-Headers: X-Requested-With' -X OPTIONS http://localhost:8002/api/v1/health"
-
-echo ""
-echo "=== CORS修复完成 ==="
-echo ""
-echo "注意事项:"
-echo "- 允许所有域名访问 (\"*\") 仅适用于开发和测试环境"
-echo "- 生产环境建议设置具体的允许域名列表"
-echo "- 如需更安全的CORS配置,请手动修改 ALLOWED_HOSTS"
\ No newline at end of file
diff --git a/backend/fix_database_connection.sh b/backend/fix_database_connection.sh
deleted file mode 100644
index 761d7b1..0000000
--- a/backend/fix_database_connection.sh
+++ /dev/null
@@ -1,194 +0,0 @@
-#!/bin/bash
-
-# 数据库连接问题修复脚本
-
-echo "=== 数据库连接问题修复工具 ==="
-
-# 检查当前目录
-if [ ! -f "main.py" ]; then
- echo "错误: 请在包含main.py的项目根目录下运行此脚本"
- exit 1
-fi
-
-echo "当前目录: $(pwd)"
-
-# 1. 检查.env文件
-echo ""
-echo "1. 检查环境配置..."
-
-if [ -f ".env" ]; then
- echo "✓ .env 文件存在"
- echo "当前数据库配置:"
- grep "DATABASE_URL" .env || echo "DATABASE_URL 未设置"
-else
- echo "⚠ .env 文件不存在,正在创建..."
- cat > .env << EOF
-# 基础配置
-ENVIRONMENT=production
-DEBUG=false
-
-# 数据库配置 - 请根据实际情况修改
-DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db
-
-# Redis配置
-REDIS_URL=redis://localhost:6379
-
-# JWT配置
-JWT_SECRET_KEY=your-super-secret-jwt-key-change-in-production-$(date +%s)
-JWT_ALGORITHM=HS256
-JWT_EXPIRE_MINUTES=30
-
-# 文件上传配置
-UPLOAD_DIR=uploads
-MAX_FILE_SIZE=10485760
-
-# CORS配置
-ALLOWED_HOSTS=["*"]
-EOF
- echo "✓ .env 文件创建成功"
-fi
-
-# 2. 测试数据库连接
-echo ""
-echo "2. 测试数据库连接..."
-
-# 创建测试脚本
-cat > test_db_connection.py << 'EOF'
-#!/usr/bin/env python3
-import sys
-import os
-sys.path.insert(0, '.')
-
-try:
- from app.core.config import settings
- print(f"✓ 配置加载成功")
- print(f"数据库URL: {settings.DATABASE_URL}")
-
- # 测试数据库连接
- from sqlalchemy import create_engine, text
- engine = create_engine(settings.DATABASE_URL)
-
- with engine.connect() as conn:
- result = conn.execute(text("SELECT VERSION()"))
- version = result.fetchone()[0]
- print(f"✓ 数据库连接成功: MySQL {version}")
-
- # 检查数据库是否存在
- result = conn.execute(text("SHOW DATABASES LIKE 'mytest_db'"))
- if result.fetchone():
- print("✓ 数据库 'mytest_db' 存在")
- else:
- print("⚠ 数据库 'mytest_db' 不存在,需要创建")
-
-except ImportError as e:
- print(f"✗ 导入错误: {e}")
- print("请确保已安装所需依赖: pip install sqlalchemy pymysql")
- sys.exit(1)
-except Exception as e:
- print(f"✗ 数据库连接失败: {e}")
- print("")
- print "可能的原因:"
- print "1. 数据库服务器未启动"
- print "2. 网络连接问题"
- print "3. 用户名或密码错误"
- print "4. 数据库不存在"
- print "5. 防火墙阻止连接"
- sys.exit(1)
-EOF
-
-python3 test_db_connection.py
-
-if [ $? -eq 0 ]; then
- echo ""
- echo "✓ 数据库连接测试通过"
-else
- echo ""
- echo "✗ 数据库连接测试失败"
- echo ""
- echo "解决方案:"
- echo "1. 检查数据库服务是否运行"
- echo "2. 验证数据库连接参数"
- echo "3. 确认网络连通性"
- echo ""
- echo "请手动编辑 .env 文件中的 DATABASE_URL"
- echo "格式: mysql+pymysql://用户名:密码@主机:端口/数据库名"
- exit 1
-fi
-
-# 3. 检查Docker环境
-echo ""
-echo "3. 检查Docker配置..."
-
-if [ -f "docker-compose.yml" ]; then
- echo "✓ 发现 docker-compose.yml 文件"
- echo "检查Docker数据库配置..."
-
- if grep -q "mysql:" docker-compose.yml; then
- echo "⚠ 检测到Docker MySQL配置"
- echo "如果使用Docker Compose,请确保:"
- echo "1. 数据库服务已启动: docker-compose up -d mysql"
- echo "2. 数据库主机名应为 'mysql' (服务名)"
- echo "3. 确认网络配置正确"
-
- echo ""
- echo "Docker数据库连接配置示例:"
- echo "DATABASE_URL=mysql+pymysql://root:password@mysql:3306/mytest_db"
- fi
-fi
-
-# 4. 提供修复建议
-echo ""
-echo "4. 修复建议..."
-
-echo "根据错误信息,应用尝试连接到 'mysql' 主机,但配置中是IP地址。"
-echo "请检查以下配置:"
-echo ""
-
-echo "选项1: 使用外部数据库 (推荐)"
-echo "DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db"
-echo ""
-
-echo "选项2: 使用Docker数据库"
-echo "DATABASE_URL=mysql+pymysql://root:password@mysql:3306/mytest_db"
-echo ""
-
-echo "选项3: 使用本地数据库"
-echo "DATABASE_URL=mysql+pymysql://root:password@localhost:3306/mytest_db"
-echo ""
-
-# 5. 自动修复.env文件
-echo "5. 自动修复配置..."
-if [ -f ".env" ]; then
- # 备份原文件
- cp .env .env.backup.$(date +%Y%m%d_%H%M%S)
-
- # 确保使用正确的数据库URL
- if grep -q "DATABASE_URL.*mysql.*mysql:" .env; then
- echo "检测到Docker主机名配置,更新为外部数据库..."
- sed -i 's|DATABASE_URL=mysql+pymysql://.*@mysql:.*|DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db|' .env
- elif ! grep -q "DATABASE_URL.*101.126.85.76" .env; then
- echo "更新数据库连接配置..."
- sed -i 's|DATABASE_URL=.*|DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db|' .env
- fi
-
- echo "✓ 数据库配置已更新"
-fi
-
-# 6. 重启应用提示
-echo ""
-echo "6. 重启应用..."
-echo "配置更新完成,请重启应用以使配置生效"
-echo ""
-echo "重启方式:"
-echo "1. 停止当前应用 (Ctrl+C)"
-echo "2. 重新启动: python main.py"
-echo "3. 或者使用启动脚本: ./start_app.sh"
-
-echo ""
-echo "=== 数据库连接修复完成 ==="
-echo ""
-echo "如果问题仍然存在,请:"
-echo "1. 确认数据库服务器地址正确: 101.126.85.76:3306"
-echo "2. 确认用户名密码正确: mytest_db / mytest_db"
-echo "3. 确认数据库名称正确: mytest_db"
-echo "4. 测试网络连通性: telnet 101.126.85.76 3306"
\ No newline at end of file
diff --git a/backend/fix_dependencies.sh b/backend/fix_dependencies.sh
deleted file mode 100644
index fcf20ef..0000000
--- a/backend/fix_dependencies.sh
+++ /dev/null
@@ -1,151 +0,0 @@
-#!/bin/bash
-
-# 依赖修复脚本 - 解决email-validator缺失问题
-
-echo "=== 云盘后端依赖修复工具 ==="
-
-# 检查当前用户
-echo "当前用户: $(whoami)"
-echo "用户ID: $EUID"
-
-# 1. 检查Python环境
-echo ""
-echo "1. 检查Python环境..."
-if ! command -v python3 &> /dev/null; then
- echo "错误: 未找到python3"
- exit 1
-fi
-echo "✓ Python版本: $(python3 --version)"
-
-# 2. 检查pip
-echo ""
-echo "2. 检查pip..."
-if ! command -v pip3 &> /dev/null; then
- echo "错误: 未找到pip3"
- exit 1
-fi
-echo "✓ pip版本: $(pip3 --version)"
-
-# 3. 升级pip
-echo ""
-echo "3. 升级pip..."
-if [ "$EUID" -eq 0 ]; then
- pip3 install --upgrade pip
-else
- pip3 install --user --upgrade pip
-fi
-echo "✓ pip升级完成"
-
-# 4. 安装email-validator(单独安装确保成功)
-echo ""
-echo "4. 安装email-validator..."
-if [ "$EUID" -eq 0 ]; then
- pip3 install email-validator
-else
- pip3 install --user email-validator
-fi
-
-if [ $? -eq 0 ]; then
- echo "✓ email-validator安装成功"
-else
- echo "✗ email-validator安装失败"
- exit 1
-fi
-
-# 5. 验证email-validator安装
-echo ""
-echo "5. 验证email-validator安装..."
-python3 -c "import email_validator; print('✓ email-validator导入成功')" || {
- echo "✗ email-validator验证失败"
- exit 1
-}
-
-# 6. 安装其他核心依赖
-echo ""
-echo "6. 安装其他核心依赖..."
-CORE_PACKAGES="fastapi uvicorn sqlalchemy pymysql redis python-jose passlib python-multipart pydantic pydantic-settings httpx python-dotenv alembic bcrypt"
-
-if [ "$EUID" -eq 0 ]; then
- pip3 install $CORE_PACKAGES
-else
- pip3 install --user $CORE_PACKAGES
-fi
-
-if [ $? -eq 0 ]; then
- echo "✓ 核心依赖安装成功"
-else
- echo "✗ 核心依赖安装失败"
- exit 1
-fi
-
-# 7. 验证核心包导入
-echo ""
-echo "7. 验证核心包导入..."
-python3 -c "
-try:
- import fastapi, uvicorn, sqlalchemy, pymysql, redis, jose, passlib, pydantic, httpx, alembic
- print('✓ 所有核心包导入成功')
-except ImportError as e:
- print(f'✗ 包导入失败: {e}')
- exit(1)
-" || exit 1
-
-# 8. 测试Pydantic配置
-echo ""
-echo "8. 测试Pydantic配置..."
-python3 -c "
-try:
- from pydantic import BaseModel, EmailStr
- print('✓ Pydantic EmailStr类型可用')
-except Exception as e:
- print(f'✗ Pydantic EmailStr测试失败: {e}')
- print('尝试重新安装pydantic[email]...')
- exit(1)
-" || {
- echo "重新安装pydantic[email]..."
- if [ "$EUID" -eq 0 ]; then
- pip3 install "pydantic[email]"
- else
- pip3 install --user "pydantic[email]"
- fi
-}
-
-# 9. 测试应用导入
-echo ""
-echo "9. 测试应用核心模块导入..."
-python3 -c "
-import sys
-sys.path.insert(0, '.')
-try:
- from app.core.config import settings
- print('✓ 应用配置模块导入成功')
-except Exception as e:
- print(f'✗ 应用配置导入失败: {e}')
- print('可能需要检查应用代码')
- exit(1)
-" || {
- echo "应用导入测试失败,但依赖已安装"
-}
-
-echo ""
-echo "=== 依赖修复完成 ==="
-echo ""
-echo "已成功安装的包:"
-echo "- email-validator (邮件验证)"
-echo "- fastapi (Web框架)"
-echo "- uvicorn (ASGI服务器)"
-echo "- sqlalchemy (ORM)"
-echo "- pymysql (MySQL驱动)"
-echo "- redis (Redis客户端)"
-echo "- python-jose (JWT处理)"
-echo "- passlib (密码处理)"
-echo "- pydantic (数据验证)"
-echo "- httpx (HTTP客户端)"
-echo "- alembic (数据库迁移)"
-echo "- bcrypt (密码哈希)"
-echo ""
-echo "现在可以运行应用:"
-echo "python3 main.py"
-echo ""
-echo "或使用部署脚本:"
-echo "./quick_deploy_linux.sh"
\ No newline at end of file
diff --git a/backend/fix_module_import.py b/backend/fix_module_import.py
deleted file mode 100644
index cf1be3e..0000000
--- a/backend/fix_module_import.py
+++ /dev/null
@@ -1,264 +0,0 @@
-#!/usr/bin/env python3
-# 修复模块导入问题的脚本
-
-import os
-import sys
-from pathlib import Path
-
-def check_project_structure():
- """检查项目结构"""
- print("=== 检查项目结构 ===")
-
- current_dir = Path.cwd()
- print(f"当前目录: {current_dir}")
-
- # 检查app目录
- app_dir = current_dir / 'app'
- if app_dir.exists():
- print("✓ app目录存在")
- else:
- print("✗ app目录不存在")
- return False
-
- # 检查app/core目录
- core_dir = app_dir / 'core'
- if core_dir.exists():
- print("✓ app/core目录存在")
- else:
- print("✗ app/core目录不存在")
- return False
-
- # 检查关键文件
- key_files = [
- 'app/__init__.py',
- 'app/core/__init__.py',
- 'app/core/config.py',
- 'main.py'
- ]
-
- for file_path in key_files:
- if (current_dir / file_path).exists():
- print(f"✓ {file_path} 存在")
- else:
- print(f"✗ {file_path} 不存在")
- return False
-
- return True
-
-def create_missing_files():
- """创建缺失的文件"""
- print("\n=== 创建缺失文件 ===")
-
- current_dir = Path.cwd()
-
- # 创建app/__init__.py
- app_init = current_dir / 'app' / '__init__.py'
- if not app_init.exists():
- with open(app_init, 'w') as f:
- f.write('"""云盘应用包"""\n')
- print("✓ 创建 app/__init__.py")
-
- # 创建app/core/__init__.py
- core_init = current_dir / 'app' / 'core' / '__init__.py'
- if not core_init.exists():
- with open(core_init, 'w') as f:
- f.write('"""核心模块包"""\n')
- print("✓ 创建 app/core/__init__.py")
-
- # 创建app/core/config.py(如果不存在)
- config_file = current_dir / 'app' / 'core' / 'config.py'
- if not config_file.exists():
- config_content = '''from pydantic_settings import BaseSettings
-from typing import List
-import os
-
-class Settings(BaseSettings):
- # 基础配置
- ENVIRONMENT: str = "development"
- DEBUG: bool = True
-
- # 数据库配置
- DATABASE_URL: str = "mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db"
-
- # Redis配置
- REDIS_URL: str = "redis://localhost:6379"
-
- # JWT配置
- JWT_SECRET_KEY: str = "your-super-secret-jwt-key-change-in-production"
- JWT_ALGORITHM: str = "HS256"
- JWT_EXPIRE_MINUTES: int = 30
- JWT_REFRESH_EXPIRE_DAYS: int = 7
-
- # CORS配置
- ALLOWED_HOSTS: List[str] = [
- "http://localhost:3000",
- "http://localhost:3001",
- "http://localhost:3002",
- "http://localhost:3003",
- "http://localhost:3004",
- "http://127.0.0.1:3000",
- "http://127.0.0.1:3001",
- "http://127.0.0.1:3002",
- "http://127.0.0.1:3003",
- "http://127.0.0.1:3004",
- "http://172.16.16.89:3000",
- "http://172.16.16.89:3001",
- "http://172.16.16.89:3002",
- "http://172.16.16.89:3003",
- "http://172.16.16.89:3004",
- "*"
- ]
-
- # 文件上传配置
- MAX_FILE_SIZE: int = 10 * 1024 * 1024 # 10MB
- UPLOAD_DIR: str = "uploads"
- ALLOWED_EXTENSIONS: List[str] = [
- # 图片
- ".jpg", ".jpeg", ".png", ".gif", ".bmp", ".webp", ".svg",
- # 文档
- ".pdf", ".doc", ".docx", ".xls", ".xlsx", ".ppt", ".pptx",
- ".txt", ".rtf", ".csv",
- # 压缩文件
- ".zip", ".rar", ".7z", ".tar", ".gz",
- # 音频
- ".mp3", ".wav", ".flac", ".aac", ".ogg",
- # 视频
- ".mp4", ".avi", ".mkv", ".mov", ".wmv", ".flv",
- # 代码文件
- ".py", ".js", ".html", ".css", ".json", ".xml", ".yaml", ".yml",
- ".java", ".cpp", ".c", ".h", ".cs", ".php", ".rb", ".go",
- ".sql", ".sh", ".bat", ".ps1", ".md", ".log"
- ]
-
- # 安全配置
- BCRYPT_ROUNDS: int = 12
-
- class Config:
- env_file = ".env"
- case_sensitive = True
-
-settings = Settings()
-'''
- with open(config_file, 'w') as f:
- f.write(config_content)
- print("✓ 创建 app/core/config.py")
-
-def create_fixed_main_py():
- """创建修复版main.py"""
- current_dir = Path.cwd()
- main_file = current_dir / 'main.py'
-
- fixed_content = '''#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-云盘后端应用主入口
-"""
-
-import os
-import sys
-from pathlib import Path
-
-# 确保项目根目录在Python路径中
-current_dir = Path(__file__).parent
-if str(current_dir) not in sys.path:
- sys.path.insert(0, str(current_dir))
-
-try:
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- from app.core.config import settings
- from app.api.v1.endpoints import health, auth, files
- import uvicorn
- from datetime import datetime
-
- # 简单的日志打印函数
- def log_info(message):
- """打印INFO级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] INFO: {message}")
-
- def log_error(message):
- """打印ERROR级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] ERROR: {message}")
-
- def log_debug(message):
- """打印DEBUG级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] DEBUG: {message}")
-
- # 确保logs目录存在
- logs_dir = current_dir / "logs"
- logs_dir.mkdir(exist_ok=True)
-
- log_info("=== Server Starting ===")
- log_info(f"Python version: {sys.version}")
- log_info(f"Working directory: {os.getcwd()}")
- log_info("Simple print logger configured")
-
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 包含路由
- app.include_router(health.router, prefix="/api/v1", tags=["health"])
- app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
- app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
-
- @app.get("/")
- async def root():
- return {"message": "云盘应用 API", "version": "1.0.1"}
-
- if __name__ == "__main__":
- uvicorn.run(
- "main:app",
- host="0.0.0.0",
- port=8000,
- reload=True if settings.ENVIRONMENT == "development" else False
- )
-
-except ImportError as e:
- print(f"导入错误: {e}")
- print("请确保已安装所有依赖: pip install -r requirements.txt")
- print("或尝试安装基础依赖: pip install fastapi uvicorn sqlalchemy pymysql redis python-jose passlib python-multipart pydantic pydantic-settings httpx python-dotenv")
- sys.exit(1)
-except Exception as e:
- print(f"启动错误: {e}")
- sys.exit(1)
-'''
-
- with open(main_file, 'w') as f:
- f.write(fixed_content)
- print("✓ 创建修复版 main.py")
-
-def main():
- """主函数"""
- print("=== 修复模块导入问题 ===")
-
- # 检查项目结构
- if not check_project_structure():
- print("\\n项目结构有问题,开始修复...")
- create_missing_files()
- create_fixed_main_py()
-
- print("\\n=== 修复完成 ===")
- print("现在可以运行:")
- print("1. 激活虚拟环境: source venv/bin/activate")
- print("2. 安装依赖: pip install -r requirements.txt")
- print("3. 启动服务: python main.py")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/fix_permissions.sh b/backend/fix_permissions.sh
deleted file mode 100644
index 1be4639..0000000
--- a/backend/fix_permissions.sh
+++ /dev/null
@@ -1,155 +0,0 @@
-#!/bin/bash
-
-# 权限问题修复脚本
-
-echo "=== 云盘后端权限修复工具 ==="
-
-# 检查当前用户
-echo "当前用户: $(whoami)"
-echo "用户ID: $EUID"
-echo "主目录: $HOME"
-echo "当前目录: $(pwd)"
-
-# 1. 检查和创建.config目录
-echo ""
-echo "1. 检查用户配置目录..."
-if [ ! -d "$HOME/.config" ]; then
- echo "创建 .config 目录..."
- mkdir -p "$HOME/.config" || {
- echo "错误: 无法创建 .config 目录"
- exit 1
- }
- echo "✓ .config 目录创建成功"
-else
- echo "✓ .config 目录已存在"
-fi
-
-# 2. 检查和创建systemd用户目录
-echo ""
-echo "2. 检查systemd用户目录..."
-SYSTEMD_USER_DIR="$HOME/.config/systemd/user"
-
-if [ ! -d "$SYSTEMD_USER_DIR" ]; then
- echo "创建systemd用户目录..."
- mkdir -p "$SYSTEMD_USER_DIR" || {
- echo "错误: 无法创建systemd用户目录"
- echo "尝试使用sudo创建..."
- sudo -u $(whoami) mkdir -p "$SYSTEMD_USER_DIR" || {
- echo "错误: 无法创建systemd用户目录,尝试使用临时目录"
- SYSTEMD_USER_DIR="/tmp/$(whoami)-systemd"
- mkdir -p "$SYSTEMD_USER_DIR"
- echo "使用临时目录: $SYSTEMD_USER_DIR"
- }
- }
- echo "✓ systemd用户目录创建成功: $SYSTEMD_USER_DIR"
-else
- echo "✓ systemd用户目录已存在: $SYSTEMD_USER_DIR"
-fi
-
-# 3. 检查目录权限
-echo ""
-echo "3. 检查目录权限..."
-echo ".config 目录权限: $(ls -ld $HOME/.config | awk '{print $1,$3,$4}')"
-echo "systemd用户目录权限: $(ls -ld $SYSTEMD_USER_DIR | awk '{print $1,$3,$4}')"
-
-# 4. 测试写入权限
-echo ""
-echo "4. 测试写入权限..."
-TEST_FILE="$SYSTEMD_USER_DIR/.test_write"
-if touch "$TEST_FILE" 2>/dev/null; then
- echo "✓ 写入权限正常"
- rm -f "$TEST_FILE"
-else
- echo "✗ 写入权限不足,尝试修复..."
- chmod 755 "$HOME/.config" 2>/dev/null
- chmod 755 "$SYSTEMD_USER_DIR" 2>/dev/null
-
- if touch "$TEST_FILE" 2>/dev/null; then
- echo "✓ 权限修复成功"
- rm -f "$TEST_FILE"
- else
- echo "✗ 权限修复失败"
- echo "可能的解决方案:"
- echo "1. 检查磁盘空间: df -h"
- echo "2. 检查用户配额: quota -u $(whoami)"
- echo "3. 检查文件系统权限: mount | grep home"
- echo "4. 联系系统管理员"
- exit 1
- fi
-fi
-
-# 5. 检查systemd用户服务是否启用
-echo ""
-echo "5. 检查systemd用户服务..."
-if systemctl --user list-units --type=service --state=running &>/dev/null; then
- echo "✓ systemd用户服务可用"
-else
- echo "⚠ systemd用户服务可能不可用"
- echo "尝试启用用户systemd服务..."
-
- # 对于某些系统,需要启用linger
- if command -v loginctl &> /dev/null; then
- if loginctl show-user $(whoami) | grep -q "Linger=no"; then
- echo "启用用户linger服务..."
- loginctl enable-linger $(whoami) || echo "无法启用linger,可能需要管理员权限"
- fi
- fi
-fi
-
-# 6. 创建测试服务文件
-echo ""
-echo "6. 创建测试服务文件..."
-SERVICE_FILE="$SYSTEMD_USER_DIR/cloud-drive.service"
-
-cat > "$SERVICE_FILE" << EOF
-[Unit]
-Description=Cloud Drive Backend Service
-Documentation=https://github.com/your-repo/cloud-drive
-After=network.target
-
-[Service]
-Type=simple
-WorkingDirectory=$(pwd)
-ExecStart=$(pwd)/venv/bin/python $(pwd)/main.py
-Restart=always
-RestartSec=10
-StandardOutput=journal
-StandardError=journal
-SyslogIdentifier=cloud-drive
-
-[Install]
-WantedBy=default.target
-EOF
-
-if [ -f "$SERVICE_FILE" ]; then
- echo "✓ 服务文件创建成功: $SERVICE_FILE"
- echo "文件权限: $(ls -l $SERVICE_FILE | awk '{print $1,$3,$4}')"
-else
- echo "✗ 服务文件创建失败"
- exit 1
-fi
-
-# 7. 测试systemd命令
-echo ""
-echo "7. 测试systemd命令..."
-if systemctl --user daemon-reload 2>/dev/null; then
- echo "✓ systemd用户服务重载成功"
-else
- echo "⚠ systemd用户服务重载失败"
- echo "错误信息: $(systemctl --user daemon-reload 2>&1)"
-fi
-
-echo ""
-echo "=== 权限修复完成 ==="
-echo ""
-echo "服务管理命令:"
-echo "重载服务: systemctl --user daemon-reload"
-echo "启用服务: systemctl --user enable cloud-drive"
-echo "启动服务: systemctl --user start cloud-drive"
-echo "查看状态: systemctl --user status cloud-drive"
-echo "查看日志: journalctl --user -u cloud-drive -f"
-echo ""
-echo "如果systemd命令不可用,请使用手动管理脚本:"
-echo "启动: ./start.sh"
-echo "停止: ./stop.sh"
-echo "状态: ./status.sh"
\ No newline at end of file
diff --git a/backend/fix_python_shared_lib.sh b/backend/fix_python_shared_lib.sh
deleted file mode 100644
index 74870cd..0000000
--- a/backend/fix_python_shared_lib.sh
+++ /dev/null
@@ -1,244 +0,0 @@
-#!/bin/bash
-# Python共享库问题修复脚本
-
-echo "=== Python共享库问题修复脚本 ==="
-
-# 检测Python环境
-echo "1. 检测Python环境..."
-python3 --version
-echo "Python路径: $(which python3)"
-
-# 检测是否支持共享库
-echo ""
-echo "2. 检测共享库支持..."
-if python3 -c "import sys; print('Shared library support:', hasattr(sys, 'getdlopenflags'))" 2>/dev/null; then
- echo "✓ Python支持共享库"
-else
- echo "✗ Python不支持共享库"
-fi
-
-# 尝试方案一:使用修复的配置文件
-echo ""
-echo "3. 方案一:使用修复的配置文件打包..."
-
-# 下载修复的配置文件
-cat > build_noshared.spec << 'EOF'
-# -*- mode: python ; coding: utf-8 -*-
-# 适用于没有共享库的Python环境的PyInstaller配置
-
-import sys
-from pathlib import Path
-
-# 项目根目录
-ROOT_DIR = Path.cwd()
-
-# 需要包含的数据文件
-datas = [
- (str(ROOT_DIR / 'app'), 'app'), # 包含整个app目录
- ('.env.example', '.'), # 包含环境配置示例文件
-]
-
-# 可选数据文件(如果存在才包含)
-optional_files = [
- ('database', 'database'), # 包含数据库相关文件
-]
-
-# 添加可选数据文件
-for src, dst in optional_files:
- src_path = ROOT_DIR / src
- if src_path.exists():
- datas.append((src, dst))
- print(f"包含可选数据文件: {src}")
- else:
- print(f"跳过可选数据文件: {src} (不存在)")
-
-# 隐式导入的模块
-hiddenimports = [
- 'fastapi', 'uvicorn', 'starlette', 'pydantic', 'sqlalchemy',
- 'passlib', 'python_jose', 'pymysql', 'redis', 'httpx', 'loguru',
- 'python_dotenv', 'alembic', 'email.utils', 'yaml', 'toml',
- 'json', 'base64', 'hashlib', 'datetime', 'uuid', 'os', 'sys',
- 'pathlib', 'typing', 'collections', 'itertools', 'functools',
- 'time', 'math', 're', 'socket', 'threading', 'asyncio',
- 'cryptography', 'jinja2', 'mimetypes', 'tempfile', 'shutil',
- 'argparse', 'codecs', 'encodings', 'random', 'secrets',
- 'urllib', 'http', 'signal', 'multiprocessing'
-]
-
-block_cipher = None
-
-a = Analysis(
- ['main.py'],
- pathex=[str(ROOT_DIR)],
- binaries=[],
- datas=datas,
- hiddenimports=hiddenimports,
- hookspath=[],
- hooksconfig={},
- runtime_hooks=[],
- excludes=[
- 'Pillow', 'numpy', 'scipy', 'matplotlib', 'pandas',
- 'torch', 'tensorflow', 'jupyter', 'notebook', 'ipython',
- 'sphinx', 'pytest', 'setuptools', 'pip', 'wheel',
- 'PyQt5', 'PyQt6', 'PySide2', 'PySide6', 'tkinter'
- ],
- win_no_prefer_redirects=False,
- win_private_assemblies=False,
- cipher=block_cipher,
- noarchive=False,
-)
-
-pyz = PYZ(a.pure, a.zipped_data, cipher=block_cipher)
-
-exe = EXE(
- pyz,
- a.scripts,
- a.binaries,
- a.zipfiles,
- a.datas,
- [],
- name='cloud-drive-server',
- debug=False,
- bootloader_ignore_signals=False,
- strip=False,
- upx=False,
- upx_exclude=[],
- runtime_tmpdir=None,
- console=True,
- disable_windowed_traceback=False,
- argv_emulation=False,
- target_arch=None,
- codesign_identity=None,
- entitlements_file=None,
-)
-EOF
-
-echo "✓ 已创建 build_noshared.spec"
-
-# 尝试打包
-echo "尝试使用修复配置打包..."
-if pyinstaller --clean --noupx build_noshared.spec; then
- echo "✓ 方案一成功:可执行文件已生成"
- echo "文件位置: dist/cloud-drive-server"
-
- # 创建部署包
- mkdir -p deploy
- cp dist/cloud-drive-server deploy/
- cp .env.example deploy/
-
- # 创建启动脚本
- cat > deploy/start.sh << 'STARTEOF'
-#!/bin/bash
-cd "$(dirname "$0")"
-if [ ! -f ".env" ]; then
- cp .env.example .env
-fi
-mkdir -p logs uploads
-./cloud-drive-server
-STARTEOF
- chmod +x deploy/start.sh
-
- echo "✓ 部署包已创建: deploy/"
- echo "现在可以运行: cd deploy && ./start.sh"
- exit 0
-else
- echo "✗ 方案一失败"
-fi
-
-# 尝试方案二:单文件模式
-echo ""
-echo "4. 方案二:尝试单文件模式..."
-if pyinstaller --clean --noupx --onefile main.py; then
- echo "✓ 方案二成功:单文件可执行文件已生成"
-
- mkdir -p deploy
- cp dist/main deploy/cloud-drive-server
- cp .env.example deploy/
-
- cat > deploy/start.sh << 'STARTEOF'
-#!/bin/bash
-cd "$(dirname "$0")"
-if [ ! -f ".env" ]; then
- cp .env.example .env
-fi
-mkdir -p logs uploads
-./cloud-drive-server
-STARTEOF
- chmod +x deploy/start.sh
-
- echo "✓ 部署包已创建: deploy/"
- exit 0
-else
- echo "✗ 方案二失败"
-fi
-
-# 尝试方案三:Python源代码部署
-echo ""
-echo "5. 方案三:创建Python源代码部署包..."
-
-mkdir -p deploy
-cp -r app deploy/
-cp main.py deploy/
-cp requirements.txt deploy/
-cp .env.example deploy/
-
-# 创建启动脚本
-cat > deploy/start.sh << 'STARTEOF'
-#!/bin/bash
-cd "$(dirname "$0")"
-
-# 检查Python环境
-if ! command -v python3 &> /dev/null; then
- echo "错误: 未找到python3"
- exit 1
-fi
-
-# 检查虚拟环境
-if [ ! -d "venv" ]; then
- echo "创建虚拟环境..."
- python3 -m venv venv
- source venv/bin/activate
- pip install -r requirements.txt
-else
- source venv/bin/activate
-fi
-
-# 检查环境文件
-if [ ! -f ".env" ]; then
- cp .env.example .env
- echo "已创建 .env 文件,请根据需要修改配置"
-fi
-
-# 创建必要目录
-mkdir -p logs uploads
-
-# 启动服务
-echo "启动云盘后端服务..."
-python main.py
-STARTEOF
-
-chmod +x deploy/start.sh
-
-# 创建安装脚本
-cat > deploy/install.sh << 'INSTALLEOF'
-#!/bin/bash
-INSTALL_DIR="$HOME/cloud-drive"
-echo "安装云盘后端服务到 $INSTALL_DIR"
-mkdir -p "$INSTALL_DIR"
-cp -r * "$INSTALL_DIR/"
-echo "安装完成!"
-echo "进入目录: cd $INSTALED_DIR"
-echo "启动服务: ./start.sh"
-INSTALLEOF
-
-chmod +x deploy/install.sh
-
-echo "✓ 方案三成功:Python源代码部署包已创建"
-echo "部署位置: deploy/"
-echo "使用方法:"
-echo " 1. cd deploy"
-echo " 2. ./start.sh"
-
-echo ""
-echo "=== 修复完成 ==="
-echo "建议使用方案三(Python源代码部署),这最稳定可靠。"
\ No newline at end of file
diff --git a/backend/fix_venv.sh b/backend/fix_venv.sh
deleted file mode 100644
index 1a16359..0000000
--- a/backend/fix_venv.sh
+++ /dev/null
@@ -1,78 +0,0 @@
-#!/bin/bash
-
-# 虚拟环境修复脚本
-
-echo "=== 虚拟环境修复工具 ==="
-
-# 检查当前目录
-if [ ! -f "main.py" ]; then
- echo "错误: 请在包含main.py的项目根目录下运行此脚本"
- exit 1
-fi
-
-echo "当前目录: $(pwd)"
-echo "当前Python版本: $(python3 --version)"
-
-# 备份现有虚拟环境(如果存在)
-if [ -d "venv" ]; then
- echo "发现现有虚拟环境,正在备份..."
- mv venv venv_backup_$(date +%Y%m%d_%H%M%S)
- echo "✓ 现有虚拟环境已备份"
-fi
-
-# 创建新的虚拟环境
-echo "正在创建新的虚拟环境..."
-python3 -m venv venv
-
-if [ $? -eq 0 ]; then
- echo "✓ 虚拟环境创建成功"
-else
- echo "✗ 虚拟环境创建失败"
- echo "可能的原因:"
- echo "1. python3-venv 未安装"
- echo "2. 权限不足"
- echo "3. 磁盘空间不足"
- echo ""
- echo "尝试安装 python3-venv:"
- echo "sudo apt-get install python3-venv # Ubuntu/Debian"
- echo "sudo yum install python3-virtualenv # CentOS/RHEL"
- exit 1
-fi
-
-# 验证虚拟环境文件
-echo "验证虚拟环境文件..."
-if [ -f "venv/bin/activate" ]; then
- echo "✓ 激活脚本存在: venv/bin/activate"
-
- # 显示虚拟环境信息
- echo "虚拟环境内容:"
- ls -la venv/bin/ | head -5
-
- # 测试激活
- echo "测试虚拟环境激活..."
- source venv/bin/activate
- echo "✓ 虚拟环境激活成功"
- echo "Python路径: $(which python)"
- echo "Python版本: $(python --version)"
-
- # 升级pip
- echo "升级pip..."
- pip install --upgrade pip
- echo "✓ pip升级完成"
-
-else
- echo "✗ 激活脚本不存在"
- echo "显示venv目录内容:"
- ls -la venv/ 2>/dev/null || echo "venv目录为空或不存在"
- exit 1
-fi
-
-echo ""
-echo "=== 修复完成 ==="
-echo "虚拟环境已成功创建并可以正常使用"
-echo ""
-echo "下一步操作:"
-echo "1. 重新运行部署脚本: ./deploy_linux.sh"
-echo "2. 或者手动激活并安装依赖:"
-echo " source venv/bin/activate"
-echo " pip install -r requirements.txt"
\ No newline at end of file
diff --git a/backend/fixed_file_upload.py b/backend/fixed_file_upload.py
deleted file mode 100644
index f306327..0000000
--- a/backend/fixed_file_upload.py
+++ /dev/null
@@ -1,118 +0,0 @@
-#!/usr/bin/env python3
-"""
-修复版文件上传测试 - 绕过有问题的业务逻辑
-"""
-
-import requests
-import os
-import uuid
-import hashlib
-import time
-
-def fixed_upload_file():
- """修复版文件上传"""
-
- print("=== 修复版5KB文件上传测试 ===")
-
- # 1. 生成5KB测试内容
- content = "Fixed upload test content. " * 200 # 约5KB
- content = content[:5000] # 确保正好5000字符
-
- print(f"1. 生成测试内容: {len(content)} 字符")
-
- # 2. 先通过API上传获取文件ID和记录
- test_file_path = 'temp_test_upload.txt'
- with open(test_file_path, 'w', encoding='utf-8') as f:
- f.write(content)
-
- print("2. 创建临时测试文件")
-
- # 3. 通过API上传(这会创建数据库记录但文件为0字节)
- with open(test_file_path, 'rb') as f:
- files = {
- 'file': ('fixed_test_5kb.txt', f, 'text/plain')
- }
- data = {
- 'user_id': 3,
- 'description': 'Fixed upload test',
- 'tags': 'test,fixed',
- 'is_public': 'false'
- }
-
- response = requests.post('http://localhost:8000/api/v1/files/upload', files=files, data=data)
-
- if response.status_code == 201:
- result = response.json()
- if result.get('success'):
- file_info = result['data']['file']
- file_id = file_info['id']
- filename = file_info['filename']
-
- print(f"3. API上传成功 - 文件ID: {file_id}, 文件名: {filename}")
-
- # 4. 手动修复文件内容
- file_path = os.path.join('uploads', filename)
- print(f"4. 手动修复文件: {file_path}")
-
- # 直接写入正确内容
- with open(file_path, 'w', encoding='utf-8') as f:
- f.write(content)
-
- # 5. 验证修复结果
- if os.path.exists(file_path):
- actual_size = os.path.getsize(file_path)
- print(f"5. 修复后文件大小: {actual_size} bytes")
-
- if actual_size == len(content.encode('utf-8')):
- print("SUCCESS: 文件修复成功!")
-
- # 验证内容
- with open(file_path, 'r', encoding='utf-8') as f:
- read_content = f.read()
-
- if read_content == content:
- print("SUCCESS: 内容验证通过!")
-
- # 6. 测试下载
- print("6. 测试下载功能...")
- download_data = {'user_id': 3, 'file_id': file_id}
- download_response = requests.post('http://localhost:8000/api/v1/files/download', json=download_data)
-
- if download_response.status_code == 200:
- downloaded_content = download_response.content.decode('utf-8')
- if downloaded_content == content:
- print("SUCCESS: 下载功能正常!")
- print(f"下载内容长度: {len(downloaded_content)} 字符")
- return True, file_id, filename
- else:
- print("ERROR: 下载内容不匹配!")
- else:
- print(f"ERROR: 下载失败 - {download_response.status_code}")
- else:
- print("ERROR: 内容验证失败!")
- else:
- print(f"ERROR: 修复后大小不匹配: {actual_size}")
- else:
- print("ERROR: 修复后文件不存在!")
- else:
- print("API上传失败:", result)
- else:
- print("API上传失败:", response.text)
-
- # 清理临时文件
- if os.path.exists(test_file_path):
- os.remove(test_file_path)
-
- return False, None, None
-
-if __name__ == "__main__":
- success, file_id, filename = fixed_upload_file()
-
- if success:
- print(f"\n=== 修复成功 ===")
- print(f"可以使用的文件ID: {file_id}")
- print(f"文件名: {filename}")
- print(f"现在可以通过正常方式下载这个完整的5KB文件!")
- else:
- print(f"\n=== 修复失败 ===")
- print("需要进一步调试文件保存逻辑")
\ No newline at end of file
diff --git a/backend/install.sh b/backend/install.sh
deleted file mode 100644
index fbfee8b..0000000
--- a/backend/install.sh
+++ /dev/null
@@ -1,118 +0,0 @@
-#!/bin/bash
-# 云盘后端服务安装脚本
-
-set -e
-
-# 配置变量
-SERVICE_NAME="cloud-drive"
-SERVICE_USER="cloud-drive"
-INSTALL_DIR="/opt/cloud-drive"
-SERVICE_FILE="cloud-drive.service"
-
-echo "=== 云盘后端服务安装脚本 ==="
-
-# 检查是否为root用户
-if [ "$EUID" -ne 0 ]; then
- echo "错误: 请使用root权限运行此脚本"
- exit 1
-fi
-
-# 检查系统
-if [ -f /etc/os-release ]; then
- . /etc/os-release
- echo "检测到系统: $NAME $VERSION"
-else
- echo "警告: 无法检测系统版本"
-fi
-
-# 创建服务用户
-echo "创建服务用户..."
-if ! id "$SERVICE_USER" &>/dev/null; then
- useradd -r -s /bin/false -d "$INSTALL_DIR" "$SERVICE_USER"
- echo "✓ 创建用户 $SERVICE_USER"
-else
- echo "✓ 用户 $SERVICE_USER 已存在"
-fi
-
-# 创建安装目录
-echo "创建安装目录..."
-mkdir -p "$INSTALL_DIR"
-mkdir -p "$INSTALL_DIR/logs"
-mkdir -p "$INSTALL_DIR/uploads"
-
-# 复制文件
-echo "复制服务文件..."
-if [ -f "deploy/cloud-drive-server" ]; then
- cp deploy/cloud-drive-server "$INSTALL_DIR/"
- chmod +x "$INSTALL_DIR/cloud-drive-server"
- echo "✓ 复制可执行文件"
-else
- echo "错误: 未找到可执行文件,请先运行打包脚本"
- exit 1
-fi
-
-if [ -f "deploy/.env.example" ]; then
- cp deploy/.env.example "$INSTALL_DIR/.env.example"
- echo "✓ 复制配置文件模板"
-fi
-
-# 设置权限
-echo "设置文件权限..."
-chown -R "$SERVICE_USER:$SERVICE_USER" "$INSTALL_DIR"
-chmod 755 "$INSTALL_DIR"
-chmod 755 "$INSTALL_DIR/cloud-drive-server"
-chmod 755 "$INSTALL_DIR/logs"
-chmod 755 "$INSTALL_DIR/uploads"
-
-# 安装systemd服务
-echo "安装systemd服务..."
-cp "$SERVICE_FILE" "/etc/systemd/system/"
-systemctl daemon-reload
-systemctl enable "$SERVICE_NAME"
-echo "✓ 服务已安装并启用"
-
-# 配置防火墙(如果存在)
-echo "配置防火墙..."
-if command -v firewall-cmd &> /dev/null; then
- firewall-cmd --permanent --add-port=8000/tcp
- firewall-cmd --reload
- echo "✓ 防火墙配置完成 (firewalld)"
-elif command -v ufw &> /dev/null; then
- ufw allow 8000/tcp
- echo "✓ 防火墙配置完成 (ufw)"
-else
- echo "注意: 未检测到防火墙管理工具,请手动开放8000端口"
-fi
-
-# 创建日志轮转配置
-echo "配置日志轮转..."
-cat > /etc/logrotate.d/cloud-drive << EOF
-$INSTALL_DIR/logs/*.log {
- daily
- missingok
- rotate 30
- compress
- delaycompress
- notifempty
- create 644 $SERVICE_USER $SERVICE_USER
- postrotate
- systemctl reload cloud-drive || true
- endscript
-}
-EOF
-echo "✓ 日志轮转配置完成"
-
-# 提示配置
-echo ""
-echo "=== 安装完成 ==="
-echo "安装目录: $INSTALL_DIR"
-echo ""
-echo "下一步操作:"
-echo "1. 编辑配置文件: nano $INSTALL_DIR/.env"
-echo "2. 启动服务: systemctl start $SERVICE_NAME"
-echo "3. 查看状态: systemctl status $SERVICE_NAME"
-echo "4. 查看日志: journalctl -u $SERVICE_NAME -f"
-echo ""
-echo "服务将在以下地址提供API:"
-echo "- API文档: http://$(hostname -I | awk '{print $1}'):8000/docs"
-echo "- 健康检查: http://$(hostname -I | awk '{print $1}'):8000/api/v1/health"
\ No newline at end of file
diff --git a/backend/install_deps_root.sh b/backend/install_deps_root.sh
deleted file mode 100644
index cd02f9d..0000000
--- a/backend/install_deps_root.sh
+++ /dev/null
@@ -1,57 +0,0 @@
-#!/bin/bash
-
-# Root用户依赖安装脚本
-
-echo "=== Root用户依赖安装脚本 ==="
-
-# 检查是否为root用户
-if [ "$EUID" -ne 0 ]; then
- echo "请使用root权限运行此脚本"
- echo "命令: sudo $0"
- exit 1
-fi
-
-echo "检测到root用户,开始安装依赖..."
-
-# 1. 升级pip
-echo "1. 升级pip..."
-pip3 install --upgrade pip
-
-# 2. 安装email-validator
-echo "2. 安装email-validator..."
-pip3 install email-validator
-
-# 3. 安装核心依赖
-echo "3. 安装核心依赖..."
-pip3 install fastapi uvicorn sqlalchemy pymysql redis python-jose passlib python-multipart pydantic pydantic-settings httpx python-dotenv loguru alembic bcrypt
-
-# 4. 验证安装
-echo "4. 验证安装..."
-python3 -c "
-import sys
-packages = ['email_validator', 'fastapi', 'uvicorn', 'sqlalchemy', 'pymysql', 'redis', 'jose', 'passlib', 'pydantic', 'httpx', 'alembic']
-success = True
-for pkg in packages:
- try:
- __import__(pkg)
- print(f'✓ {pkg}')
- except ImportError as e:
- print(f'✗ {pkg}: {e}')
- success = False
-
-if success:
- print('\\n✓ 所有依赖安装成功!')
-else:
- print('\\n✗ 部分依赖安装失败')
- sys.exit(1)
-"
-
-if [ $? -eq 0 ]; then
- echo ""
- echo "=== 安装完成 ==="
- echo "现在可以启动应用:"
- echo "python3 main.py"
-else
- echo "安装失败,请检查错误信息"
- exit 1
-fi
\ No newline at end of file
diff --git a/backend/install_user.sh b/backend/install_user.sh
deleted file mode 100644
index 4731319..0000000
--- a/backend/install_user.sh
+++ /dev/null
@@ -1,154 +0,0 @@
-#!/bin/bash
-# 云盘后端服务用户级安装脚本(无需sudo权限)
-
-set -e
-
-# 配置变量
-SERVICE_NAME="cloud-drive"
-INSTALL_DIR="$HOME/cloud-drive"
-LOG_DIR="$HOME/.local/share/cloud-drive/logs"
-UPLOAD_DIR="$HOME/.local/share/cloud-drive/uploads"
-
-echo "=== 云盘后端服务用户级安装脚本 ==="
-
-# 检查系统
-if [ -f /etc/os-release ]; then
- . /etc/os-release
- echo "检测到系统: $NAME $VERSION"
-else
- echo "警告: 无法检测系统版本"
-fi
-
-# 创建安装目录
-echo "创建安装目录..."
-mkdir -p "$INSTALL_DIR"
-mkdir -p "$LOG_DIR"
-mkdir -p "$UPLOAD_DIR"
-
-# 复制文件
-echo "复制服务文件..."
-if [ -f "deploy/cloud-drive-server" ]; then
- cp deploy/cloud-drive-server "$INSTALL_DIR/"
- chmod +x "$INSTALL_DIR/cloud-drive-server"
- echo "✓ 复制可执行文件"
-else
- echo "错误: 未找到可执行文件,请先运行打包脚本"
- exit 1
-fi
-
-if [ -f "deploy/.env.example" ]; then
- cp deploy/.env.example "$INSTALL_DIR/.env.example"
- echo "✓ 复制配置文件模板"
-fi
-
-# 创建启动脚本
-echo "创建启动脚本..."
-cat > "$INSTALL_DIR/start.sh" << EOF
-#!/bin/bash
-# 云盘后端服务启动脚本(用户级)
-
-# 设置环境变量
-export PYTHONPATH=\${PYTHONPATH}:$(dirname "$0")
-
-# 进入脚本所在目录
-cd "\$(dirname "$0")"
-
-# 检查环境文件
-if [ ! -f ".env" ]; then
- echo "警告: .env 文件不存在,将使用默认配置"
- if [ -f ".env.example" ]; then
- cp .env.example .env
- echo "已复制 .env.example 为 .env,请根据需要修改配置"
- fi
-fi
-
-# 启动服务
-echo "启动云盘后端服务..."
-./cloud-drive-server
-EOF
-
-chmod +x "$INSTALL_DIR/start.sh"
-echo "✓ 创建启动脚本"
-
-# 创建停止脚本
-cat > "$INSTALL_DIR/stop.sh" << 'EOF'
-#!/bin/bash
-# 云盘后端服务停止脚本
-
-echo "停止云盘后端服务..."
-pkill -f cloud-drive-server || echo "服务未运行"
-EOF
-
-chmod +x "$INSTALL_DIR/stop.sh"
-echo "✓ 创建停止脚本"
-
-# 创建状态检查脚本
-cat > "$INSTALL_DIR/status.sh" << 'EOF'
-#!/bin/bash
-# 云盘后端服务状态检查脚本
-
-if pgrep -f cloud-drive-server > /dev/null; then
- echo "云盘后端服务正在运行"
- echo "进程ID: $(pgrep -f cloud-drive-server)"
- echo "端口: 8000"
-else
- echo "云盘后端服务未运行"
-fi
-EOF
-
-chmod +x "$INSTALL_DIR/status.sh"
-echo "✓ 创建状态检查脚本"
-
-# 创建systemd用户服务文件(可选)
-echo "创建systemd用户服务文件..."
-mkdir -p "$HOME/.config/systemd/user"
-cat > "$HOME/.config/systemd/user/$SERVICE_NAME.service" << EOF
-[Unit]
-Description=Cloud Drive Backend Service (User)
-Documentation=https://github.com/your-repo/cloud-drive
-After=network.target
-
-[Service]
-Type=simple
-WorkingDirectory=$INSTALL_DIR
-ExecStart=$INSTALL_DIR/cloud-drive-server
-Restart=always
-RestartSec=10
-StandardOutput=journal
-StandardError=journal
-SyslogIdentifier=cloud-drive
-
-[Install]
-WantedBy=default.target
-EOF
-
-echo "✓ 创建systemd用户服务文件"
-
-# 重载systemd用户服务
-systemctl --user daemon-reload
-echo "✓ systemd用户服务已加载"
-
-# 提示配置
-echo ""
-echo "=== 用户级安装完成 ==="
-echo "安装目录: $INSTALL_DIR"
-echo "日志目录: $LOG_DIR"
-echo "上传目录: $UPLOAD_DIR"
-echo ""
-echo "手动启动方式:"
-echo "1. 编辑配置文件: nano $INSTALL_DIR/.env"
-echo "2. 启动服务: $INSTALL_DIR/start.sh"
-echo "3. 查看状态: $INSTALL_DIR/status.sh"
-echo "4. 停止服务: $INSTALL_DIR/stop.sh"
-echo ""
-echo "systemd用户服务方式:"
-echo "1. 启用服务: systemctl --user enable $SERVICE_NAME"
-echo "2. 启动服务: systemctl --user start $SERVICE_NAME"
-echo "3. 查看状态: systemctl --user status $SERVICE_NAME"
-echo "4. 查看日志: journalctl --user -u $SERVICE_NAME -f"
-echo ""
-echo "服务将在以下地址提供API:"
-echo "- API文档: http://localhost:8000/docs"
-echo "- 健康检查: http://localhost:8000/api/v1/health"
-echo ""
-echo "注意: 如需绑定到特权端口(如80)或访问系统资源,请使用sudo运行install.sh"
\ No newline at end of file
diff --git a/backend/package-app.py b/backend/package-app.py
deleted file mode 100644
index 23493ad..0000000
--- a/backend/package-app.py
+++ /dev/null
@@ -1,200 +0,0 @@
-#!/usr/bin/env python3
-"""
-应用打包脚本 - 将Python应用打包为可执行文件
-"""
-
-import os
-import sys
-import shutil
-import subprocess
-from pathlib import Path
-
-def check_dependencies():
- """检查必要的依赖"""
- try:
- import PyInstaller
- print("OK PyInstaller 已安装")
- except ImportError:
- print("正在安装 PyInstaller...")
- subprocess.check_call([sys.executable, "-m", "pip", "install", "pyinstaller"])
- print("OK PyInstaller 安装完成")
-
-def create_spec_file():
- """创建 PyInstaller spec 文件"""
- spec_content = '''
-# -*- mode: python ; coding: utf-8 -*-
-
-block_cipher = None
-
-a = Analysis(
- ['main.py'],
- pathex=[],
- binaries=[],
- datas=[
- ('app', 'app'),
- ('uploads', 'uploads'),
- ('logs', 'logs'),
- ],
- hiddenimports=[
- 'uvicorn',
- 'fastapi',
- 'sqlalchemy',
- 'pymysql',
- 'pydantic',
- 'pydantic_settings',
- 'redis',
- 'passlib',
- 'python_jose',
- 'uvicorn.protocols.http.httptools_impl',
- ],
- hookspath=[],
- hooksconfig={},
- runtime_hooks=[],
- excludes=[],
- win_no_prefer_redirects=False,
- win_private_assemblies=False,
- cipher=block_cipher,
- noarchive=False,
-)
-
-pyz = PYZ(a.pure, a.zipped_data, cipher=block_cipher)
-
-exe = EXE(
- pyz,
- a.scripts,
- a.binaries,
- a.zipfiles,
- a.datas,
- [],
- name='cloud-drive-server',
- debug=False,
- bootloader_ignore_signals=False,
- strip=False,
- upx=True,
- upx_exclude=[],
- runtime_tmpdir=None,
- console=True,
- disable_windowed_traceback=False,
- argv_emulation=False,
- target_arch=None,
- codesign_identity=None,
- entitlements_file=None,
- icon=None
-)
-'''
-
- with open('cloud-drive-server.spec', 'w', encoding='utf-8') as f:
- f.write(spec_content)
- print("OK 创建了 cloud-drive-server.spec 文件")
-
-def build_executable():
- """构建可执行文件"""
- print("开始构建可执行文件...")
-
- try:
- # 使用 PyInstaller 构建
- result = subprocess.run([
- sys.executable, '-m', 'PyInstaller',
- '--clean',
- '--noconfirm',
- 'cloud-drive-server.spec'
- ], capture_output=True, text=True)
-
- if result.returncode == 0:
- print("OK 可执行文件构建成功")
- print("输出目录: dist/")
- return True
- else:
- print("ERROR 构建失败:")
- print(result.stdout)
- print(result.stderr)
- return False
-
- except Exception as e:
- print(f"ERROR 构建过程中出现错误: {e}")
- return False
-
-def create_dockerfile_for_executable():
- """为可执行文件创建最小化的 Dockerfile"""
- dockerfile_content = '''# 最小化运行环境 - 使用可执行文件
-FROM alpine:latest
-
-# 安装运行时依赖
-RUN apk add --no-cache \\
- curl \\
- tzdata \\
- ca-certificates \\
- && rm -rf /var/cache/apk/*
-
-# 设置时区
-ENV TZ=Asia/Shanghai
-RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
-
-# 创建应用用户
-RUN adduser -D -s /bin/sh app
-
-# 设置工作目录
-WORKDIR /app
-
-# 复制可执行文件
-COPY dist/cloud-drive-server /app/cloud-drive-server
-
-# 创建必要的目录
-RUN mkdir -p /app/uploads /app/logs \\
- && chown -R app:app /app
-
-# 切换到非root用户
-USER app
-
-# 暴露端口
-EXPOSE 8002
-
-# 健康检查
-HEALTHCHECK --interval=30s --timeout=30s --start-period=5s --retries=3 \\
- CMD curl -f http://localhost:8002/api/v1/health || exit 1
-
-# 启动命令
-CMD ["./cloud-drive-server"]
-'''
-
- with open('Dockerfile.executable', 'w', encoding='utf-8') as f:
- f.write(dockerfile_content)
- print("OK 创建了 Dockerfile.executable 文件")
-
-def main():
- """主函数"""
- print("=== 云盘应用打包工具 ===")
- print("正在将应用打包为Docker镜像...")
-
- # 检查当前目录
- if not Path('main.py').exists():
- print("ERROR 错误: 在当前目录未找到 main.py 文件")
- print("请在 backend 目录中运行此脚本")
- return False
-
- # 检查依赖
- check_dependencies()
-
- # 创建 spec 文件
- create_spec_file()
-
- # 构建可执行文件
- if not build_executable():
- return False
-
- # 创建可执行文件的 Dockerfile
- create_dockerfile_for_executable()
-
- print("\n=== 打包完成 ===")
- print("OK 应用已成功打包")
- print("OK 可执行文件位于: dist/cloud-drive-server")
- print("OK Dockerfile: Dockerfile.executable")
- print("\n下一步命令:")
- print(" docker build -f Dockerfile.executable -t cloud-drive-backend:latest .")
- print(" docker run -d -p 8002:8002 --name cloud-drive-backend cloud-drive-backend:latest")
-
- return True
-
-if __name__ == "__main__":
- success = main()
- sys.exit(0 if success else 1)
\ No newline at end of file
diff --git a/backend/prepare_linux_package.sh b/backend/prepare_linux_package.sh
deleted file mode 100644
index 8cc88f0..0000000
--- a/backend/prepare_linux_package.sh
+++ /dev/null
@@ -1,66 +0,0 @@
-#!/bin/bash
-# 准备Linux打包的源代码包
-
-echo "=== 准备Linux打包源代码包 ==="
-
-# 创建临时目录
-PACKAGE_DIR="cloud-drive-source-$(date +%Y%m%d)"
-mkdir -p "$PACKAGE_DIR"
-
-# 复制必要文件
-echo "复制源代码..."
-cp -r app/ "$PACKAGE_DIR/"
-cp main.py "$PACKAGE_DIR/"
-cp build.spec "$PACKAGE_DIR/"
-cp build_linux.py "$PACKAGE_DIR/"
-cp requirements.txt "$PACKAGE_DIR/"
-cp requirements-build.txt "$PACKAGE_DIR/"
-cp .env.example "$PACKAGE_DIR/"
-cp cloud-drive.service "$PACKAGE_DIR/"
-cp install.sh "$PACKAGE_DIR/"
-cp uninstall.sh "$PACKAGE_DIR/"
-cp BUILD_GUIDE.md "$PACKAGE_DIR/"
-
-# 创建Linux打包脚本
-cat > "$PACKAGE_DIR/build_on_linux.sh" << 'EOF'
-#!/bin/bash
-# 在Linux环境下的打包脚本
-
-echo "=== 在Linux环境下打包云盘后端 ==="
-
-# 安装系统依赖
-sudo apt-get update
-sudo apt-get install -y python3 python3-pip python3-venv build-essential
-
-# 创建虚拟环境
-python3 -m venv venv
-source venv/bin/activate
-
-# 安装依赖
-pip install --upgrade pip
-pip install -r requirements-build.txt
-pip install -r requirements.txt
-
-# 运行打包
-python build_linux.py
-
-echo "=== 打包完成 ==="
-echo "可执行文件位置: deploy/cloud-drive-server"
-echo "现在可以运行 ./install.sh 进行安装"
-EOF
-
-chmod +x "$PACKAGE_DIR/build_on_linux.sh"
-
-# 创建压缩包
-echo "创建压缩包..."
-tar -czf "$PACKAGE_DIR.tar.gz" "$PACKAGE_DIR"
-
-echo "=== 源代码包准备完成 ==="
-echo "生成的文件:"
-echo " $PACKAGE_DIR/ - 源代码目录"
-echo " $PACKAGE_DIR.tar.gz - 压缩包"
-echo ""
-echo "将压缩包上传到Linux服务器后,解压并运行:"
-echo " tar -xzf $PACKAGE_DIR.tar.gz"
-echo " cd $PACKAGE_DIR"
-echo " ./build_on_linux.sh"
\ No newline at end of file
diff --git a/backend/prepare_linux_package_fixed.sh b/backend/prepare_linux_package_fixed.sh
deleted file mode 100644
index 6615f90..0000000
--- a/backend/prepare_linux_package_fixed.sh
+++ /dev/null
@@ -1,229 +0,0 @@
-#!/bin/bash
-# 准备Linux打包的源代码包(修复版)
-
-echo "=== 准备Linux打包源代码包(修复版) ==="
-
-# 删除旧的包
-rm -rf cloud-drive-source-*
-
-# 创建临时目录
-PACKAGE_DIR="cloud-drive-source-$(date +%Y%m%d-%H%M%S)"
-mkdir -p "$PACKAGE_DIR"
-
-echo "复制源代码和配置文件..."
-# 复制必要文件
-cp -r app/ "$PACKAGE_DIR/"
-cp main.py "$PACKAGE_DIR/"
-cp build.spec "$PACKAGE_DIR/"
-cp build_linux_fixed.py "$PACKAGE_DIR/build_linux.py"
-cp requirements.txt "$PACKAGE_DIR/"
-cp requirements-build.txt "$PACKAGE_DIR/"
-cp .env.example "$PACKAGE_DIR/"
-cp cloud-drive.service "$PACKAGE_DIR/"
-cp install.sh "$PACKAGE_DIR/"
-cp install_user.sh "$PACKAGE_DIR/"
-cp BUILD_GUIDE.md "$PACKAGE_DIR/"
-
-# 创建Linux打包脚本
-cat > "$PACKAGE_DIR/build_on_linux.sh" << 'EOF'
-#!/bin/bash
-# 在Linux环境下的打包脚本(修复版)
-
-echo "=== 在Linux环境下打包云盘后端(修复版) ==="
-
-# 检查是否为root用户
-if [ "$EUID" -eq 0 ]; then
- echo "警告: 不建议在root用户下直接打包,建议使用普通用户"
- read -p "是否继续?(y/N): " -n 1 -r
- echo
- if [[ ! $REPLY =~ ^[Yy]$ ]]; then
- exit 1
- fi
-fi
-
-# 安装系统依赖(Ubuntu/Debian)
-if command -v apt-get &> /dev/null; then
- echo "检测到Ubuntu/Debian系统"
- sudo apt-get update || echo "无法更新包列表,跳过..."
- sudo apt-get install -y python3 python3-pip python3-venv build-essential || echo "安装系统依赖失败,请手动安装"
-# 安装系统依赖(CentOS/RHEL)
-elif command -v yum &> /dev/null; then
- echo "检测到CentOS/RHEL系统"
- sudo yum install -y python3 python3-pip python3-devel gcc gcc-c++ make || echo "安装系统依赖失败,请手动安装"
-# 安装系统依赖(其他系统)
-else
- echo "警告: 未检测到支持的包管理器,请手动安装Python3和编译工具"
-fi
-
-# 检查Python版本
-python3 --version
-if [ $? -ne 0 ]; then
- echo "错误: Python3 未安装或无法访问"
- exit 1
-fi
-
-# 创建虚拟环境
-echo "创建Python虚拟环境..."
-python3 -m venv venv || {
- echo "错误: 创建虚拟环境失败"
- exit 1
-}
-
-# 激活虚拟环境
-echo "激活虚拟环境..."
-source venv/bin/activate || {
- echo "错误: 激活虚拟环境失败"
- exit 1
-}
-
-# 升级pip
-echo "升级pip..."
-pip install --upgrade pip
-
-# 安装依赖
-echo "安装Python依赖包..."
-pip install -r requirements-build.txt || {
- echo "错误: 安装构建依赖失败"
- exit 1
-}
-
-pip install -r requirements.txt || {
- echo "错误: 安装应用依赖失败"
- exit 1
-}
-
-# 运行打包
-echo "开始打包..."
-python build_linux.py || {
- echo "错误: 打包失败"
- exit 1
-}
-
-# 检查打包结果
-if [ -f "deploy/cloud-drive-server" ]; then
- echo "=== 打包成功 ==="
- echo "可执行文件位置: deploy/cloud-drive-server"
- echo "文件大小: $(ls -lh deploy/cloud-drive-server | awk '{print $5}')"
- echo ""
- echo "下一步操作:"
- echo "1. 用户级安装(推荐,无需sudo):"
- echo " cd deploy && ./install_user.sh"
- echo ""
- echo "2. 系统级安装(需要sudo权限):"
- echo " cd deploy && sudo ./install.sh"
- echo ""
- echo "3. 直接运行:"
- echo " cd deploy && ./cloud-drive-server"
- echo ""
- echo "4. 查看详细说明:"
- echo " cat deploy/README.md"
-else
- echo "错误: 打包失败,未找到可执行文件"
- exit 1
-fi
-EOF
-
-chmod +x "$PACKAGE_DIR/build_on_linux.sh"
-
-# 创建问题排查脚本
-cat > "$PACKAGE_DIR/troubleshoot.sh" << 'EOF'
-#!/bin/bash
-# 问题排查脚本
-
-echo "=== 云盘后端问题排查工具 ==="
-
-echo "1. 检查Python环境:"
-python3 --version 2>&1 || echo "Python3 未安装"
-
-echo ""
-echo "2. 检查pip:"
-pip3 --version 2>&1 || echo "pip3 未安装"
-
-echo ""
-echo "3. 检查系统依赖:"
-if command -v apt-get &> /dev/null; then
- echo "包管理器: apt-get (Ubuntu/Debian)"
- dpkg -l | grep -E "(python3|gcc|make)" || echo "检查系统依赖包..."
-elif command -v yum &> /dev/null; then
- echo "包管理器: yum (CentOS/RHEL)"
- rpm -qa | grep -E "(python3|gcc|make)" || echo "检查系统依赖包..."
-else
- echo "未检测到支持的包管理器"
-fi
-
-echo ""
-echo "4. 检查虚拟环境:"
-if [ -d "venv" ]; then
- echo "虚拟环境目录存在"
- if [ -f "venv/bin/python" ]; then
- echo "虚拟环境Python可执行文件存在"
- venv/bin/python --version
- else
- echo "虚拟环境Python可执行文件不存在"
- fi
-else
- echo "虚拟环境目录不存在"
-fi
-
-echo ""
-echo "5. 检查源代码文件:"
-for file in main.py build.spec requirements.txt; do
- if [ -f "$file" ]; then
- echo "✓ $file 存在"
- else
- echo "✗ $file 不存在"
- fi
-done
-
-echo ""
-echo "6. 检查app目录:"
-if [ -d "app" ]; then
- echo "✓ app目录存在"
- find app -name "*.py" | head -5 | while read file; do
- echo " ✓ $file"
- done
-else
- echo "✗ app目录不存在"
-fi
-
-echo ""
-echo "7. 网络连接测试:"
-if ping -c 1 pypi.org &> /dev/null; then
- echo "✓ 可以访问PyPI"
-else
- echo "✗ 无法访问PyPI,可能需要配置代理"
-fi
-
-echo ""
-echo "=== 排查完成 ==="
-echo "如果发现问题,请根据上述输出进行修复"
-EOF
-
-chmod +x "$PACKAGE_DIR/troubleshoot.sh"
-
-# 创建压缩包
-echo "创建压缩包..."
-tar -czf "$PACKAGE_DIR.tar.gz" "$PACKAGE_DIR"
-
-echo "=== 源代码包准备完成 ==="
-echo "生成的文件:"
-echo " $PACKAGE_DIR/ - 源代码目录"
-echo " $PACKAGE_DIR.tar.gz - 压缩包 ($(ls -lh "$PACKAGE_DIR.tar.gz" | awk '{print $5}'))"
-echo ""
-echo "修复内容:"
-echo " ✓ 添加了用户级安装脚本 install_user.sh"
-echo " ✓ 修复了 build.spec 依赖缺失问题"
-echo " ✓ 改进了打包脚本 build_linux.py"
-echo " ✓ 添加了问题排查脚本 troubleshoot.sh"
-echo " ✓ 增强了安装说明文档"
-echo ""
-echo "将压缩包上传到Linux服务器后,解压并运行:"
-echo " tar -xzf $PACKAGE_DIR.tar.gz"
-echo " cd $PACKAGE_DIR"
-echo " ./build_on_linux.sh"
-echo ""
-echo "如果遇到问题,可以先运行:"
-echo " ./troubleshoot.sh"
-EOF
-
-chmod +x backend/prepare_linux_package_fixed.sh
\ No newline at end of file
diff --git a/backend/quick_build.sh b/backend/quick_build.sh
deleted file mode 100644
index 6940705..0000000
--- a/backend/quick_build.sh
+++ /dev/null
@@ -1,28 +0,0 @@
-#!/bin/bash
-# 快速打包脚本 - Linux环境
-
-echo "=== 云盘后端快速打包脚本 ==="
-
-# 检查Python环境
-if ! command -v python3 &> /dev/null; then
- echo "错误: 未找到Python3"
- exit 1
-fi
-
-echo "Python版本: $(python3 --version)"
-
-# 安装PyInstaller
-echo "安装PyInstaller..."
-pip3 install pyinstaller
-
-# 安装项目依赖
-echo "安装项目依赖..."
-pip3 install -r requirements.txt
-
-# 运行打包
-echo "开始打包..."
-python3 build_linux.py
-
-echo "=== 打包完成 ==="
-echo "部署包位置: ./deploy/"
-echo "请查看 ./deploy/README.md 了解部署说明"
\ No newline at end of file
diff --git a/backend/quick_db_fix.sh b/backend/quick_db_fix.sh
deleted file mode 100644
index a2c5b66..0000000
--- a/backend/quick_db_fix.sh
+++ /dev/null
@@ -1,28 +0,0 @@
-#!/bin/bash
-
-# 快速数据库连接修复
-
-echo "=== 快速数据库连接修复 ==="
-
-# 检查.env文件并修复数据库URL
-if [ -f ".env" ]; then
- echo "修复 .env 文件中的数据库配置..."
-
- # 备份原文件
- cp .env .env.backup.$(date +%Y%m%d_%H%M%S)
-
- # 更新数据库URL为外部数据库
- sed -i 's|DATABASE_URL=.*|DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db|' .env
-
- echo "✓ 数据库配置已更新为外部数据库"
-else
- echo "创建 .env 文件..."
- cat > .env << EOF
-DATABASE_URL=mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db
-EOF
- echo "✓ .env 文件已创建"
-fi
-
-echo ""
-echo "请重启应用以使配置生效"
-echo "重启命令: python main.py"
\ No newline at end of file
diff --git a/backend/quick_fix_server.py b/backend/quick_fix_server.py
deleted file mode 100644
index 04513af..0000000
--- a/backend/quick_fix_server.py
+++ /dev/null
@@ -1,131 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-服务器端快速修复脚本
-修复PyInstaller打包时的database目录缺失问题
-"""
-
-import os
-from pathlib import Path
-
-def fix_build_spec():
- """修复build.spec文件,处理可选数据文件"""
- spec_file = Path('build.spec')
-
- if not spec_file.exists():
- print("错误: build.spec 文件不存在")
- return False
-
- # 读取原文件内容
- with open(spec_file, 'r', encoding='utf-8') as f:
- content = f.read()
-
- # 查找并替换datas部分
- old_datas = '''# 需要包含的数据文件
-datas = [
- (str(ROOT_DIR / 'app'), 'app'), # 包含整个app目录
- ('.env.example', '.'), # 包含环境配置示例文件
- ('database', 'database'), # 包含数据库相关文件
-]'''
-
- new_datas = '''# 需要包含的数据文件
-datas = [
- (str(ROOT_DIR / 'app'), 'app'), # 包含整个app目录
- ('.env.example', '.'), # 包含环境配置示例文件
-]
-
-# 可选数据文件(如果存在才包含)
-optional_files = [
- ('database', 'database'), # 包含数据库相关文件
-]
-
-# 添加可选数据文件
-for src, dst in optional_files:
- src_path = ROOT_DIR / src
- if src_path.exists():
- datas.append((src, dst))
- print(f"包含可选数据文件: {src}")
- else:
- print(f"跳过可选数据文件: {src} (不存在)")'''
-
- if old_datas in content:
- content = content.replace(old_datas, new_datas)
-
- # 写回文件
- with open(spec_file, 'w', encoding='utf-8') as f:
- f.write(content)
-
- print("✓ 已修复 build.spec 文件")
- return True
- else:
- print("build.spec 文件已经包含修复或格式不匹配")
- return False
-
-def create_database_dir():
- """创建database目录(如果不存在)"""
- db_dir = Path('database')
-
- if not db_dir.exists():
- db_dir.mkdir(exist_ok=True)
-
- # 创建一个空的初始化文件
- init_file = db_dir / 'init' / '.gitkeep'
- init_file.parent.mkdir(exist_ok=True)
- init_file.touch()
-
- # 创建一个说明文件
- readme_file = db_dir / 'README.md'
- with open(readme_file, 'w', encoding='utf-8') as f:
- f.write("""# Database目录
-
-此目录包含数据库相关的初始化脚本和配置文件。
-
-## 文件说明
-
-- `init/`: 数据库初始化脚本目录
-- `create_files_table.py`: 创建文件表的脚本
-
-## 注意
-
-如果此目录为空,不会影响应用的正常运行。应用会自动创建所需的数据库表。
-""")
-
- print("✓ 已创建 database 目录")
- return True
- else:
- print("✓ database 目录已存在")
- return True
-
-def main():
- """主函数"""
- print("=== 服务器端快速修复脚本 ===")
-
- # 修复build.spec文件
- print("1. 修复 build.spec 文件...")
- fix_build_spec()
-
- # 创建database目录
- print("\n2. 检查 database 目录...")
- create_database_dir()
-
- print("\n=== 修复完成 ===")
- print("现在可以重新运行打包:")
- print("python build_linux.py")
-
- # 验证修复结果
- print("\n=== 验证修复结果 ===")
-
- if Path('build.spec').exists():
- print("✓ build.spec 文件存在")
- else:
- print("✗ build.spec 文件不存在")
-
- if Path('database').exists():
- print("✓ database 目录存在")
- files = list(Path('database').rglob('*'))
- print(f" 包含 {len(files)} 个文件/目录")
- else:
- print("✗ database 目录不存在")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/quick_start_project.py b/backend/quick_start_project.py
deleted file mode 100644
index 4fee35b..0000000
--- a/backend/quick_start_project.py
+++ /dev/null
@@ -1,291 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-快速启动和恢复脚本
-"""
-
-import os
-import sys
-import subprocess
-from pathlib import Path
-
-def check_python_version():
- """检查Python版本"""
- if sys.version_info < (3, 8):
- print("错误: 需要Python 3.8或更高版本")
- return False
- print(f"✓ Python版本: {sys.version}")
- return True
-
-def check_virtual_env():
- """检查虚拟环境"""
- venv_path = Path('venv')
- if venv_path.exists():
- print("✓ 虚拟环境存在")
- return True
- else:
- print("✗ 虚拟环境不存在,正在创建...")
- try:
- subprocess.run([sys.executable, '-m', 'venv', 'venv'], check=True)
- print("✓ 虚拟环境创建成功")
- return True
- except subprocess.CalledProcessError:
- print("✗ 虚拟环境创建失败")
- return False
-
-def activate_virtual_env():
- """激活虚拟环境"""
- if sys.platform == "win32":
- activate_script = Path('venv/Scripts/activate')
- else:
- activate_script = Path('venv/bin/activate')
-
- if activate_script.exists():
- print("✓ 虚拟环境激活脚本存在")
- return True
- else:
- print("✗ 虚拟环境激活脚本不存在")
- return False
-
-def install_dependencies():
- """安装依赖"""
- print("安装依赖包...")
-
- if sys.platform == "win32":
- pip_path = 'venv/Scripts/pip'
- python_path = 'venv/Scripts/python'
- else:
- pip_path = 'venv/bin/pip'
- python_path = 'venv/bin/python'
-
- # 升级pip
- try:
- subprocess.run([python_path, '-m', 'pip', 'install', '--upgrade', 'pip'], check=True)
- print("✓ pip升级成功")
- except subprocess.CalledProcessError:
- print("✗ pip升级失败")
-
- # 安装基础依赖
- basic_packages = [
- 'fastapi==0.104.1',
- 'uvicorn[standard]==0.24.0',
- 'sqlalchemy==2.0.23',
- 'pymysql==1.1.0',
- 'python-jose[cryptography]==3.3.0',
- 'passlib[bcrypt]==1.7.4',
- 'python-multipart==0.0.6',
- 'pydantic==2.5.0',
- 'pydantic-settings==2.1.0',
- 'httpx==0.25.2',
- 'python-dotenv==1.0.0',
- 'loguru>=0.7.0'
- ]
-
- try:
- for package in basic_packages:
- print(f"安装 {package}...")
- subprocess.run([pip_path, 'install', package], check=True)
- print("✓ 依赖安装成功")
- return True
- except subprocess.CalledProcessError as e:
- print(f"✗ 依赖安装失败: {e}")
- return False
-
-def create_basic_app_structure():
- """创建基本的app结构"""
- print("创建基本app结构...")
-
- # 创建目录
- directories = [
- 'app',
- 'app/core',
- 'app/api/v1/endpoints'
- ]
-
- for dir_path in directories:
- Path(dir_path).mkdir(parents=True, exist_ok=True)
- print(f"✓ 创建目录: {dir_path}")
-
- # 创建__init__.py文件
- init_files = [
- ('app/__init__.py', '"""云盘应用包"""\n'),
- ('app/core/__init__.py', '"""核心模块包"""\n'),
- ('app/api/__init__.py', '"""API模块包"""\n'),
- ('app/api/v1/__init__.py', '"""API v1模块包"""\n'),
- ('app/api/v1/endpoints/__init__.py', '"""API端点模块包"""\n')
- ]
-
- for file_path, content in init_files:
- full_path = Path(file_path)
- if not full_path.exists():
- full_path.write_text(content, encoding='utf-8')
- print(f"✓ 创建文件: {file_path}")
-
-def create_essential_files():
- """创建必要的文件"""
- print("创建必要的文件...")
-
- # app/core/config.py
- config_content = '''from pydantic_settings import BaseSettings
-from typing import List
-
-class Settings(BaseSettings):
- ENVIRONMENT: str = "development"
- DEBUG: bool = True
- DATABASE_URL: str = "mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db"
- REDIS_URL: str = "redis://localhost:6379"
- JWT_SECRET_KEY: str = "your-super-secret-jwt-key-change-in-production"
- JWT_ALGORITHM: str = "HS256"
- JWT_EXPIRE_MINUTES: int = 30
- ALLOWED_HOSTS: List[str] = ["*"]
- MAX_FILE_SIZE: int = 10 * 1024 * 1024
- UPLOAD_DIR: str = "uploads"
-
- class Config:
- env_file = ".env"
- case_sensitive = True
-
-settings = Settings()
-'''
-
- Path('app/core/config.py').write_text(config_content, encoding='utf-8')
- print("✓ 创建 app/core/config.py")
-
- # app/api/v1/endpoints/health.py
- health_content = '''from fastapi import APIRouter
-from datetime import datetime
-
-router = APIRouter()
-
-@router.get("/health")
-async def health_check():
- return {
- "status": "healthy",
- "timestamp": datetime.utcnow(),
- "version": "1.0.0"
- }
-
-@router.get("/")
-async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.0",
- "docs": "/docs"
- }
-'''
-
- Path('app/api/v1/endpoints/health.py').write_text(health_content, encoding='utf-8')
- print("✓ 创建 app/api/v1/endpoints/health.py")
-
-def create_simple_main():
- """创建简化的main.py"""
- print("创建简化的main.py...")
-
- main_content = '''import os
-import sys
-from pathlib import Path
-
-# 添加当前目录到Python路径
-current_dir = Path(__file__).parent
-sys.path.insert(0, str(current_dir))
-
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-from app.core.config import settings
-from app.api.v1.endpoints import health
-
-app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-# CORS中间件
-app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-# 包含路由
-app.include_router(health.router, prefix="/api/v1", tags=["health"])
-
-if __name__ == "__main__":
- import uvicorn
- print("启动云盘后端服务...")
- print("访问地址: http://localhost:8000")
- print("API文档: http://localhost:8000/docs")
-
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8000,
- reload=False
- )
-'''
-
- Path('main.py').write_text(main_content, encoding='utf-8')
- print("✓ 创建 main.py")
-
-def start_project():
- """启动项目"""
- print("启动项目...")
-
- if sys.platform == "win32":
- python_path = 'venv/Scripts/python'
- else:
- python_path = 'venv/bin/python'
-
- try:
- # 直接运行main.py
- subprocess.run([python_path, 'main.py'], check=True)
- except subprocess.CalledProcessError as e:
- print(f"启动失败: {e}")
- return False
- except KeyboardInterrupt:
- print("服务已停止")
- return True
-
-def main():
- """主函数"""
- print("=== 云盘后端快速启动脚本 ===")
-
- # 检查Python版本
- if not check_python_version():
- return
-
- # 检查和创建虚拟环境
- if not check_virtual_env():
- print("虚拟环境创建失败")
- return
-
- # 安装依赖
- if not install_dependencies():
- print("依赖安装失败")
- return
-
- # 创建基本结构
- create_basic_app_structure()
-
- # 创建必要文件
- create_essential_files()
-
- # 创建简化main.py
- create_simple_main()
-
- # 创建日志和上传目录
- Path('logs').mkdir(exist_ok=True)
- Path('uploads').mkdir(exist_ok=True)
-
- print("\n=== 准备完成 ===")
- print("现在启动项目...")
-
- # 启动项目
- start_project()
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/recreate_app_structure.py b/backend/recreate_app_structure.py
deleted file mode 100644
index ffb41c4..0000000
--- a/backend/recreate_app_structure.py
+++ /dev/null
@@ -1,491 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-重新创建完整的app目录结构和文件
-"""
-
-import os
-from pathlib import Path
-
-def create_app_directory():
- """创建app目录结构"""
- print("=== 创建app目录结构 ===")
-
- base_dir = Path('.')
-
- # 创建主要目录结构
- directories = [
- 'app',
- 'app/core',
- 'app/api',
- 'app/api/v1',
- 'app/api/v1/endpoints',
- 'app/models',
- 'app/schemas',
- 'app/services',
- 'app/utils'
- ]
-
- for dir_path in directories:
- full_path = base_dir / dir_path
- full_path.mkdir(parents=True, exist_ok=True)
- print(f"✓ 创建目录: {dir_path}")
-
-def create_init_files():
- """创建__init__.py文件"""
- print("\n=== 创建__init__.py文件 ===")
-
- base_dir = Path('.')
-
- # 各目录的__init__.py内容
- init_contents = {
- 'app/__init__.py': '"""云盘应用包"""\n\n__version__ = "1.0.0"\n',
- 'app/core/__init__.py': '"""核心模块包"""\n',
- 'app/api/__init__.py': '"""API模块包"""\n',
- 'app/api/v1/__init__.py': '"""API v1模块包"""\n',
- 'app/api/v1/endpoints/__init__.py': '"""API端点模块包"""\n',
- 'app/models/__init__.py': '"""数据模型包"""\n',
- 'app/schemas/__init__.py': '"""Pydantic模式包"""\n',
- 'app/services/__init__.py': '"""业务逻辑服务包"""\n',
- 'app/utils/__init__.py': '"""工具函数包"""\n'
- }
-
- for file_path, content in init_contents.items():
- full_path = base_dir / file_path
- if not full_path.exists():
- full_path.write_text(content, encoding='utf-8')
- print(f"✓ 创建文件: {file_path}")
-
-def create_core_files():
- """创建核心文件"""
- print("\n=== 创建核心文件 ===")
-
- base_dir = Path('.')
-
- # app/core/config.py
- config_content = '''from pydantic_settings import BaseSettings
-from typing import List
-import os
-
-class Settings(BaseSettings):
- # 基础配置
- ENVIRONMENT: str = "development"
- DEBUG: bool = True
-
- # 数据库配置
- DATABASE_URL: str = "mysql+pymysql://mytest_db:mytest_db@101.126.85.76:3306/mytest_db"
-
- # Redis配置
- REDIS_URL: str = "redis://localhost:6379"
-
- # JWT配置
- JWT_SECRET_KEY: str = "your-super-secret-jwt-key-change-in-production"
- JWT_ALGORITHM: str = "HS256"
- JWT_EXPIRE_MINUTES: int = 30
- JWT_REFRESH_EXPIRE_DAYS: int = 7
-
- # CORS配置
- ALLOWED_HOSTS: List[str] = [
- "http://localhost:3000",
- "http://localhost:3001",
- "http://localhost:3002",
- "http://localhost:3003",
- "http://localhost:3004",
- "http://127.0.0.1:3000",
- "http://127.0.0.1:3001",
- "http://127.0.0.1:3002",
- "http://127.0.0.1:3003",
- "http://127.0.0.1:3004",
- "http://172.16.16.89:3000",
- "http://172.16.16.89:3001",
- "http://172.16.16.89:3002",
- "http://172.16.16.89:3003",
- "http://172.16.16.89:3004",
- "*"
- ]
-
- # 文件上传配置
- MAX_FILE_SIZE: int = 10 * 1024 * 1024 # 10MB
- UPLOAD_DIR: str = "uploads"
- ALLOWED_EXTENSIONS: List[str] = [
- # 图片
- ".jpg", ".jpeg", ".png", ".gif", ".bmp", ".webp", ".svg",
- # 文档
- ".pdf", ".doc", ".docx", ".xls", ".xlsx", ".ppt", ".pptx",
- ".txt", ".rtf", ".csv",
- # 压缩文件
- ".zip", ".rar", ".7z", ".tar", ".gz",
- # 音频
- ".mp3", ".wav", ".flac", ".aac", ".ogg",
- # 视频
- ".mp4", ".avi", ".mkv", ".mov", ".wmv", ".flv",
- # 代码文件
- ".py", ".js", ".html", ".css", ".json", ".xml", ".yaml", ".yml",
- ".java", ".cpp", ".c", ".h", ".cs", ".php", ".rb", ".go",
- ".sql", ".sh", ".bat", ".ps1", ".md", ".log"
- ]
-
- # 安全配置
- BCRYPT_ROUNDS: int = 12
-
- class Config:
- env_file = ".env"
- case_sensitive = True
-
-settings = Settings()
-'''
-
- config_file = base_dir / 'app' / 'core' / 'config.py'
- config_file.write_text(config_content, encoding='utf-8')
- print("✓ 创建 app/core/config.py")
-
- # app/core/database.py
- database_content = '''from sqlalchemy import create_engine
-from sqlalchemy.ext.declarative import declarative_base
-from sqlalchemy.orm import sessionmaker
-from app.core.config import settings
-
-# 创建数据库引擎
-engine = create_engine(
- settings.DATABASE_URL,
- pool_pre_ping=True,
- pool_recycle=300,
-)
-
-# 创建会话工厂
-SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
-
-# 创建Base类
-Base = declarative_base()
-
-def get_db():
- """获取数据库会话"""
- db = SessionLocal()
- try:
- yield db
- finally:
- db.close()
-'''
-
- database_file = base_dir / 'app' / 'core' / 'database.py'
- database_file.write_text(database_content, encoding='utf-8')
- print("✓ 创建 app/core/database.py")
-
- # app/core/security.py
- security_content = '''from datetime import datetime, timedelta
-from typing import Optional
-from jose import JWTError, jwt
-from passlib.context import CryptContext
-from app.core.config import settings
-
-# 密码加密上下文
-pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
-
-def verify_password(plain_password: str, hashed_password: str) -> bool:
- """验证密码"""
- return pwd_context.verify(plain_password, hashed_password)
-
-def get_password_hash(password: str) -> str:
- """获取密码哈希"""
- return pwd_context.hash(password)
-
-def create_access_token(data: dict, expires_delta: Optional[timedelta] = None):
- """创建访问令牌"""
- to_encode = data.copy()
- if expires_delta:
- expire = datetime.utcnow() + expires_delta
- else:
- expire = datetime.utcnow() + timedelta(minutes=settings.JWT_EXPIRE_MINUTES)
-
- to_encode.update({"exp": expire})
- encoded_jwt = jwt.encode(to_encode, settings.JWT_SECRET_KEY, algorithm=settings.JWT_ALGORITHM)
- return encoded_jwt
-
-def verify_token(token: str):
- """验证令牌"""
- try:
- payload = jwt.decode(token, settings.JWT_SECRET_KEY, algorithms=[settings.JWT_ALGORITHM])
- return payload
- except JWTError:
- return None
-'''
-
- security_file = base_dir / 'app' / 'core' / 'security.py'
- security_file.write_text(security_content, encoding='utf-8')
- print("✓ 创建 app/core/security.py")
-
-def create_api_files():
- """创建API文件"""
- print("\n=== 创建API文件 ===")
-
- base_dir = Path('.')
-
- # app/api/v1/endpoints/health.py
- health_content = '''from fastapi import APIRouter, status
-from datetime import datetime
-
-router = APIRouter()
-
-@router.get("/health", status_code=status.HTTP_200_OK)
-async def health_check():
- """健康检查端点"""
- return {
- "status": "healthy",
- "timestamp": datetime.utcnow(),
- "version": "1.0.0",
- "message": "云盘后端服务运行正常"
- }
-
-@router.get("/")
-async def root():
- """根端点"""
- return {
- "message": "云盘应用 API",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/api/v1/health"
- }
-'''
-
- health_file = base_dir / 'app' / 'api' / 'v1' / 'endpoints' / 'health.py'
- health_file.write_text(health_content, encoding='utf-8')
- print("✓ 创建 app/api/v1/endpoints/health.py")
-
- # app/api/v1/endpoints/auth.py
- auth_content = '''from fastapi import APIRouter, Depends, HTTPException, status
-from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm
-from sqlalchemy.orm import Session
-from typing import Optional
-from datetime import timedelta
-
-from app.core.database import get_db
-from app.core.security import verify_password, create_access_token
-from app.core.config import settings
-from app.schemas.user import UserCreate, UserResponse, Token
-
-router = APIRouter()
-oauth2_scheme = OAuth2PasswordBearer(tokenUrl="api/v1/auth/token")
-
-@router.post("/register", response_model=UserResponse)
-async def register(user_data: UserCreate, db: Session = Depends(get_db)):
- """用户注册"""
- # TODO: 实现用户注册逻辑
- return {"message": "注册功能待实现"}
-
-@router.post("/token", response_model=Token)
-async def login(form_data: OAuth2PasswordRequestForm = Depends(), db: Session = Depends(get_db)):
- """用户登录"""
- # TODO: 实现用户登录逻辑
- return {
- "access_token": "dummy_token",
- "token_type": "bearer",
- "expires_in": settings.JWT_EXPIRE_MINUTES * 60
- }
-
-@router.get("/me", response_model=UserResponse)
-async def get_current_user(token: str = Depends(oauth2_scheme), db: Session = Depends(get_db)):
- """获取当前用户信息"""
- # TODO: 实现获取当前用户逻辑
- return {"message": "用户信息功能待实现"}
-'''
-
- auth_file = base_dir / 'app' / 'api' / 'v1' / 'endpoints' / 'auth.py'
- auth_file.write_text(auth_content, encoding='utf-8')
- print("✓ 创建 app/api/v1/endpoints/auth.py")
-
- # app/api/v1/endpoints/files.py
- files_content = '''from fastapi import APIRouter, Depends, HTTPException, UploadFile, File
-from sqlalchemy.orm import Session
-from typing import List
-
-from app.core.database import get_db
-from app.schemas.file import FileResponse, FileUploadResponse
-
-router = APIRouter()
-
-@router.post("/upload", response_model=FileUploadResponse)
-async def upload_file(
- file: UploadFile = File(...),
- db: Session = Depends(get_db)
-):
- """上传文件"""
- # TODO: 实现文件上传逻辑
- return {
- "message": "文件上传功能待实现",
- "filename": file.filename,
- "size": 0
- }
-
-@router.get("/list", response_model=List[FileResponse])
-async def list_files(
- skip: int = 0,
- limit: int = 100,
- db: Session = Depends(get_db)
-):
- """获取文件列表"""
- # TODO: 实现文件列表逻辑
- return []
-
-@router.get("/{file_id}", response_model=FileResponse)
-async def get_file_info(file_id: int, db: Session = Depends(get_db)):
- """获取文件信息"""
- # TODO: 实现获取文件信息逻辑
- return {"message": "文件信息功能待实现"}
-
-@router.delete("/{file_id}")
-async def delete_file(file_id: int, db: Session = Depends(get_db)):
- """删除文件"""
- # TODO: 实现文件删除逻辑
- return {"message": "文件删除功能待实现"}
-'''
-
- files_file = base_dir / 'app' / 'api' / 'v1' / 'endpoints' / 'files.py'
- files_file.write_text(files_content, encoding='utf-8')
- print("✓ 创建 app/api/v1/endpoints/files.py")
-
-def create_schema_files():
- """创建Pydantic模式文件"""
- print("\n=== 创建模式文件 ===")
-
- base_dir = Path('.')
-
- # app/schemas/user.py
- user_schema_content = '''from pydantic import BaseModel, EmailStr
-from typing import Optional
-
-class UserBase(BaseModel):
- username: str
- email: EmailStr
-
-class UserCreate(UserBase):
- password: str
- confirm_password: str
-
-class UserUpdate(BaseModel):
- username: Optional[str] = None
- email: Optional[EmailStr] = None
-
-class UserResponse(UserBase):
- id: int
- is_active: bool
- created_at: str
-
- class Config:
- from_attributes = True
-
-class Token(BaseModel):
- access_token: str
- token_type: str
- expires_in: int
-'''
-
- user_schema_file = base_dir / 'app' / 'schemas' / 'user.py'
- user_schema_file.write_text(user_schema_content, encoding='utf-8')
- print("✓ 创建 app/schemas/user.py")
-
- # app/schemas/file.py
- file_schema_content = '''from pydantic import BaseModel
-from typing import Optional
-from datetime import datetime
-
-class FileBase(BaseModel):
- filename: str
- original_filename: str
- file_size: int
- content_type: str
-
-class FileCreate(FileBase):
- pass
-
-class FileUpdate(BaseModel):
- filename: Optional[str] = None
-
-class FileResponse(FileBase):
- id: int
- user_id: int
- file_path: str
- created_at: datetime
-
- class Config:
- from_attributes = True
-
-class FileUploadResponse(BaseModel):
- message: str
- filename: str
- size: int
- file_id: Optional[int] = None
-'''
-
- file_schema_file = base_dir / 'app' / 'schemas' / 'file.py'
- file_schema_file.write_text(file_schema_content, encoding='utf-8')
- print("✓ 创建 app/schemas/file.py")
-
-def verify_structure():
- """验证项目结构"""
- print("\n=== 验证项目结构 ===")
-
- base_dir = Path('.')
-
- required_files = [
- 'app/__init__.py',
- 'app/core/__init__.py',
- 'app/core/config.py',
- 'app/core/database.py',
- 'app/core/security.py',
- 'app/api/__init__.py',
- 'app/api/v1/__init__.py',
- 'app/api/v1/endpoints/__init__.py',
- 'app/api/v1/endpoints/health.py',
- 'app/api/v1/endpoints/auth.py',
- 'app/api/v1/endpoints/files.py',
- 'app/schemas/__init__.py',
- 'app/schemas/user.py',
- 'app/schemas/file.py'
- ]
-
- all_exist = True
- for file_path in required_files:
- full_path = base_dir / file_path
- if full_path.exists():
- print(f"✓ {file_path}")
- else:
- print(f"✗ {file_path}")
- all_exist = False
-
- if all_exist:
- print("\n🎉 所有文件创建成功!")
- print("现在可以运行: python main.py")
- else:
- print("\n⚠️ 部分文件创建失败,请检查错误信息")
-
-def main():
- """主函数"""
- print("=== 重新创建app目录结构 ===")
-
- # 创建目录结构
- create_app_directory()
-
- # 创建__init__.py文件
- create_init_files()
-
- # 创建核心文件
- create_core_files()
-
- # 创建API文件
- create_api_files()
-
- # 创建模式文件
- create_schema_files()
-
- # 验证结构
- verify_structure()
-
- print("\n=== 恢复完成 ===")
- print("app目录结构和所有必要文件已重新创建")
- print("下一步:")
- print("1. 激活虚拟环境: source venv/bin/activate")
- print("2. 安装依赖: pip install -r requirements.txt")
- print("3. 启动服务: python main.py")
-
-if __name__ == '__main__':
- main()
\ No newline at end of file
diff --git a/backend/server_no_loguru.py b/backend/server_no_loguru.py
deleted file mode 100644
index 4ab5619..0000000
--- a/backend/server_no_loguru.py
+++ /dev/null
@@ -1,271 +0,0 @@
-#!/usr/bin/env python3
-# 不依赖loguru的启动脚本
-
-import os
-import sys
-import logging
-from pathlib import Path
-
-# 添加当前目录到Python路径
-current_dir = Path(__file__).parent
-sys.path.insert(0, str(current_dir))
-
-# 配置标准日志
-logging.basicConfig(
- level=logging.INFO,
- format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
-)
-logger = logging.getLogger(__name__)
-
-logger.info("Starting Cloud Drive Application Server...")
-
-# 导入FastAPI相关
-try:
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
- logger.info("FastAPI dependencies available")
-except ImportError as e:
- logger.error(f"FastAPI import failed: {e}")
- logger.error("Please install dependencies: pip install fastapi uvicorn")
- sys.exit(1)
-
-# 尝试导入app模块
-try:
- from app.core.config import settings
- from app.api.v1.endpoints import health, auth, files
- APP_AVAILABLE = True
- logger.info("Full app module available")
-except ImportError as e:
- logger.warning(f"App module import failed: {e}")
- logger.info("Using simplified mode")
- APP_AVAILABLE = False
-
-def create_app():
- """创建FastAPI应用"""
- if APP_AVAILABLE:
- # 使用完整的应用
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- try:
- app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
- except Exception as e:
- logger.warning(f"CORS configuration failed: {e}")
- # 使用默认配置
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 包含路由
- try:
- app.include_router(health.router, prefix="/api/v1", tags=["health"])
- app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
- app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
- except Exception as e:
- logger.warning(f"Router inclusion failed: {e}")
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.1",
- "docs": "/docs",
- "health": "/api/v1/health"
- }
-
- # 添加缺失的端点
- @app.get("/health")
- async def health_endpoint():
- import time
- return {
- "success": True,
- "data": {
- "status": "healthy",
- "service": "cloud-drive-api",
- "environment": "development",
- "timestamp": int(time.time())
- },
- "message": "API服务运行正常"
- }
-
- @app.get("/test")
- async def test_endpoint():
- return {
- "message": "测试端点正常工作",
- "server": "port 8080",
- "status": "ok"
- }
-
- @app.get("/info")
- async def info_endpoint():
- return {
- "mode": "full",
- "python_version": str(sys.version),
- "status": "running",
- "app_type": "FastAPI"
- }
-
- return app
- else:
- # 创建简化版本的应用
- app = FastAPI(
- title="云盘应用 API (简化版)",
- description="云存储Web应用后端API - 简化版本",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API (简化版)",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/health",
- "mode": "simplified"
- }
-
- @app.get("/health")
- async def health_check():
- return {
- "status": "healthy",
- "message": "服务运行正常",
- "mode": "simplified"
- }
-
- @app.get("/api/v1/health")
- async def api_health():
- import time
- return {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0"
- }
-
- @app.get("/test")
- async def test_endpoint():
- return {
- "message": "测试端点正常工作",
- "server": "port 8080",
- "status": "ok"
- }
-
- @app.get("/health")
- async def health_endpoint():
- import time
- return {
- "success": True,
- "data": {
- "status": "healthy",
- "service": "cloud-drive-api",
- "environment": "development",
- "timestamp": int(time.time())
- },
- "message": "API服务运行正常"
- }
-
- @app.get("/info")
- async def info_endpoint():
- return {
- "mode": "simplified",
- "python_version": str(sys.version),
- "status": "running",
- "app_type": "FastAPI"
- }
-
- return app
-
-def main():
- """主函数"""
- logger.info("Initializing Cloud Drive Application...")
-
- # 创建必要目录
- os.makedirs("logs", exist_ok=True)
- os.makedirs("uploads", exist_ok=True)
- logger.info("Created necessary directories")
-
- # 创建FastAPI应用
- app = create_app()
- logger.info("FastAPI application created")
-
- # 获取本机IP
- try:
- import socket
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- local_ip = s.getsockname()[0]
- s.close()
- except:
- local_ip = "127.0.0.1"
- logger.warning("Could not determine local IP, using 127.0.0.1")
-
- # 显示启动信息
- logger.info("=" * 50)
- logger.info(f"Local access:")
- logger.info(f" Root path: http://localhost:8080")
- logger.info(f" API docs: http://localhost:8080/docs")
- logger.info(f" ReDoc: http://localhost:8080/redoc")
- logger.info(f" Health check: http://localhost:8080/api/v1/health")
- logger.info("")
- logger.info(f"Network access:")
- logger.info(f" Root path: http://{local_ip}:8080")
- logger.info(f" API docs: http://{local_ip}:8080/docs")
- logger.info("")
- logger.info("Service information:")
- logger.info(f" Python version: {sys.version}")
- logger.info(f" Working directory: {os.getcwd()}")
- logger.info(f" Mode: {'Full' if APP_AVAILABLE else 'Simplified'}")
- logger.info("=" * 50)
- logger.info("Press Ctrl+C to stop service")
-
- # 启动服务器
- try:
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8080,
- reload=False,
- access_log=True,
- log_level="info"
- )
- except KeyboardInterrupt:
- logger.info("Server stopped by user")
- except Exception as e:
- logger.error(f"Startup failed: {e}")
- logger.info("Possible solutions:")
- logger.info("1. Check if port 8080 is occupied")
- logger.info("2. Ensure dependencies are installed: pip install fastapi uvicorn")
- logger.info("3. Check firewall settings")
- return False
-
- return True
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/simple-build.sh b/backend/simple-build.sh
deleted file mode 100644
index 41096c7..0000000
--- a/backend/simple-build.sh
+++ /dev/null
@@ -1,79 +0,0 @@
-#!/bin/bash
-
-# 简单的Docker镜像构建脚本
-# 当无法访问Docker Hub时使用
-
-echo "=== 云盘应用 Docker 镜像构建工具 ==="
-
-# 检查可执行文件
-if [ ! -f "dist/cloud-drive-server.exe" ]; then
- echo "错误: 未找到可执行文件"
- echo "请先运行: python package-app.py"
- exit 1
-fi
-
-# 创建临时目录
-TEMP_DIR="temp-docker"
-rm -rf $TEMP_DIR
-mkdir -p $TEMP_DIR
-
-echo "正在准备Docker镜像内容..."
-
-# 复制可执行文件
-cp dist/cloud-drive-server.exe $TEMP_DIR/
-
-# 创建运行脚本
-cat > $TEMP_DIR/start.sh << 'EOF'
-#!/bin/sh
-# 设置时区
-export TZ=Asia/Shanghai
-ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
-
-# 创建必要目录
-mkdir -p /app/uploads /app/logs
-
-# 启动应用
-exec ./cloud-drive-server.exe
-EOF
-
-chmod +x $TEMP_DIR/start.sh
-
-# 创建简化的Dockerfile
-cat > $TEMP_DIR/Dockerfile << 'EOF'
-# 使用scratch基础镜像(无依赖)
-FROM scratch
-
-# 复制可执行文件和脚本
-COPY cloud-drive-server.exe /
-COPY start.sh /
-
-# 设置执行权限
-CMD ["/start.sh"]
-EOF
-
-echo "Docker镜像内容准备完成"
-echo "临时目录: $TEMP_DIR"
-
-# 如果可以使用Docker
-if command -v docker &> /dev/null; then
- echo "正在构建Docker镜像..."
- cd $TEMP_DIR
-
- # 尝试构建
- if docker build -t cloud-drive-backend:simple . 2>/dev/null; then
- echo "OK Docker镜像构建成功"
- echo "镜像名称: cloud-drive-backend:simple"
- echo ""
- echo "运行命令:"
- echo " docker run -d -p 8002:8002 --name cloud-drive-backend cloud-drive-backend:simple"
- else
- echo "Docker镜像构建失败,可能是网络问题"
- echo "请检查Docker网络配置或稍后重试"
- fi
-
- cd ..
-else
- echo "未找到Docker命令"
-fi
-
-echo "=== 构建完成 ==="
\ No newline at end of file
diff --git a/backend/simple_files_check.py b/backend/simple_files_check.py
deleted file mode 100644
index f92be08..0000000
--- a/backend/simple_files_check.py
+++ /dev/null
@@ -1,168 +0,0 @@
-#!/usr/bin/env python3
-"""
-简化版文件存储检查脚本
-"""
-
-import mysql.connector
-import os
-import hashlib
-
-def check_files_storage():
- """检查文件存储情况"""
-
- print("=== 文件存储情况检查 ===")
-
- try:
- # 连接数据库
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- # 查询所有文件
- cursor.execute("""
- SELECT id, user_id, original_filename, filename, file_path, file_size,
- file_hash, mime_type, created_at
- FROM files
- ORDER BY created_at DESC
- """)
-
- db_files = cursor.fetchall()
- print(f"数据库中的文件记录数: {len(db_files)}")
- print()
-
- print("=== 数据库中的文件记录 ===")
- for file in db_files:
- (id, user_id, original_filename, filename, file_path,
- file_size, file_hash, mime_type, created_at) = file
-
- print(f"ID: {id}")
- print(f" 原始文件名: {original_filename}")
- print(f" 存储文件名: {filename}")
- print(f" 文件大小: {file_size} bytes")
- print(f" MIME类型: {mime_type}")
- print(f" 创建时间: {created_at}")
- print("-" * 40)
-
- # 检查实际文件存在情况
- print("\n=== 文件存在性检查 ===")
- existing_count = 0
- for file in db_files:
- (id, user_id, original_filename, filename, file_path,
- file_size, file_hash, mime_type, created_at) = file
-
- full_path = os.path.join("uploads", filename)
- if os.path.exists(full_path):
- existing_count += 1
- print(f"[存在] ID {id}: {original_filename}")
- else:
- print(f"[缺失] ID {id}: {original_filename}")
-
- print(f"\n实际存在的文件数: {existing_count}")
- print(f"缺失的文件数: {len(db_files) - existing_count}")
-
- # 检查uploads目录详情
- print("\n=== uploads目录详情 ===")
- uploads_dir = "uploads"
- if os.path.exists(uploads_dir):
- files = os.listdir(uploads_dir)
- print(f"uploads目录中的文件数: {len(files)}")
-
- for file in files:
- file_path = os.path.join(uploads_dir, file)
- file_size = os.path.getsize(file_path)
- print(f"文件: {file}, 大小: {file_size} bytes")
- else:
- print("uploads目录不存在")
-
- except Exception as e:
- print(f"检查出错: {e}")
- finally:
- if 'conn' in locals() and conn.is_connected():
- cursor.close()
- conn.close()
-
-def check_file_integrity():
- """检查文件完整性"""
-
- print("\n=== 文件完整性检查 ===")
-
- try:
- conn = mysql.connector.connect(
- host="101.126.85.76",
- user="mytest_db",
- password="mytest_db",
- database="mytest_db"
- )
- cursor = conn.cursor()
-
- cursor.execute("SELECT id, filename, file_hash, file_size FROM files")
- db_files = cursor.fetchall()
-
- integrity_ok = True
-
- for (id, filename, expected_hash, expected_size) in db_files:
- full_path = os.path.join("uploads", filename)
-
- if os.path.exists(full_path):
- actual_size = os.path.getsize(full_path)
- if actual_size != expected_size:
- print(f"ID {id}: 文件大小不匹配 (期望: {expected_size}, 实际: {actual_size})")
- integrity_ok = False
- continue
-
- try:
- with open(full_path, 'rb') as f:
- content = f.read()
- actual_hash = hashlib.sha256(content).hexdigest()
-
- if actual_hash != expected_hash:
- print(f"ID {id}: 文件哈希不匹配")
- print(f" 期望: {expected_hash}")
- print(f" 实际: {actual_hash}")
- integrity_ok = False
- else:
- print(f"ID {id}: 完整性检查通过")
- except Exception as e:
- print(f"ID {id}: 无法计算哈希 - {e}")
- integrity_ok = False
- else:
- print(f"ID {id}: 文件不存在")
- integrity_ok = False
-
- if integrity_ok:
- print("所有文件完整性检查通过!")
- else:
- print("发现文件完整性问题!")
-
- except Exception as e:
- print(f"完整性检查出错: {e}")
- finally:
- if 'conn' in locals() and conn.is_connected():
- cursor.close()
- conn.close()
-
-if __name__ == "__main__":
- check_files_storage()
- check_file_integrity()
-
- print("\n=== 文件存储架构总结 ===")
- print("1. 数据库(files表): 存储文件元数据")
- print(" - 文件ID、用户ID、原始文件名")
- print(" - 存储文件名(UUID格式)")
- print(" - 文件大小、MIME类型")
- print(" - SHA-256哈希值")
- print(" - 创建时间等")
- print()
- print("2. 文件系统(uploads目录): 存储实际文件")
- print(" - 文件使用UUID命名确保唯一性")
- print(" - 文件内容与数据库记录一一对应")
- print(" - 通过file_hash验证完整性")
- print()
- print("3. 回答您的问题:")
- print(" 是的,数据库中存储的是文件元数据,")
- print(" 实际文件内容存储在服务器的uploads目录中。")
- print(" 两者通过file_hash保持关联和完整性验证。")
\ No newline at end of file
diff --git a/backend/simple_hash_demo.py b/backend/simple_hash_demo.py
deleted file mode 100644
index 048f68f..0000000
--- a/backend/simple_hash_demo.py
+++ /dev/null
@@ -1,226 +0,0 @@
-#!/usr/bin/env python3
-"""
-简化版文件哈希演示脚本
-"""
-
-import hashlib
-import requests
-import os
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-USER_ID = 8
-
-def calculate_sha256_hash(file_content: bytes) -> str:
- """计算文件的SHA-256哈希值"""
- return hashlib.sha256(file_content).hexdigest()
-
-def upload_and_demo_hash():
- """上传文件并演示哈希功能"""
-
- # 创建测试文件内容
- original_content = "Hello World! 这是演示文件哈希的测试内容。"
-
- print("=== 文件哈希演示 ===")
- print("原始文件内容:")
- print(f"'{original_content}'")
- print(f"文件大小: {len(original_content.encode('utf-8'))} bytes")
- print()
-
- # 计算哈希值
- file_hash = calculate_sha256_hash(original_content.encode('utf-8'))
- print("计算的SHA-256哈希值:")
- print(file_hash)
- print()
-
- # 上传文件
- try:
- files = {
- "file": ("hash_demo.txt", original_content.encode('utf-8'), "text/plain")
- }
- data = {
- "user_id": USER_ID,
- "description": "哈希演示文件",
- "tags": "demo,hash",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- files=files,
- data=data
- )
-
- if response.status_code == 201:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- server_hash = file_info["file_hash"]
- file_id = file_info["id"]
-
- print("文件上传成功!")
- print(f"文件ID: {file_id}")
- print(f"服务器哈希值: {server_hash}")
- print()
-
- # 验证哈希值一致性
- if file_hash == server_hash:
- print("哈希值验证通过! 客户端和服务器计算结果一致")
- else:
- print("哈希值验证失败!")
- print(f"客户端: {file_hash}")
- print(f"服务器: {server_hash}")
-
- return file_id, original_content, file_hash, file_info['filename']
- else:
- print(f"上传失败: {response.text}")
- return None, None, None, None
-
- except Exception as e:
- print(f"上传出错: {e}")
- return None, None, None, None
-
-def verify_download_integrity(file_id, original_content, original_hash, filename):
- """验证下载文件的完整性"""
-
- print("\n=== 文件下载和完整性验证 ===")
-
- try:
- # 下载文件
- data = {
- "user_id": USER_ID,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/download",
- json=data
- )
-
- if response.status_code == 200:
- downloaded_content = response.content.decode('utf-8')
-
- print("下载的文件内容:")
- print(f"'{downloaded_content}'")
- print()
-
- # 验证内容完整性
- if downloaded_content == original_content:
- print("内容完整性验证通过!")
- else:
- print("内容完整性验证失败!")
-
- # 计算下载文件的哈希值
- downloaded_hash = calculate_sha256_hash(downloaded_content.encode('utf-8'))
- print("下载文件的哈希值:")
- print(downloaded_hash)
- print()
-
- # 验证哈希值
- if downloaded_hash == original_hash:
- print("下载文件哈希验证通过! 文件完整性得到保证")
- else:
- print("下载文件哈希验证失败! 文件可能已损坏")
- print(f"原始哈希: {original_hash}")
- print(f"下载哈希: {downloaded_hash}")
-
- else:
- print(f"下载失败: {response.text}")
-
- except Exception as e:
- print(f"下载过程出错: {e}")
-
-def show_server_file_info(filename):
- """显示服务器上文件的信息"""
-
- print("\n=== 服务器文件信息 ===")
-
- # 检查uploads目录
- upload_path = os.path.join("uploads", filename)
- if os.path.exists(upload_path):
- file_size = os.path.getsize(upload_path)
- print(f"文件路径: {upload_path}")
- print(f"文件大小: {file_size} bytes")
-
- # 计算文件哈希
- with open(upload_path, 'rb') as f:
- content = f.read()
- file_hash = calculate_sha256_hash(content)
- print(f"文件SHA-256哈希: {file_hash}")
-
- # 显示文件内容
- with open(upload_path, 'r', encoding='utf-8') as f:
- content = f.read()
- print(f"文件内容: '{content}'")
- else:
- print(f"文件不存在: {upload_path}")
-
-def demonstrate_hash_properties():
- """演示哈希的重要特性"""
-
- print("\n=== 哈希特性演示 ===")
-
- # 特性1: 相同输入产生相同哈希
- text1 = "Hello World"
- text2 = "Hello World"
- hash1 = calculate_sha256_hash(text1.encode())
- hash2 = calculate_sha256_hash(text2.encode())
-
- print("特性1: 相同输入产生相同哈希")
- print(f"文本1: '{text1}' -> {hash1}")
- print(f"文本2: '{text2}' -> {hash2}")
- print(f"哈希值相同: {hash1 == hash2}")
- print()
-
- # 特性2: 微小变化导致完全不同的哈希
- text3 = "Hello World"
- text4 = "Hello World!" # 只多了一个感叹号
- hash3 = calculate_sha256_hash(text3.encode())
- hash4 = calculate_sha256_hash(text4.encode())
-
- print("特性2: 微小变化导致完全不同的哈希")
- print(f"文本3: '{text3}' -> {hash3}")
- print(f"文本4: '{text4}' -> {hash4}")
- print(f"哈希值不同: {hash3 != hash4}")
- print()
-
- # 特性3: 不可逆性
- sample_hash = "a591a6d40bf420404a011733cfb7b190d62c65bf0bcda32b57b277d9ad9f146e"
- print("特性3: 哈希是单向的,无法从哈希反推原始内容")
- print(f"示例哈希: {sample_hash}")
- print("无法从这个哈希值推断出原始文本内容")
- print()
-
-def main():
- """主演示函数"""
-
- # 演示哈希特性
- demonstrate_hash_properties()
-
- # 上传并演示哈希功能
- file_id, original_content, original_hash, filename = upload_and_demo_hash()
-
- if file_id:
- # 验证下载完整性
- verify_download_integrity(file_id, original_content, original_hash, filename)
-
- # 显示服务器文件信息
- show_server_file_info(filename)
-
- print("\n=== 总结 ===")
- print("file_hash 的作用:")
- print("1. 完整性验证 - 确保文件在传输存储过程中未损坏")
- print("2. 文件去重 - 相同内容只存储一份,节省空间")
- print("3. 安全检查 - 防止恶意文件和内容篡改")
- print("4. 快速比较 - 通过哈希值快速判断文件是否相同")
- print()
- print("如何还原文件:")
- print("1. 通过API下载: POST /api/v1/files/download")
- print("2. 直接从服务器目录读取: backend/uploads/[filename]")
- print("3. 验证文件完整性: 计算SHA-256哈希并与数据库中的file_hash比较")
-
- else:
- print("演示失败,无法上传测试文件")
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/simple_http_server.py b/backend/simple_http_server.py
deleted file mode 100644
index 75442ac..0000000
--- a/backend/simple_http_server.py
+++ /dev/null
@@ -1,107 +0,0 @@
-#!/usr/bin/env python3
-# 简单的HTTP服务器用于端口测试
-
-from http.server import HTTPServer, BaseHTTPRequestHandler
-import json
-import socket
-import time
-
-class SimpleHandler(BaseHTTPRequestHandler):
- def do_GET(self):
- print(f"收到请求: {self.path}")
-
- # 设置响应头
- self.send_response(200)
- self.send_header('Content-Type', 'application/json')
- self.send_header('Access-Control-Allow-Origin', '*')
- self.end_headers()
-
- # 根据路径返回不同响应
- if self.path == '/':
- response = {
- "message": "简单HTTP服务器运行正常",
- "port": 8080,
- "status": "ok"
- }
- elif self.path == '/health':
- response = {
- "status": "healthy",
- "timestamp": time.time(),
- "server": "simple-http-server"
- }
- elif self.path == '/api/v1/health':
- response = {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0",
- "server": "simple-http-server"
- }
- elif self.path == '/test':
- response = {
- "test": "ok",
- "message": "测试端点正常工作"
- }
- else:
- response = {
- "error": "Not Found",
- "message": "路径不存在",
- "path": self.path
- }
-
- self.wfile.write(json.dumps(response, ensure_ascii=False).encode('utf-8'))
-
- def do_OPTIONS(self):
- # 处理CORS预检请求
- self.send_response(200)
- self.send_header('Access-Control-Allow-Origin', '*')
- self.send_header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS')
- self.send_header('Access-Control-Allow-Headers', 'Content-Type')
- self.end_headers()
-
-def check_port_available(port):
- """检查端口是否可用"""
- try:
- with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
- s.bind(('0.0.0.0', port))
- return True
- except OSError:
- return False
-
-def main():
- port = 8080
-
- print("🔍 检查端口可用性...")
- if not check_port_available(port):
- print(f"❌ 端口 {port} 被占用")
- # 尝试其他端口
- for test_port in range(8001, 8010):
- if check_port_available(test_port):
- print(f"✅ 使用端口 {test_port}")
- port = test_port
- break
- else:
- print("❌ 无法找到可用端口")
- return
-
- print(f"🚀 启动简单HTTP服务器在端口 {port}")
- print("=" * 50)
- print(f"📍 本地访问: http://localhost:{port}")
- print(f"📋 测试端点:")
- print(f" 根路径: http://localhost:{port}/")
- print(f" 健康检查: http://localhost:{port}/health")
- print(f" API健康: http://localhost:{port}/api/v1/health")
- print(f" 测试端点: http://localhost:{port}/test")
- print("=" * 50)
- print("⏹️ 按 Ctrl+C 停止服务")
-
- try:
- server = HTTPServer(('0.0.0.0', port), SimpleHandler)
- print(f"✅ 服务器已启动在端口 {port}")
- server.serve_forever()
- except KeyboardInterrupt:
- print("\n🛑 服务器已停止")
- except Exception as e:
- print(f"❌ 服务器错误: {e}")
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/simple_main.py b/backend/simple_main.py
deleted file mode 100644
index 823fa0a..0000000
--- a/backend/simple_main.py
+++ /dev/null
@@ -1,79 +0,0 @@
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-import time
-
-app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-# CORS中间件
-app.add_middleware(
- CORSMiddleware,
- allow_origins=["http://localhost:3000", "http://127.0.0.1:3000"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-@app.get("/")
-async def root():
- return {"message": "云盘应用 API", "version": "1.0.0"}
-
-@app.get("/api/v1/health")
-async def health_check():
- """基础健康检查"""
- return {
- "success": True,
- "data": {
- "status": "healthy",
- "service": "cloud-drive-api",
- "environment": "development",
- "timestamp": int(time.time())
- },
- "message": "API服务运行正常"
- }
-
-@app.get("/api/v1/ready")
-async def readiness_check():
- """就绪检查 - 简化版本,不检查数据库"""
- checks = {
- "api": {
- "status": "healthy",
- "message": "API服务正常"
- },
- "database": {
- "status": "unknown",
- "message": "数据库连接未配置(简化模式)"
- },
- "redis": {
- "status": "unknown",
- "message": "Redis连接未配置(简化模式)"
- },
- "storage": {
- "status": "healthy",
- "message": "文件存储正常"
- }
- }
-
- return {
- "success": True,
- "data": {
- "status": "ready",
- "checks": checks,
- "timestamp": int(time.time())
- },
- "message": "API服务已就绪(简化模式)"
- }
-
-if __name__ == "__main__":
- import uvicorn
- uvicorn.run(
- "simple_main:app",
- host="0.0.0.0",
- port=8000,
- reload=True
- )
\ No newline at end of file
diff --git a/backend/simple_server_8080.py b/backend/simple_server_8080.py
deleted file mode 100644
index 7ff0e37..0000000
--- a/backend/simple_server_8080.py
+++ /dev/null
@@ -1,208 +0,0 @@
-#!/usr/bin/env python3
-# 简化版FastAPI服务器 - 端口8080
-
-import sys
-import os
-from pathlib import Path
-
-# 添加当前目录到Python路径
-current_dir = Path(__file__).parent
-sys.path.insert(0, str(current_dir))
-
-try:
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
- FASTAPI_AVAILABLE = True
-except ImportError:
- print("❌ FastAPI未安装,正在安装基础依赖...")
- import subprocess
- subprocess.run([sys.executable, "-m", "pip", "install", "fastapi", "uvicorn", "requests"])
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
- FASTAPI_AVAILABLE = True
-
-# 尝试导入app模块
-try:
- from app.core.config import settings
- from app.api.v1.endpoints import health, auth, files
- APP_AVAILABLE = True
- print("✅ 完整app模块可用")
-except ImportError as e:
- print(f"⚠️ App模块导入失败: {e}")
- print("🔧 使用简化模式启动...")
- APP_AVAILABLE = False
-
-def create_app():
- """创建FastAPI应用"""
- if APP_AVAILABLE:
- # 使用完整的应用
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- try:
- app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
- except:
- # 如果settings有问题,使用默认配置
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 包含路由
- try:
- app.include_router(health.router, prefix="/api/v1", tags=["health"])
- app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
- app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
- except Exception as e:
- print(f"⚠️ 路由包含失败: {e}")
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.1",
- "docs": "/docs",
- "health": "/api/v1/health",
- "mode": "full"
- }
-
- return app
- else:
- # 创建简化版本的应用
- app = FastAPI(
- title="云盘应用 API (简化版)",
- description="云存储Web应用后端API - 简化版本",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API (简化版)",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/health",
- "mode": "simplified"
- }
-
- @app.get("/health")
- async def health_check():
- return {
- "status": "healthy",
- "message": "服务运行正常",
- "mode": "simplified"
- }
-
- @app.get("/api/v1/health")
- async def api_health():
- import time
- return {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0"
- }
-
- @app.get("/api/v1/test")
- async def test_endpoint():
- return {
- "message": "测试端点正常工作",
- "server": "port 8080",
- "status": "ok"
- }
-
- return app
-
-def main():
- """主函数"""
- print("🚀 启动云盘应用服务器...")
- print("=" * 50)
-
- # 创建必要目录
- os.makedirs("logs", exist_ok=True)
- os.makedirs("uploads", exist_ok=True)
-
- # 创建FastAPI应用
- app = create_app()
-
- # 获取本机IP
- try:
- import socket
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- local_ip = s.getsockname()[0]
- s.close()
- except:
- local_ip = "127.0.0.1"
-
- # 显示启动信息
- print(f"📍 本地访问:")
- print(f" 根路径: http://localhost:8080")
- print(f" API文档: http://localhost:8080/docs")
- print(f" ReDoc: http://localhost:8080/redoc")
- print(f" 健康检查: http://localhost:8080/api/v1/health")
- print(f" 测试端点: http://localhost:8080/api/v1/test")
- print("")
- print(f"🌐 网络访问:")
- print(f" 根路径: http://{local_ip}:8080")
- print(f" API文档: http://{local_ip}:8080/docs")
- print("")
- print("🔧 服务信息:")
- print(f" Python版本: {sys.version}")
- print(f" 工作目录: {os.getcwd()}")
- print(f" 启动模式: {'完整版' if APP_AVAILABLE else '简化版'}")
- print("=" * 50)
- print("⏹️ 按 Ctrl+C 停止服务")
- print("")
-
- # 启动服务器
- try:
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8080,
- reload=False,
- access_log=True,
- log_level="info"
- )
- except KeyboardInterrupt:
- print("\n🛑 服务已停止")
- except Exception as e:
- print(f"❌ 启动失败: {e}")
- print("\n💡 可能的解决方案:")
- print("1. 检查端口8080是否被占用")
- print("2. 确保安装了必要的依赖: pip install fastapi uvicorn")
- print("3. 检查防火墙设置")
- return False
-
- return True
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/simple_start.py b/backend/simple_start.py
deleted file mode 100644
index 01ada15..0000000
--- a/backend/simple_start.py
+++ /dev/null
@@ -1,54 +0,0 @@
-#!/usr/bin/env python3
-# 最简单的启动方式
-
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-import uvicorn
-
-app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-# CORS中间件
-app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-@app.get("/")
-async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/health"
- }
-
-@app.get("/health")
-async def health():
- return {
- "status": "healthy",
- "message": "服务运行正常"
- }
-
-if __name__ == "__main__":
- print("🚀 启动云盘后端服务...")
- print("📍 服务地址: http://localhost:8000")
- print("📚 API文档: http://localhost:8000/docs")
- print("❤️ 健康检查: http://localhost:8000/health")
- print("⏹️ 按 Ctrl+C 停止服务")
- print("=" * 50)
-
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8000,
- reload=False
- )
\ No newline at end of file
diff --git a/backend/simple_test.py b/backend/simple_test.py
deleted file mode 100644
index 8138b63..0000000
--- a/backend/simple_test.py
+++ /dev/null
@@ -1,172 +0,0 @@
-#!/usr/bin/env python3
-"""
-简单的文件上传测试脚本
-"""
-
-import requests
-import json
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-def test_auth():
- """测试认证"""
- # 先注册
- register_data = {
- "username": "testuser",
- "email": "test@example.com",
- "password": "TestPass123!",
- "confirm_password": "TestPass123!"
- }
-
- try:
- print("尝试注册用户...")
- reg_response = requests.post(f"{BASE_URL}/auth/register", json=register_data)
- print(f"注册状态码: {reg_response.status_code}")
-
- if reg_response.status_code == 201:
- reg_result = reg_response.json()
- if reg_result.get("success"):
- token = reg_result["data"]["tokens"]["access_token"]
- print("注册成功,获得token")
- return token
- else:
- print(f"注册失败: {reg_result}")
- else:
- print(f"注册请求失败,状态码: {reg_response.status_code}")
-
- # 如果注册失败,尝试登录
- print("尝试登录用户...")
- login_data = {
- "username": "testuser",
- "password": "testpass123"
- }
-
- response = requests.post(f"{BASE_URL}/auth/login", json=login_data)
- print(f"登录状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- print(f"登录结果: {result.get('success', False)}")
- if result.get("success"):
- token = result["data"]["tokens"]["access_token"]
- print("登录成功,获得token")
- return token
- else:
- print(f"登录失败: {result}")
-
- return None
- except Exception as e:
- print(f"认证出错: {e}")
- return None
-
-def test_file_upload(token):
- """测试文件上传"""
- headers = {
- "Authorization": f"Bearer {token}"
- }
-
- # 创建测试文件
- test_content = "Hello World! 测试文件内容"
-
- try:
- files = {
- "file": ("test.txt", test_content.encode("utf-8"), "text/plain")
- }
- data = {
- "description": "测试文件",
- "tags": "test,upload",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- headers=headers,
- files=files,
- data=data
- )
-
- print(f"上传状态码: {response.status_code}")
- print(f"上传响应: {response.text}")
-
- if response.status_code == 201:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- print(f"上传成功! 文件ID: {file_info['id']}")
- return file_info['id']
-
- return None
- except Exception as e:
- print(f"上传出错: {e}")
- return None
-
-def test_file_list(token):
- """测试获取文件列表"""
- headers = {
- "Authorization": f"Bearer {token}"
- }
-
- try:
- response = requests.get(
- f"{BASE_URL}/files/list",
- headers=headers
- )
-
- print(f"列表状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- files = result["data"]["files"]
- print(f"文件数量: {len(files)}")
- for f in files:
- print(f" - {f['original_filename']} ({f['file_size']} bytes)")
-
- except Exception as e:
- print(f"获取列表出错: {e}")
-
-def test_storage_info(token):
- """测试存储信息"""
- headers = {
- "Authorization": f"Bearer {token}"
- }
-
- try:
- response = requests.get(
- f"{BASE_URL}/files/storage/info",
- headers=headers
- )
-
- print(f"存储信息状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- info = result["data"]
- print(f"存储配额: {info['total_quota']} bytes")
- print(f"已使用: {info['used_space']} bytes")
- print(f"文件数量: {info['file_count']}")
-
- except Exception as e:
- print(f"获取存储信息出错: {e}")
-
-if __name__ == "__main__":
- print("开始测试文件存储功能...")
-
- # 1. 认证
- token = test_auth()
- if not token:
- print("认证失败,退出测试")
- exit(1)
-
- # 2. 上传文件
- file_id = test_file_upload(token)
-
- # 3. 获取文件列表
- test_file_list(token)
-
- # 4. 获取存储信息
- test_storage_info(token)
-
- print("测试完成!")
\ No newline at end of file
diff --git a/backend/simple_upload_test.py b/backend/simple_upload_test.py
deleted file mode 100644
index 7e062a5..0000000
--- a/backend/simple_upload_test.py
+++ /dev/null
@@ -1,112 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-简单上传下载测试
-"""
-
-import requests
-import sys
-import io
-
-# 设置stdout编码为utf-8
-sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8")
-
-BASE_URL = "http://localhost:8000/api/v1"
-
-def simple_test():
- print("=== 简单上传下载测试 ===")
-
- # 使用存在的用户ID (用户ID=3存在)
- user_id = 3
- print(f"使用用户ID: {user_id}")
-
- # 直接测试下载现有文件 (文件ID=24, test.txt)
- file_id = 24
- print(f"\n直接下载现有文件 ID: {file_id} (test.txt)...")
-
- download_data = {
- "file_id": file_id,
- "user_id": user_id
- }
-
- try:
- download_resp = requests.post(f"{BASE_URL}/files/download", json=download_data)
- print(f"下载状态码: {download_resp.status_code}")
- print(f"下载响应头: {dict(download_resp.headers)}")
-
- if download_resp.status_code == 200:
- downloaded_content = download_resp.text
- print(f"[OK] 下载成功")
- print(f"下载内容: {downloaded_content}")
- print(f"内容长度: {len(downloaded_content)}")
-
- # 读取原始文件内容进行对比
- try:
- with open(f"uploads/608408b0-02c7-449e-ba58-be43c4360333.txt", 'r', encoding='utf-8') as f:
- original_content = f.read()
- print(f"原始文件长度: {len(original_content)}")
-
- if original_content == downloaded_content:
- print("[OK] 内容一致!上传下载功能正常")
- else:
- print("[ERROR] 内容不一致")
- print(f"原始: {repr(original_content[:100])}")
- print(f"下载: {repr(downloaded_content[:100])}")
- except Exception as e:
- print(f"无法读取原始文件进行对比: {e}")
-
- else:
- print(f"[ERROR] 下载失败: {download_resp.text}")
- except Exception as e:
- print(f"[ERROR] 下载异常: {e}")
- import traceback
- traceback.print_exc()
-
- # 现在测试上传新文件
- print(f"\n=== 测试上传新文件 ===")
- test_content = f"这是全新的测试文件内容\nBrand new test file content\n唯一时间戳: {hash('unique_content_' + str(__import__('time').time()))}"
-
- files = {"file": (f"unique_test_{hash(test_content) % 10000}.txt", test_content, "text/plain")}
- data = {
- "user_id": str(user_id),
- "description": "新测试文件",
- "tags": "test,new",
- "is_public": "false"
- }
-
- try:
- upload_resp = requests.post(f"{BASE_URL}/files/upload", files=files, data=data)
- print(f"上传状态码: {upload_resp.status_code}")
-
- if upload_resp.status_code == 201:
- new_file_id = upload_resp.json()["data"]["file"]["id"]
- print(f"[OK] 新文件上传成功,文件ID: {new_file_id}")
-
- # 立即下载新文件
- print(f"\n下载新上传的文件 ID: {new_file_id}...")
- download_data = {
- "file_id": new_file_id,
- "user_id": user_id
- }
-
- download_resp = requests.post(f"{BASE_URL}/files/download", json=download_data)
- if download_resp.status_code == 200:
- new_downloaded_content = download_resp.text
- print(f"[OK] 新文件下载成功")
- print(f"下载内容: {new_downloaded_content}")
-
- if test_content == new_downloaded_content:
- print("[OK] 新文件内容一致!")
- else:
- print("[ERROR] 新文件内容不一致")
- else:
- print(f"[ERROR] 新文件下载失败: {download_resp.text}")
- else:
- print(f"[ERROR] 新文件上传失败: {upload_resp.text}")
- except Exception as e:
- print(f"[ERROR] 新文件测试异常: {e}")
- import traceback
- traceback.print_exc()
-
-if __name__ == "__main__":
- simple_test()
diff --git a/backend/start_8080.py b/backend/start_8080.py
deleted file mode 100644
index f3c0e16..0000000
--- a/backend/start_8080.py
+++ /dev/null
@@ -1,314 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-云盘应用启动脚本 - 端口8080版本
-包含完整的API测试功能
-"""
-
-import os
-import sys
-from pathlib import Path
-
-# 添加当前目录到Python路径
-current_dir = Path(__file__).parent
-sys.path.insert(0, str(current_dir))
-
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-import uvicorn
-import subprocess
-import time
-import requests
-from typing import Dict, List
-
-# 导入应用模块
-try:
- from app.core.config import settings
- from app.api.v1.endpoints import health, auth, files
- APP_AVAILABLE = True
-except ImportError as e:
- print(f"⚠️ App模块导入失败: {e}")
- print("🔧 使用简化模式启动...")
- APP_AVAILABLE = False
-
-def create_fastapi_app():
- """创建FastAPI应用"""
- if APP_AVAILABLE:
- # 使用完整的应用
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 包含路由
- app.include_router(health.router, prefix="/api/v1", tags=["health"])
- app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
- app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.1",
- "docs": "/docs",
- "health": "/api/v1/health"
- }
-
- return app
- else:
- # 创建简化版本的应用
- app = FastAPI(
- title="云盘应用 API (简化版)",
- description="云存储Web应用后端API - 简化版本",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API (简化版)",
- "version": "1.0.0",
- "docs": "/docs",
- "health": "/health"
- }
-
- @app.get("/health")
- async def health_check():
- return {
- "status": "healthy",
- "message": "服务运行正常",
- "mode": "simplified"
- }
-
- @app.get("/api/v1/health")
- async def api_health():
- return {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0"
- }
-
- return app
-
-def test_api_endpoints(base_url: str = "http://localhost:8080") -> Dict[str, any]:
- """测试API端点"""
- print("\n🧪 开始测试API端点...")
- print("=" * 50)
-
- results = {}
-
- # 测试端点列表
- endpoints = [
- ("/", "根路径"),
- ("/health", "健康检查"),
- ("/api/v1/health", "API健康检查"),
- ("/docs", "API文档"),
- ("/redoc", "ReDoc文档"),
- ("/openapi.json", "OpenAPI规范")
- ]
-
- for endpoint, description in endpoints:
- try:
- print(f"📍 测试 {description}: {endpoint}")
-
- if endpoint in ["/docs", "/redoc"]:
- # 对于文档端点,只检查HTTP状态
- response = requests.get(f"{base_url}{endpoint}", timeout=5)
- if response.status_code == 200:
- print(f" ✅ {description} - 状态码: {response.status_code}")
- results[endpoint] = {"status": "success", "code": response.status_code}
- else:
- print(f" ❌ {description} - 状态码: {response.status_code}")
- results[endpoint] = {"status": "failed", "code": response.status_code}
- else:
- # 对于API端点,检查响应内容
- response = requests.get(f"{base_url}{endpoint}", timeout=5)
- if response.status_code == 200:
- data = response.json()
- print(f" ✅ {description} - 响应: {data}")
- results[endpoint] = {"status": "success", "data": data}
- else:
- print(f" ❌ {description} - 状态码: {response.status_code}")
- results[endpoint] = {"status": "failed", "code": response.status_code}
-
- except requests.exceptions.ConnectionError:
- print(f" ❌ {description} - 连接失败")
- results[endpoint] = {"status": "connection_failed"}
- except requests.exceptions.Timeout:
- print(f" ❌ {description} - 请求超时")
- results[endpoint] = {"status": "timeout"}
- except Exception as e:
- print(f" ❌ {description} - 错误: {e}")
- results[endpoint] = {"status": "error", "error": str(e)}
-
- return results
-
-def start_server():
- """启动服务器"""
- print("🚀 启动云盘应用服务...")
- print("=" * 50)
-
- # 创建必要目录
- os.makedirs("logs", exist_ok=True)
- os.makedirs("uploads", exist_ok=True)
-
- # 创建FastAPI应用
- app = create_fastapi_app()
-
- # 获取本机IP
- import socket
- try:
- s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
- s.connect(("8.8.8.8", 80))
- local_ip = s.getsockname()[0]
- s.close()
- except:
- local_ip = "127.0.0.1"
-
- # 显示启动信息
- print(f"📍 本地访问:")
- print(f" 根路径: http://localhost:8080")
- print(f" API文档: http://localhost:8080/docs")
- print(f" ReDoc: http://localhost:8080/redoc")
- print(f" 健康检查: http://localhost:8080/api/v1/health")
- print("")
- print(f"🌐 网络访问:")
- print(f" 根路径: http://{local_ip}:8080")
- print(f" API文档: http://{local_ip}:8080/docs")
- print(f" ReDoc: http://{local_ip}:8080/redoc")
- print("")
- print(f"🔧 API测试:")
- print(f" 自动测试将在服务启动后执行")
- print("=" * 50)
- print("⏹️ 按 Ctrl+C 停止服务")
- print("")
-
- # 启动服务器
- try:
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8080,
- reload=False,
- access_log=True,
- log_level="info"
- )
- except KeyboardInterrupt:
- print("\n🛑 服务已停止")
- except Exception as e:
- print(f"❌ 启动失败: {e}")
- return False
-
- return True
-
-def run_with_auto_test():
- """启动服务器并自动测试"""
- print("🤖 自动模式:启动服务器并进行API测试")
-
- # 启动服务器(在后台)
- import subprocess
- import signal
- import threading
-
- # 启动服务器进程
- server_process = subprocess.Popen([
- sys.executable, __file__
- ], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
-
- # 等待服务器启动
- print("⏳ 等待服务器启动...")
- time.sleep(5)
-
- try:
- # 测试API端点
- results = test_api_endpoints()
-
- # 显示测试结果
- print("\n📊 测试结果汇总:")
- print("=" * 50)
-
- success_count = sum(1 for r in results.values() if r.get("status") == "success")
- total_count = len(results)
-
- print(f"成功: {success_count}/{total_count}")
-
- for endpoint, result in results.items():
- status = result.get("status", "unknown")
- if status == "success":
- print(f" ✅ {endpoint}")
- else:
- print(f" ❌ {endpoint} - {status}")
-
- if success_count == total_count:
- print("\n🎉 所有API端点测试通过!")
- else:
- print(f"\n⚠️ {total_count - success_count} 个端点测试失败")
-
- finally:
- # 停止服务器
- print("\n🛑 停止服务器...")
- server_process.terminate()
- server_process.wait()
-
-if __name__ == "__main__":
- import argparse
-
- parser = argparse.ArgumentParser(description="云盘应用启动器 - 端口8080")
- parser.add_argument("--test", action="store_true", help="启动后自动测试API端点")
- parser.add_argument("--auto", action="store_true", help="自动模式:启动并测试")
- args = parser.parse_args()
-
- if args.auto:
- run_with_auto_test()
- elif args.test:
- # 先启动,再测试
- print("🚀 启动服务器...")
- app = create_fastapi_app()
-
- # 在单独线程中启动服务器
- import threading
-
- def run_server():
- uvicorn.run(app, host="0.0.0.0", port=8080, reload=False, log_level="warning")
-
- server_thread = threading.Thread(target=run_server, daemon=True)
- server_thread.start()
-
- # 等待服务器启动
- time.sleep(3)
-
- # 测试API
- test_api_endpoints()
-
- print("\n服务器继续运行,按 Ctrl+C 停止...")
- try:
- while True:
- time.sleep(1)
- except KeyboardInterrupt:
- print("\n🛑 服务已停止")
- else:
- # 正常启动
- start_server()
\ No newline at end of file
diff --git a/backend/start_and_test_8080.sh b/backend/start_and_test_8080.sh
deleted file mode 100644
index 67028d8..0000000
--- a/backend/start_and_test_8080.sh
+++ /dev/null
@@ -1,54 +0,0 @@
-#!/bin/bash
-# 启动服务并测试API的脚本
-
-echo "🚀 云盘应用启动和测试脚本"
-echo "=================================="
-
-# 检查Python环境
-if ! command -v python3 &> /dev/null; then
- echo "❌ Python3 未安装"
- exit 1
-fi
-
-echo "✅ Python3 已安装"
-
-# 检查端口8080是否被占用
-if lsof -Pi :8080 -sTCP:LISTEN -t >/dev/null ; then
- echo "❌ 端口8080已被占用"
- echo "🔧 尝试停止占用端口的进程..."
- lsof -ti:8080 | xargs kill -9 2>/dev/null || echo "无法停止进程"
- sleep 2
-fi
-
-# 启动服务器(后台)
-echo "🚀 启动服务器在端口8080..."
-python3 start_8080.py &
-SERVER_PID=$!
-
-# 等待服务器启动
-echo "⏳ 等待服务器启动..."
-sleep 5
-
-# 测试服务器是否启动成功
-if curl -s http://localhost:8080/health > /dev/null; then
- echo "✅ 服务器启动成功"
-else
- echo "❌ 服务器启动失败"
- kill $SERVER_PID 2>/dev/null
- exit 1
-fi
-
-# 运行API测试
-echo ""
-echo "🧪 开始API测试..."
-echo "=================================="
-python3 test_api_8080.py
-
-# 停止服务器
-echo ""
-echo "🛑 停止服务器..."
-kill $SERVER_PID 2>/dev/null
-wait $SERVER_PID 2>/dev/null
-
-echo ""
-echo "✅ 测试完成!"
\ No newline at end of file
diff --git a/backend/start_simple.py b/backend/start_simple.py
deleted file mode 100644
index e0841c8..0000000
--- a/backend/start_simple.py
+++ /dev/null
@@ -1,92 +0,0 @@
-#!/usr/bin/env python3
-# 简化版启动脚本,解决模块导入问题
-
-import os
-import sys
-from pathlib import Path
-
-# 添加当前目录到Python路径
-current_dir = Path(__file__).parent
-sys.path.insert(0, str(current_dir))
-
-print(f"当前目录: {current_dir}")
-print(f"Python路径: {sys.path[:3]}...")
-
-# 检查必要目录
-required_dirs = ['app', 'app/core', 'app/api/v1/endpoints']
-for dir_path in required_dirs:
- full_path = current_dir / dir_path
- if not full_path.exists():
- print(f"创建目录: {dir_path}")
- full_path.mkdir(parents=True, exist_ok=True)
-
- # 创建__init__.py
- init_file = full_path / '__init__.py'
- if not init_file.exists():
- init_file.write_text(f'"""{dir_path} 模块包"""\n')
-
-try:
- # 测试导入
- print("测试导入模块...")
- from app.core.config import settings
- print("✓ app.core.config 导入成功")
-
- from app.api.v1.endpoints import health, auth, files
- print("✓ app.api.v1.endpoints 导入成功")
-
- # 启动FastAPI应用
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
-
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"], # 临时允许所有来源
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 包含路由
- app.include_router(health.router, prefix="/api/v1", tags=["health"])
- app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
- app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
-
- @app.get("/")
- async def root():
- return {"message": "云盘应用 API", "version": "1.0.1"}
-
- print("✓ FastAPI应用创建成功")
-
- # 启动服务
- print("启动服务...")
- print("访问地址: http://localhost:8000")
- print("API文档: http://localhost:8000/docs")
-
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8000,
- reload=False # 关闭热重载避免问题
- )
-
-except ImportError as e:
- print(f"导入错误: {e}")
- print("\n可能的解决方案:")
- print("1. 确保在正确的目录运行(包含main.py的目录)")
- print("2. 安装依赖: pip install fastapi uvicorn sqlalchemy pymysql redis python-jose passlib python-multipart pydantic pydantic-settings httpx python-dotenv loguru")
- print("3. 检查app目录结构是否完整")
- sys.exit(1)
-
-except Exception as e:
- print(f"启动错误: {e}")
- sys.exit(1)
\ No newline at end of file
diff --git a/backend/test-main.py b/backend/test-main.py
deleted file mode 100644
index 41f8d0e..0000000
--- a/backend/test-main.py
+++ /dev/null
@@ -1,76 +0,0 @@
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-from app.core.config import settings
-from app.api.v1.endpoints import health, auth, files
-import uvicorn
-from datetime import datetime
-import sys
-import os
-
-# 简单的日志打印函数
-def log_info(message):
- """打印INFO级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] INFO: {message}")
-
-def log_error(message):
- """打印ERROR级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] ERROR: {message}")
-
-def log_debug(message):
- """打印DEBUG级别日志"""
- timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
- print(f"[{timestamp}] DEBUG: {message}")
-
-# 确保logs目录存在
-os.makedirs("logs", exist_ok=True)
-
-log_info("=== Test Server Starting ===")
-log_info(f"Python version: {sys.version}")
-log_info(f"Working directory: {os.getcwd()}")
-log_info("Simple print logger configured")
-
-app = FastAPI(
- title="云盘应用 API (测试环境)",
- description="现代化的云存储Web应用后端API - 测试环境",
- version="1.0.0-test",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-# CORS中间件
-app.add_middleware(
- CORSMiddleware,
- allow_origins=settings.ALLOWED_HOSTS,
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-# 包含路由
-app.include_router(health.router, prefix="/api/v1", tags=["health"])
-app.include_router(auth.router, prefix="/api/v1/auth", tags=["authentication"])
-app.include_router(files.router, prefix="/api/v1/files", tags=["files"])
-
-@app.get("/")
-async def root():
- return {"message": "云盘应用 API (测试环境)", "version": "1.0.1-test", "port": 8010}
-
-@app.get("/test")
-async def test():
- return {"status": "ok", "message": "测试服务器运行正常", "port": 8010}
-
-if __name__ == "__main__":
- # 设置测试端口
- test_port = 8010
-
- # 临时设置环境变量覆盖配置
- os.environ["PORT"] = str(test_port)
-
- uvicorn.run(
- "test-main:app",
- host="0.0.0.0",
- port=test_port,
- reload=False # 测试环境不使用热重载
- )
\ No newline at end of file
diff --git a/backend/test_api_8080.py b/backend/test_api_8080.py
deleted file mode 100644
index a4c667c..0000000
--- a/backend/test_api_8080.py
+++ /dev/null
@@ -1,231 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-API测试脚本 - 测试端口8080上的所有端点
-"""
-
-import requests
-import json
-import time
-from typing import Dict, List
-
-class CloudDriveAPITester:
- def __init__(self, base_url: str = "http://localhost:8080"):
- self.base_url = base_url
- self.session = requests.Session()
- self.session.headers.update({
- 'Content-Type': 'application/json',
- 'Accept': 'application/json'
- })
-
- def test_endpoint(self, method: str, endpoint: str, data: Dict = None, description: str = "") -> Dict:
- """测试单个端点"""
- url = f"{self.base_url}{endpoint}"
-
- try:
- print(f"📍 {description or f'{method.upper()} {endpoint}'}")
-
- if method.upper() == 'GET':
- response = self.session.get(url, timeout=10)
- elif method.upper() == 'POST':
- response = self.session.post(url, json=data, timeout=10)
- elif method.upper() == 'PUT':
- response = self.session.put(url, json=data, timeout=10)
- elif method.upper() == 'DELETE':
- response = self.session.delete(url, timeout=10)
- else:
- return {"status": "error", "message": f"不支持的HTTP方法: {method}"}
-
- if response.status_code == 200:
- try:
- data = response.json()
- print(f" ✅ 成功 (200): {json.dumps(data, ensure_ascii=False, indent=2)[:200]}...")
- return {
- "status": "success",
- "code": response.status_code,
- "data": data
- }
- except json.JSONDecodeError:
- print(f" ✅ 成功 (200): {response.text[:200]}...")
- return {
- "status": "success",
- "code": response.status_code,
- "text": response.text
- }
- else:
- print(f" ❌ 失败 ({response.status_code}): {response.text[:200]}...")
- return {
- "status": "failed",
- "code": response.status_code,
- "error": response.text
- }
-
- except requests.exceptions.ConnectionError:
- print(f" ❌ 连接失败 - 无法连接到 {url}")
- return {"status": "connection_failed", "error": "Connection failed"}
- except requests.exceptions.Timeout:
- print(f" ❌ 请求超时")
- return {"status": "timeout", "error": "Request timeout"}
- except Exception as e:
- print(f" ❌ 未知错误: {e}")
- return {"status": "error", "error": str(e)}
-
- def test_basic_endpoints(self) -> Dict:
- """测试基础端点"""
- print("🔍 测试基础端点")
- print("=" * 50)
-
- results = {}
-
- # 测试根路径
- results["root"] = self.test_endpoint("GET", "/", description="根路径")
-
- # 测试健康检查端点
- results["health"] = self.test_endpoint("GET", "/health", description="健康检查")
- results["api_health"] = self.test_endpoint("GET", "/api/v1/health", description="API健康检查")
-
- # 测试文档端点
- results["docs"] = self.test_endpoint("GET", "/docs", description="API文档")
- results["redoc"] = self.test_endpoint("GET", "/redoc", description="ReDoc文档")
- results["openapi"] = self.test_endpoint("GET", "/openapi.json", description="OpenAPI规范")
-
- return results
-
- def test_auth_endpoints(self) -> Dict:
- """测试认证端点"""
- print("\n🔐 测试认证端点")
- print("=" * 50)
-
- results = {}
-
- # 测试注册端点
- test_user = {
- "username": "testuser8080",
- "email": "test8080@example.com",
- "password": "Test123!@#",
- "confirm_password": "Test123!@#"
- }
- results["register"] = self.test_endpoint("POST", "/api/v1/auth/register",
- data=test_user, description="用户注册")
-
- # 测试登录端点
- login_data = {
- "username": "testuser8080",
- "password": "Test123!@#"
- }
- results["login"] = self.test_endpoint("POST", "/api/v1/auth/token",
- data=login_data, description="用户登录")
-
- return results
-
- def test_file_endpoints(self) -> Dict:
- """测试文件端点"""
- print("\n📁 测试文件端点")
- print("=" * 50)
-
- results = {}
-
- # 测试文件列表
- results["list_files"] = self.test_endpoint("GET", "/api/v1/files",
- description="获取文件列表")
-
- # 测试文件上传(模拟)
- results["upload_info"] = self.test_endpoint("GET", "/api/v1/files",
- description="文件上传信息")
-
- return results
-
- def run_all_tests(self) -> Dict:
- """运行所有测试"""
- print("🧪 开始API测试 - 端口8080")
- print("=" * 60)
- print(f"测试目标: {self.base_url}")
- print("=" * 60)
-
- all_results = {}
-
- # 测试基础端点
- basic_results = self.test_basic_endpoints()
- all_results.update(basic_results)
-
- # 测试认证端点
- auth_results = self.test_auth_endpoints()
- all_results.update(auth_results)
-
- # 测试文件端点
- file_results = self.test_file_endpoints()
- all_results.update(file_results)
-
- # 生成测试报告
- self.generate_report(all_results)
-
- return all_results
-
- def generate_report(self, results: Dict):
- """生成测试报告"""
- print("\n📊 测试报告")
- print("=" * 60)
-
- total_tests = len(results)
- success_tests = sum(1 for r in results.values() if r.get("status") == "success")
- failed_tests = total_tests - success_tests
-
- print(f"总测试数: {total_tests}")
- print(f"成功: {success_tests}")
- print(f"失败: {failed_tests}")
- print(f"成功率: {(success_tests/total_tests*100):.1f}%")
-
- if failed_tests == 0:
- print("\n🎉 所有测试通过!API服务运行正常")
- else:
- print(f"\n⚠️ 有 {failed_tests} 个测试失败,请检查服务状态")
-
- print("\n📋 详细结果:")
- for endpoint, result in results.items():
- status = result.get("status", "unknown")
- if status == "success":
- print(f" ✅ {endpoint}")
- elif status == "connection_failed":
- print(f" 🔌 {endpoint} - 连接失败")
- elif status == "timeout":
- print(f" ⏰ {endpoint} - 超时")
- else:
- print(f" ❌ {endpoint} - {status}")
-
-def main():
- """主函数"""
- import argparse
-
- parser = argparse.ArgumentParser(description="云盘API测试工具")
- parser.add_argument("--url", default="http://localhost:8080",
- help="API基础URL (默认: http://localhost:8080)")
- parser.add_argument("--wait", type=int, default=0,
- help="启动前等待时间(秒)")
- parser.add_argument("--basic", action="store_true", help="只测试基础端点")
- parser.add_argument("--auth", action="store_true", help="只测试认证端点")
- parser.add_argument("--files", action="store_true", help="只测试文件端点")
-
- args = parser.parse_args()
-
- if args.wait > 0:
- print(f"⏳ 等待 {args.wait} 秒后开始测试...")
- time.sleep(args.wait)
-
- tester = CloudDriveAPITester(args.url)
-
- try:
- if args.basic:
- tester.test_basic_endpoints()
- elif args.auth:
- tester.test_auth_endpoints()
- elif args.files:
- tester.test_file_endpoints()
- else:
- tester.run_all_tests()
- except KeyboardInterrupt:
- print("\n🛑 测试已中断")
- except Exception as e:
- print(f"\n❌ 测试过程中出现错误: {e}")
-
-if __name__ == "__main__":
- main()
\ No newline at end of file
diff --git a/backend/test_api_exception.py b/backend/test_api_exception.py
deleted file mode 100644
index 24762f9..0000000
--- a/backend/test_api_exception.py
+++ /dev/null
@@ -1,50 +0,0 @@
-import sys
-import traceback
-from fastapi import FastAPI
-from fastapi.testclient import TestClient
-from app.core.database import get_db
-from app.services.user_service import UserService
-from app.schemas.auth import UserRegister
-
-def test_api_exception():
- """测试API异常处理"""
- try:
- print("=== 测试API异常处理 ===")
-
- # 导入应用
- import sys
- import os
- sys.path.append(os.path.dirname(os.path.abspath(__file__)))
- from main import app
-
- # 创建测试客户端
- client = TestClient(app)
-
- # 测试重复邮箱注册
- print("1. 测试重复邮箱注册...")
- response = client.post("/api/v1/auth/register", json={
- "username": "test_api",
- "email": "user@example.com", # 重复邮箱
- "password": "TestPass123!",
- "confirm_password": "TestPass123!"
- })
-
- print(f" HTTP状态码: {response.status_code}")
- print(f" 响应内容: {response.json()}")
-
- if response.status_code == 400:
- print(" ✓ 正确返回400错误")
- detail = response.json().get("detail", {})
- if detail.get("code") == "EMAIL_EXISTS":
- print(" ✓ 正确返回EMAIL_EXISTS错误码")
- else:
- print(f" ✗ 错误码不正确: {detail.get('code')}")
- else:
- print(f" ✗ 状态码不正确,期望400,实际{response.status_code}")
-
- except Exception as e:
- print(f"测试过程出错: {e}")
- traceback.print_exc()
-
-if __name__ == "__main__":
- test_api_exception()
\ No newline at end of file
diff --git a/backend/test_apis.py b/backend/test_apis.py
deleted file mode 100644
index da26ec5..0000000
--- a/backend/test_apis.py
+++ /dev/null
@@ -1,72 +0,0 @@
-#!/usr/bin/env python3
-import requests
-import json
-import time
-
-def test_api():
- base_url = "http://localhost:8080"
-
- print("Testing API endpoints...")
- print("=" * 40)
-
- # Test endpoints
- endpoints = [
- ("/", "Root endpoint"),
- ("/health", "Health check"),
- ("/api/v1/health", "API health"),
- ("/test", "Test endpoint"),
- ("/info", "Info endpoint")
- ]
-
- results = {}
-
- for endpoint, description in endpoints:
- try:
- print(f"Testing {description}: {endpoint}")
- response = requests.get(f"{base_url}{endpoint}", timeout=5)
-
- if response.status_code == 200:
- data = response.json()
- print(f" SUCCESS: {data}")
- results[endpoint] = {"status": "success", "data": data}
- else:
- print(f" FAILED: Status code {response.status_code}")
- results[endpoint] = {"status": "failed", "code": response.status_code}
-
- except requests.exceptions.ConnectionError:
- print(f" FAILED: Connection error")
- results[endpoint] = {"status": "connection_error"}
- except requests.exceptions.Timeout:
- print(f" FAILED: Timeout")
- results[endpoint] = {"status": "timeout"}
- except Exception as e:
- print(f" FAILED: {e}")
- results[endpoint] = {"status": "error", "error": str(e)}
-
- # Summary
- print("\n" + "=" * 40)
- print("Test Summary:")
-
- success_count = sum(1 for r in results.values() if r.get("status") == "success")
- total_count = len(results)
-
- print(f"Total tests: {total_count}")
- print(f"Successful: {success_count}")
- print(f"Failed: {total_count - success_count}")
- print(f"Success rate: {(success_count/total_count*100):.1f}%")
-
- if success_count == total_count:
- print("\n🎉 All API tests passed!")
- print("✅ Server is running correctly on port 8080")
- print("✅ You can access:")
- print(" - http://localhost:8080/docs (Swagger UI)")
- print(" - http://localhost:8080/redoc (ReDoc)")
- else:
- print(f"\n⚠️ {total_count - success_count} tests failed")
-
- return results
-
-if __name__ == "__main__":
- # Wait a bit for server to fully start
- time.sleep(2)
- test_api()
\ No newline at end of file
diff --git a/backend/test_basic_server.py b/backend/test_basic_server.py
deleted file mode 100644
index 598cef6..0000000
--- a/backend/test_basic_server.py
+++ /dev/null
@@ -1,78 +0,0 @@
-#!/usr/bin/env python3
-# 最基础的FastAPI测试服务器
-
-import sys
-import os
-
-print("🔍 检查Python环境...")
-print(f"Python版本: {sys.version}")
-print(f"当前目录: {os.getcwd()}")
-
-# 测试导入
-try:
- import fastapi
- print(f"✅ FastAPI可用: {fastapi.__version__}")
-except ImportError as e:
- print(f"❌ FastAPI不可用: {e}")
- print("正在安装FastAPI...")
- import subprocess
- subprocess.run([sys.executable, "-m", "pip", "install", "fastapi", "uvicorn"])
- import fastapi
- print(f"✅ FastAPI安装成功: {fastapi.__version__}")
-
-try:
- import uvicorn
- print(f"✅ Uvicorn可用: {uvicorn.__version__}")
-except ImportError as e:
- print(f"❌ Uvicorn不可用: {e}")
- print("正在安装Uvicorn...")
- import subprocess
- subprocess.run([sys.executable, "-m", "pip", "install", "uvicorn"])
- import uvicorn
- print(f"✅ Uvicorn安装成功: {uvicorn.__version__}")
-
-# 创建最简单的FastAPI应用
-from fastapi import FastAPI
-from fastapi.middleware.cors import CORSMiddleware
-
-app = FastAPI(
- title="云盘应用测试",
- description="测试服务器",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
-)
-
-app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
-)
-
-@app.get("/")
-async def root():
- return {"message": "服务器运行正常", "port": 8080, "status": "ok"}
-
-@app.get("/test")
-async def test():
- return {"test": "ok", "server": "working"}
-
-@app.get("/api/v1/health")
-async def health():
- import time
- return {"status": "healthy", "timestamp": time.time(), "server": "port 8080"}
-
-if __name__ == "__main__":
- print("🚀 启动测试服务器...")
- print("=" * 40)
- print("📍 本地访问: http://localhost:8080")
- print("📚 API文档: http://localhost:8080/docs")
- print("=" * 40)
- print("按 Ctrl+C 停止服务")
-
- try:
- uvicorn.run(app, host="0.0.0.0", port=8080, log_level="info")
- except Exception as e:
- print(f"❌ 启动失败: {e}")
\ No newline at end of file
diff --git a/backend/test_blacklist.py b/backend/test_blacklist.py
deleted file mode 100644
index 3439f54..0000000
--- a/backend/test_blacklist.py
+++ /dev/null
@@ -1,52 +0,0 @@
-import sys
-from app.core.token_blacklist import token_blacklist
-from app.core.security import verify_token
-
-def test_blacklist():
- """测试令牌黑名单功能"""
- try:
- print("=== 测试令牌黑名单功能 ===")
-
- # 使用之前获取的令牌
- token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiI3IiwidXNlcm5hbWUiOiJ0ZXN0bWUiLCJlbWFpbCI6InRlc3RtZUBleGFtcGxlLmNvbSIsImV4cCI6MTc2MDE3MjI5OCwidHlwZSI6ImFjY2VzcyJ9.Fp9cZ4rDelm6mpxc0cYqXJJ4ne-xG90QuAx1UNfJBIY"
-
- # 1. 检查令牌是否在黑名单中
- print("1. 检查令牌是否在黑名单中...")
- is_blacklisted = token_blacklist.is_blacklisted(token)
- print(f" 令牌在黑名单中: {is_blacklisted}")
-
- # 2. 验证令牌
- print("2. 验证令牌...")
- payload = verify_token(token, "access")
- if payload:
- print(f" 令牌验证成功,用户ID: {payload.get('sub')}")
- else:
- print(" 令牌验证失败")
-
- # 3. 手动将令牌加入黑名单
- print("3. 将令牌加入黑名单...")
- token_blacklist.add_token(token)
- print(" 令牌已加入黑名单")
-
- # 4. 再次检查
- print("4. 再次检查令牌是否在黑名单中...")
- is_blacklisted = token_blacklist.is_blacklisted(token)
- print(f" 令牌在黑名单中: {is_blacklisted}")
-
- # 5. 再次验证令牌
- print("5. 再次验证令牌...")
- payload = verify_token(token, "access")
- if payload:
- print(f" 令牌验证成功,用户ID: {payload.get('sub')}")
- else:
- print(" 令牌验证失败(预期结果)")
-
- print("\n=== 黑名单功能测试完成 ===")
-
- except Exception as e:
- print(f"测试过程出错: {e}")
- import traceback
- traceback.print_exc()
-
-if __name__ == "__main__":
- test_blacklist()
\ No newline at end of file
diff --git a/backend/test_db_connection.py b/backend/test_db_connection.py
deleted file mode 100644
index 44c12b0..0000000
--- a/backend/test_db_connection.py
+++ /dev/null
@@ -1,57 +0,0 @@
-import pymysql
-from app.core.config import settings
-
-def test_mysql_connection():
- try:
- print(f"正在连接数据库: {settings.DATABASE_URL}")
-
- # 解析连接字符串
- import re
- pattern = r'mysql\+pymysql://([^:]+):([^@]+)@([^:]+):(\d+)/(.+)'
- match = re.match(pattern, settings.DATABASE_URL)
-
- if match:
- username, password, host, port, database = match.groups()
- print(f"主机: {host}")
- print(f"端口: {port}")
- print(f"用户: {username}")
- print(f"数据库: {database}")
-
- # 尝试连接
- connection = pymysql.connect(
- host=host,
- port=int(port),
- user=username,
- password=password,
- database=database,
- charset='utf8mb4'
- )
-
- print("MySQL数据库连接成功!")
-
- # 测试查询
- with connection.cursor() as cursor:
- cursor.execute("SELECT VERSION()")
- version = cursor.fetchone()
- print(f"MySQL版本: {version[0]}")
-
- cursor.execute("SHOW TABLES")
- tables = cursor.fetchall()
- print(f"现有表数量: {len(tables)}")
- for table in tables:
- print(f"- {table[0]}")
-
- connection.close()
- return True
-
- else:
- print("连接字符串格式错误")
- return False
-
- except Exception as e:
- print(f"数据库连接失败: {str(e)}")
- print(f"错误类型: {type(e).__name__}")
- return False
-
-if __name__ == "__main__":
- test_mysql_connection()
\ No newline at end of file
diff --git a/backend/test_direct_write.py b/backend/test_direct_write.py
deleted file mode 100644
index 4cfbf0b..0000000
--- a/backend/test_direct_write.py
+++ /dev/null
@@ -1,90 +0,0 @@
-#!/usr/bin/env python3
-"""
-直接测试文件写入,绕过所有业务逻辑
-"""
-
-import os
-
-def test_direct_write():
- """直接测试文件写入"""
-
- print("=== 直接文件写入测试 ===")
-
- # 测试内容
- test_content = b"Direct write test content - bypassing all logic"
-
- # 文件路径
- file_path = "uploads/direct_test_write.txt"
-
- print(f"测试内容大小: {len(test_content)} bytes")
- print(f"目标路径: {os.path.abspath(file_path)}")
-
- # 确保目录存在
- os.makedirs("uploads", exist_ok=True)
-
- # 方法1: 使用 open 直接写入
- print("\n--- 方法1: 直接 open 写入 ---")
- try:
- with open(file_path, "wb") as f:
- written = f.write(test_content)
- f.flush()
- os.fsync(f.fileno())
- print(f"写入字节数: {written}")
-
- if os.path.exists(file_path):
- size = os.path.getsize(file_path)
- print(f"文件大小: {size} bytes")
-
- if size == len(test_content):
- print("✅ 方法1成功!")
- else:
- print(f"❌ 方法1失败: 大小不匹配 {size} != {len(test_content)}")
- else:
- print("❌ 方法1失败: 文件不存在")
-
- except Exception as e:
- print(f"❌ 方法1异常: {e}")
-
- # 方法2: 使用 Path 写入
- print("\n--- 方法2: 使用 pathlib.Path 写入 ---")
- from pathlib import Path
- file_path2 = "uploads/path_test_write.txt"
-
- try:
- Path(file_path2).write_bytes(test_content)
-
- if os.path.exists(file_path2):
- size = os.path.getsize(file_path2)
- print(f"文件大小: {size} bytes")
-
- if size == len(test_content):
- print("✅ 方法2成功!")
- else:
- print(f"❌ 方法2失败: 大小不匹配 {size} != {len(test_content)}")
- else:
- print("❌ 方法2失败: 文件不存在")
-
- except Exception as e:
- print(f"❌ 方法2异常: {e}")
-
- # 方法3: 检查现有文件
- print("\n--- 方法3: 检查现有损坏的文件 ---")
- existing_files = [f for f in os.listdir("uploads") if f.endswith('.txt')]
- print(f"现有文本文件: {existing_files}")
-
- for filename in existing_files[:3]: # 只检查前3个
- file_path = os.path.join("uploads", filename)
- try:
- size = os.path.getsize(file_path)
- print(f"{filename}: {size} bytes")
-
- if size > 0:
- with open(file_path, 'rb') as f:
- content = f.read(min(100, size))
- print(f" 内容预览: {content}")
-
- except Exception as e:
- print(f" 读取错误: {e}")
-
-if __name__ == "__main__":
- test_direct_write()
\ No newline at end of file
diff --git a/backend/test_file_upload.py b/backend/test_file_upload.py
deleted file mode 100644
index 114dac5..0000000
--- a/backend/test_file_upload.py
+++ /dev/null
@@ -1,214 +0,0 @@
-#!/usr/bin/env python3
-"""
-测试文件上传功能的脚本
-"""
-
-import requests
-import json
-from pathlib import Path
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-def test_file_upload():
- """测试文件上传功能"""
-
- # 1. 先注册或登录用户获取token
- print("1. 测试用户登录...")
- login_data = {
- "username": "testuser",
- "password": "testpass123"
- }
-
- try:
- # 尝试登录
- response = requests.post(f"{BASE_URL}/auth/login", json=login_data)
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- token = result["data"]["tokens"]["access_token"]
- print("[OK] 登录成功")
- else:
- print("[ERROR] 登录失败,尝试注册...")
- # 如果登录失败,先注册
- register_data = {
- "username": "testuser",
- "email": "test@example.com",
- "password": "testpass123"
- }
- register_response = requests.post(f"{BASE_URL}/auth/register", json=register_data)
- if register_response.status_code == 201:
- register_result = register_response.json()
- if register_result.get("success"):
- token = register_result["data"]["tokens"]["access_token"]
- print("✓ 注册成功")
- else:
- print(f"✗ 注册失败: {register_result}")
- return
- else:
- print(f"✗ 注册请求失败: {register_response.status_code}")
- return
-
- # 注册后再次登录
- login_response = requests.post(f"{BASE_URL}/auth/login", json=login_data)
- if login_response.status_code == 200:
- login_result = login_response.json()
- if login_result.get("success"):
- token = login_result["data"]["tokens"]["access_token"]
- print("✓ 登录成功")
- else:
- print(f"登录请求失败: {response.status_code}")
- return
-
- except Exception as e:
- print(f"认证过程出错: {e}")
- return
-
- # 设置认证头
- headers = {
- "Authorization": f"Bearer {token}"
- }
-
- # 2. 创建测试文件
- print("\n2. 创建测试文件...")
- test_file_path = "test_file.txt"
- test_content = "这是一个测试文件内容\nHello, World!\n测试文件上传功能"
-
- try:
- with open(test_file_path, "w", encoding="utf-8") as f:
- f.write(test_content)
- print(f"✓ 创建测试文件: {test_file_path}")
- except Exception as e:
- print(f"✗ 创建测试文件失败: {e}")
- return
-
- # 3. 测试文件上传
- print("\n3. 测试文件上传...")
- try:
- with open(test_file_path, "rb") as f:
- files = {
- "file": (test_file_path, f, "text/plain")
- }
- data = {
- "description": "测试文件描述",
- "tags": "测试,文件,上传",
- "is_public": "false"
- }
-
- upload_response = requests.post(
- f"{BASE_URL}/files/upload",
- headers=headers,
- files=files,
- data=data
- )
-
- if upload_response.status_code == 201:
- upload_result = upload_response.json()
- if upload_result.get("success"):
- file_info = upload_result["data"]["file"]
- print(f"✓ 文件上传成功!")
- print(f" 文件ID: {file_info['id']}")
- print(f" 文件名: {file_info['original_filename']}")
- print(f" 文件大小: {file_info['file_size']} 字节")
-
- # 保存文件ID用于后续测试
- file_id = file_info["id"]
- else:
- print(f"✗ 文件上传失败: {upload_result}")
- return
- else:
- print(f"✗ 文件上传请求失败: {upload_response.status_code}")
- print(f"响应内容: {upload_response.text}")
- return
-
- except Exception as e:
- print(f"✗ 文件上传过程出错: {e}")
- return
-
- # 4. 测试获取文件列表
- print("\n4. 测试获取文件列表...")
- try:
- list_response = requests.get(
- f"{BASE_URL}/files/list",
- headers=headers
- )
-
- if list_response.status_code == 200:
- list_result = list_response.json()
- if list_result.get("success"):
- files_list = list_result["data"]["files"]
- pagination = list_result["data"]["pagination"]
- print(f"✓ 获取文件列表成功!")
- print(f" 文件数量: {len(files_list)}")
- print(f" 总数: {pagination['total']}")
- for file_item in files_list:
- print(f" - {file_item['original_filename']} ({file_item['file_size']} 字节)")
- else:
- print(f"✗ 获取文件列表失败: {list_result}")
- else:
- print(f"✗ 获取文件列表请求失败: {list_response.status_code}")
-
- except Exception as e:
- print(f"✗ 获取文件列表过程出错: {e}")
-
- # 5. 测试获取存储信息
- print("\n5. 测试获取存储信息...")
- try:
- storage_response = requests.get(
- f"{BASE_URL}/files/storage/info",
- headers=headers
- )
-
- if storage_response.status_code == 200:
- storage_result = storage_response.json()
- if storage_result.get("success"):
- storage_info = storage_result["data"]
- print(f"✓ 获取存储信息成功!")
- print(f" 总配额: {storage_info['total_quota']} 字节")
- print(f" 已使用: {storage_info['used_space']} 字节")
- print(f" 可用空间: {storage_info['available_space']} 字节")
- print(f" 使用百分比: {storage_info['usage_percentage']:.2f}%")
- print(f" 文件数量: {storage_info['file_count']}")
- else:
- print(f"✗ 获取存储信息失败: {storage_result}")
- else:
- print(f"✗ 获取存储信息请求失败: {storage_response.status_code}")
-
- except Exception as e:
- print(f"✗ 获取存储信息过程出错: {e}")
-
- # 6. 测试文件下载
- print("\n6. 测试文件下载...")
- try:
- download_response = requests.get(
- f"{BASE_URL}/files/{file_id}/download",
- headers=headers
- )
-
- if download_response.status_code == 200:
- print(f"✓ 文件下载成功!")
- print(f" 下载内容长度: {len(download_response.content)} 字节")
- # 保存下载的文件
- downloaded_file_path = "downloaded_test_file.txt"
- with open(downloaded_file_path, "wb") as f:
- f.write(download_response.content)
- print(f" 已保存为: {downloaded_file_path}")
- else:
- print(f"✗ 文件下载请求失败: {download_response.status_code}")
-
- except Exception as e:
- print(f"✗ 文件下载过程出错: {e}")
-
- # 7. 清理测试文件
- print("\n7. 清理测试文件...")
- try:
- Path(test_file_path).unlink(missing_ok=True)
- Path("downloaded_test_file.txt").unlink(missing_ok=True)
- print("✓ 清理完成")
- except Exception as e:
- print(f"✗ 清理过程出错: {e}")
-
- print("\n🎉 文件存储功能测试完成!")
-
-if __name__ == "__main__":
- test_file_upload()
\ No newline at end of file
diff --git a/backend/test_files_simple.py b/backend/test_files_simple.py
deleted file mode 100644
index b898cc0..0000000
--- a/backend/test_files_simple.py
+++ /dev/null
@@ -1,194 +0,0 @@
-#!/usr/bin/env python3
-"""
-简化版文件API测试脚本
-"""
-
-import requests
-import json
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-# 固定用户ID
-USER_ID = 8
-
-def test_file_upload():
- """测试文件上传"""
- test_content = "Hello World! 这是测试文件内容。"
-
- try:
- files = {
- "file": ("test.txt", test_content.encode("utf-8"), "text/plain")
- }
- data = {
- "user_id": USER_ID,
- "description": "测试文件上传",
- "tags": "test,upload",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- files=files,
- data=data
- )
-
- print(f"上传状态码: {response.status_code}")
- print(f"上传响应: {response.text}")
-
- if response.status_code == 201:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- print(f"上传成功! 文件ID: {file_info['id']}")
- return file_info['id']
-
- return None
- except Exception as e:
- print(f"上传出错: {e}")
- return None
-
-def test_file_list():
- """测试获取文件列表"""
- try:
- data = {
- "user_id": USER_ID,
- "page": 1,
- "size": 20
- }
-
- response = requests.post(
- f"{BASE_URL}/files/list",
- json=data
- )
-
- print(f"列表状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- files = result["data"]["files"]
- print(f"文件数量: {len(files)}")
- for f in files:
- print(f" - {f['original_filename']} (ID: {f['id']}, 大小: {f['file_size']} bytes)")
- return files
-
- except Exception as e:
- print(f"获取列表出错: {e}")
- return []
-
-def test_storage_info():
- """测试存储信息"""
- try:
- data = {
- "user_id": USER_ID
- }
-
- response = requests.post(
- f"{BASE_URL}/files/storage/info",
- json=data
- )
-
- print(f"存储信息状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- info = result["data"]
- print(f"存储信息:")
- print(f" 总配额: {info['total_quota']} bytes")
- print(f" 已使用: {info['used_space']} bytes")
- print(f" 可用空间: {info['available_space']} bytes")
- print(f" 使用百分比: {info['usage_percentage']:.2f}%")
- print(f" 文件数量: {info['file_count']}")
-
- except Exception as e:
- print(f"获取存储信息出错: {e}")
-
-def test_file_info(file_id):
- """测试获取文件信息"""
- try:
- data = {
- "user_id": USER_ID,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/info",
- json=data
- )
-
- print(f"文件信息状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- info = result["data"]
- print(f"文件信息:")
- print(f" 文件名: {info['original_filename']}")
- print(f" 大小: {info['file_size']} bytes")
- print(f" MIME类型: {info['mime_type']}")
- print(f" 是否图片: {info['is_image']}")
- print(f" 是否文档: {info['is_document']}")
- print(f" 格式化大小: {info['size_formatted']}")
-
- except Exception as e:
- print(f"获取文件信息出错: {e}")
-
-def test_file_delete(file_id):
- """测试删除文件"""
- try:
- data = {
- "user_id": USER_ID,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/delete",
- json=data
- )
-
- print(f"删除状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- print("文件删除成功")
- else:
- print(f"删除失败: {result}")
- else:
- print(f"删除请求失败: {response.text}")
-
- except Exception as e:
- print(f"删除文件出错: {e}")
-
-if __name__ == "__main__":
- print(f"开始测试文件API (用户ID: {USER_ID})...")
-
- # 1. 测试存储信息
- print("\n=== 测试存储信息 ===")
- test_storage_info()
-
- # 2. 上传文件
- print("\n=== 测试文件上传 ===")
- file_id = test_file_upload()
-
- # 3. 获取文件列表
- print("\n=== 测试文件列表 ===")
- files = test_file_list()
-
- # 4. 获取文件信息
- if file_id:
- print("\n=== 测试文件信息 ===")
- test_file_info(file_id)
-
- # 5. 删除文件
- print("\n=== 测试文件删除 ===")
- test_file_delete(file_id)
-
- # 6. 再次检查文件列表和存储信息
- print("\n=== 最终检查 ===")
- test_file_list()
- test_storage_info()
-
- print("\n测试完成!")
\ No newline at end of file
diff --git a/backend/test_loguru.py b/backend/test_loguru.py
deleted file mode 100644
index de24a5f..0000000
--- a/backend/test_loguru.py
+++ /dev/null
@@ -1,31 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-
-from loguru import logger
-import sys
-import os
-
-# 移除默认处理器
-logger.remove()
-
-# 添加控制台输出
-logger.add(
- sys.stdout,
- format="{time:HH:mm:ss} | {level: <8} | {message}",
- level="INFO",
- colorize=True
-)
-
-print("=== Loguru Test ===")
-logger.info("This is an info message")
-logger.success("This is a success message")
-logger.warning("This is a warning message")
-logger.error("This is an error message")
-logger.debug("This debug message won't show (level too high)")
-
-# 测试中文输出
-logger.info("中文测试输出 🚀")
-logger.success("上传文件成功 ✅")
-logger.error("下载文件失败 ❌")
-
-print("Test completed!")
\ No newline at end of file
diff --git a/backend/test_loguru_simple.py b/backend/test_loguru_simple.py
deleted file mode 100644
index b25fb43..0000000
--- a/backend/test_loguru_simple.py
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-
-from loguru import logger
-import sys
-
-# 创建安全流处理器
-class SafeStreamHandler:
- def __init__(self, stream):
- self.stream = stream
-
- def write(self, message):
- try:
- self.stream.write(message)
- except UnicodeEncodeError:
- clean_message = message.encode('utf-8', errors='ignore').decode('utf-8')
- self.stream.write(clean_message)
-
- def flush(self):
- self.stream.flush()
-
-# 配置loguru
-logger.remove()
-logger.add(
- SafeStreamHandler(sys.stdout),
- format="{time:HH:mm:ss} | {level: <8} | {message}",
- level="INFO"
-)
-
-print("=== Loguru Simple Test ===")
-logger.info("Server starting...")
-logger.info("Test upload file")
-logger.success("Upload completed")
-logger.warning("File already exists")
-logger.error("Download failed")
-print("Test completed!")
\ No newline at end of file
diff --git a/backend/test_output.py b/backend/test_output.py
deleted file mode 100644
index 35691ee..0000000
--- a/backend/test_output.py
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-
-import sys
-import os
-
-print("=== 测试输出 ===", flush=True)
-print("Python版本:", sys.version, flush=True)
-print("当前工作目录:", os.getcwd(), flush=True)
-print("stdout编码:", sys.stdout.encoding, flush=True)
-print("stderr编码:", sys.stderr.encoding, flush=True)
-
-import logging
-
-# 配置日志
-logging.basicConfig(
- level=logging.INFO,
- format='%(asctime)s - %(levelname)s - %(message)s',
- handlers=[logging.StreamHandler(sys.stdout)]
-)
-
-logger = logging.getLogger(__name__)
-logger.info("这是一条测试日志")
-logger.warning("这是一条警告日志")
-
-print("测试完成!", flush=True)
-
-# 写入文件测试
-with open("test_log.txt", "w", encoding="utf-8") as f:
- f.write("测试文件写入\n")
- f.write(f"时间: {os.times()}\n")
-
-print("文件写入完成", flush=True)
\ No newline at end of file
diff --git a/backend/test_post_api.py b/backend/test_post_api.py
deleted file mode 100644
index 93f5eea..0000000
--- a/backend/test_post_api.py
+++ /dev/null
@@ -1,308 +0,0 @@
-#!/usr/bin/env python3
-"""
-测试POST文件API的脚本
-"""
-
-import requests
-import json
-
-# API基础URL
-BASE_URL = "http://localhost:8000/api/v1"
-
-def create_test_user():
- """创建测试用户"""
- register_data = {
- "username": "testuser",
- "email": "test@example.com",
- "password": "TestPass123!",
- "confirm_password": "TestPass123!"
- }
-
- try:
- print("创建测试用户...")
- reg_response = requests.post(f"{BASE_URL}/auth/register", json=register_data)
- print(f"注册状态码: {reg_response.status_code}")
-
- if reg_response.status_code == 201:
- reg_result = reg_response.json()
- if reg_result.get("success"):
- user_id = reg_result["data"]["user"]["id"]
- print(f"用户创建成功,ID: {user_id}")
- return user_id
- else:
- print(f"注册失败: {reg_result}")
- else:
- print(f"注册请求失败,状态码: {reg_response.status_code}")
-
- # 如果注册失败,尝试获取现有用户
- print("尝试获取现有用户...")
- login_data = {
- "username": "testuser",
- "password": "TestPass123!"
- }
- login_response = requests.post(f"{BASE_URL}/auth/login", json=login_data)
- if login_response.status_code == 200:
- login_result = login_response.json()
- if login_result.get("success"):
- user_id = login_result["data"]["user"]["id"]
- print(f"登录成功,用户ID: {user_id}")
- return user_id
-
- return None
- except Exception as e:
- print(f"创建用户出错: {e}")
- return None
-
-def test_file_upload(user_id):
- """测试文件上传"""
- test_content = "Hello World! 测试文件上传内容"
-
- try:
- files = {
- "file": ("test.txt", test_content.encode("utf-8"), "text/plain")
- }
- data = {
- "user_id": user_id,
- "description": "测试文件上传",
- "tags": "test,upload,api",
- "is_public": "false"
- }
-
- response = requests.post(
- f"{BASE_URL}/files/upload",
- files=files,
- data=data
- )
-
- print(f"上传状态码: {response.status_code}")
- print(f"上传响应: {response.text}")
-
- if response.status_code == 201:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- print(f"上传成功! 文件ID: {file_info['id']}")
- print(f"文件名: {file_info['original_filename']}")
- print(f"文件大小: {file_info['file_size']} bytes")
- return file_info['id']
-
- return None
- except Exception as e:
- print(f"上传出错: {e}")
- return None
-
-def test_file_list(user_id):
- """测试获取文件列表"""
- try:
- data = {
- "user_id": user_id,
- "page": 1,
- "size": 20
- }
-
- response = requests.post(
- f"{BASE_URL}/files/list",
- json=data
- )
-
- print(f"列表状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- files = result["data"]["files"]
- pagination = result["data"]["pagination"]
- print(f"文件数量: {len(files)}")
- print(f"总数: {pagination['total']}")
- for f in files:
- print(f" - {f['original_filename']} ({f['file_size']} bytes)")
- print(f" ID: {f['id']}, 创建时间: {f['created_at']}")
-
- except Exception as e:
- print(f"获取列表出错: {e}")
-
-def test_file_info(user_id, file_id):
- """测试获取文件信息"""
- try:
- data = {
- "user_id": user_id,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/info",
- json=data
- )
-
- print(f"文件信息状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- info = result["data"]
- print(f"文件信息:")
- print(f" 文件名: {info['original_filename']}")
- print(f" 大小: {info['file_size']} bytes")
- print(f" MIME类型: {info['mime_type']}")
- print(f" 是否图片: {info['is_image']}")
- print(f" 是否文档: {info['is_document']}")
- print(f" 文件扩展名: {info['file_extension']}")
- print(f" 格式化大小: {info['size_formatted']}")
-
- except Exception as e:
- print(f"获取文件信息出错: {e}")
-
-def test_storage_info(user_id):
- """测试存储信息"""
- try:
- data = {
- "user_id": user_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/storage/info",
- json=data
- )
-
- print(f"存储信息状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- info = result["data"]
- print(f"存储信息:")
- print(f" 总配额: {info['total_quota']} bytes")
- print(f" 已使用: {info['used_space']} bytes")
- print(f" 可用空间: {info['available_space']} bytes")
- print(f" 使用百分比: {info['usage_percentage']:.2f}%")
- print(f" 文件数量: {info['file_count']}")
-
- except Exception as e:
- print(f"获取存储信息出错: {e}")
-
-def test_file_update(user_id, file_id):
- """测试更新文件信息"""
- try:
- data = {
- "user_id": user_id,
- "file_id": file_id
- }
-
- update_data = {
- "description": "更新后的文件描述",
- "tags": "updated,test",
- "is_public": True
- }
-
- response = requests.post(
- f"{BASE_URL}/files/update",
- json=data,
- params=update_data
- )
-
- print(f"更新文件状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- file_info = result["data"]["file"]
- print(f"文件更新成功:")
- print(f" 描述: {file_info['description']}")
- print(f" 标签: {file_info['tags']}")
- print(f" 是否公开: {file_info['is_public']}")
-
- except Exception as e:
- print(f"更新文件出错: {e}")
-
-def test_file_download(user_id, file_id):
- """测试文件下载"""
- try:
- data = {
- "user_id": user_id,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/download",
- json=data
- )
-
- print(f"下载状态码: {response.status_code}")
-
- if response.status_code == 200:
- print(f"下载成功! 内容长度: {len(response.content)} bytes")
- print(f"下载内容: {response.text[:100]}...") # 显示前100个字符
- else:
- print(f"下载失败: {response.text}")
-
- except Exception as e:
- print(f"下载出错: {e}")
-
-def test_file_delete(user_id, file_id):
- """测试删除文件"""
- try:
- data = {
- "user_id": user_id,
- "file_id": file_id
- }
-
- response = requests.post(
- f"{BASE_URL}/files/delete",
- json=data
- )
-
- print(f"删除状态码: {response.status_code}")
-
- if response.status_code == 200:
- result = response.json()
- if result.get("success"):
- print("文件删除成功")
- else:
- print(f"删除失败: {result}")
- else:
- print(f"删除请求失败: {response.text}")
-
- except Exception as e:
- print(f"删除文件出错: {e}")
-
-if __name__ == "__main__":
- print("开始测试POST文件API...")
-
- # 1. 创建测试用户
- user_id = create_test_user()
- if not user_id:
- print("无法创建或获取用户,退出测试")
- exit(1)
-
- # 2. 上传文件
- print("\n=== 测试文件上传 ===")
- file_id = test_file_upload(user_id)
- if not file_id:
- print("文件上传失败,继续其他测试")
-
- # 3. 获取文件列表
- print("\n=== 测试文件列表 ===")
- test_file_list(user_id)
-
- # 4. 获取存储信息
- print("\n=== 测试存储信息 ===")
- test_storage_info(user_id)
-
- # 5. 获取文件信息
- if file_id:
- print("\n=== 测试文件信息 ===")
- test_file_info(user_id, file_id)
-
- # 6. 更新文件信息
- print("\n=== 测试文件更新 ===")
- test_file_update(user_id, file_id)
-
- # 7. 下载文件
- print("\n=== 测试文件下载 ===")
- test_file_download(user_id, file_id)
-
- # 8. 删除文件
- print("\n=== 测试文件删除 ===")
- test_file_delete(user_id, file_id)
-
- print("\n测试完成!")
\ No newline at end of file
diff --git a/backend/test_server_8080.sh b/backend/test_server_8080.sh
deleted file mode 100644
index 5a2061d..0000000
--- a/backend/test_server_8080.sh
+++ /dev/null
@@ -1,116 +0,0 @@
-#!/bin/bash
-# 测试服务器API连通性的脚本
-
-echo "=== 测试云盘应用API ==="
-echo "目标地址: http://localhost:8080"
-echo "=================================="
-
-# 检查服务器是否运行
-echo "1. 检查服务器状态..."
-
-# 使用curl测试连接
-if curl -s http://localhost:8080/ > /dev/null; then
- echo "✅ 服务器正在运行"
-else
- echo "❌ 服务器未运行,请先启动服务器:"
- echo "cd /www/wwwroot/云盘后台/backend && python3 server_no_loguru.py"
- exit 1
-fi
-
-echo ""
-echo "2. 测试API端点..."
-
-# 测试根路径
-echo "测试根路径: http://localhost:8080/"
-root_response=$(curl -s http://localhost:8000/ 2>/dev/null)
-if [ $? -eq 0 ]; then
- echo "✅ 根路径响应正常"
-else
- echo "❌ 根路径无响应"
-fi
-
-# 测试健康检查
-echo "测试健康检查: http://localhost:8080/api/v1/health"
-health_response=$(curl -s http://localhost:8080/api/v1/health 2>/dev/null)
-if [ $? -eq 0 ]; then
- echo "✅ API健康检查正常"
- echo "响应内容: $health_response"
-else
- echo "❌ API健康检查无响应"
-fi
-
-# 测试API文档
-echo "测试API文档: http://localhost:8080/docs"
-docs_response=$(curl -s -I http://localhost:8080/docs 2>/dev/null)
-if [ $? -eq 0 ]; then
- echo "✅ API文档可访问"
-else
- echo "❌ API文档无法访问"
-fi
-
-# 测试测试端点
-echo "测试端点: http://localhost:8080/test"
-test_response=$(curl -s http://localhost:8080/test 2>/dev/null)
-if [ $? -eq 0 ]; then
- echo "✅ 测试端点正常"
- echo "响应内容: $test_response"
-else
- echo "❌ 测试端点无响应"
-fi
-
-echo ""
-echo "3. 详细测试..."
-
-# 详细测试多个端点
-endpoints=(
- "http://localhost:8080/"
- "http://localhost:8080/health"
- "http://localhost:8080/api/v1/health"
- "http://localhost:8080/test"
- "http://localhost:8080/openapi.json"
-)
-
-success_count=0
-total_count=${#endpoints[@]}
-
-for endpoint in "${endpoints[@]}"; do
- echo -n "Testing $endpoint ... "
-
- response=$(curl -s "$endpoint" 2>/dev/null)
- http_code=$(curl -s -o /dev/null -w "%{http_code}" "$endpoint" 2>/dev/null)
-
- if [ "$http_code" = "200" ]; then
- echo "✅ (200)"
- success_count=$((success_count + 1))
- else
- echo "❌ ($http_code)"
- fi
-done
-
-echo ""
-echo "=================================="
-echo "测试结果汇总:"
-echo "总测试数: $total_count"
-echo "成功: $success_count"
-echo "失败: $((total_count - success_count))"
-echo "成功率: $((success_count * 100 / total_count))%"
-
-if [ $success_count -eq $total_count ]; then
- echo ""
- echo "🎉 所有API测试通过!"
- echo ""
- echo "📋 可访问的URL:"
- echo " http://localhost:8080/ (根路径)"
- echo " http://localhost:8080/docs (Swagger UI)"
- echo " http://localhost:8080/redoc (ReDoc)"
- echo " http://localhost:8080/api/v1/health (健康检查)"
- echo ""
- echo "✅ 服务器在端口8080上运行正常!"
-else
- echo ""
- echo "⚠️ 有 $((total_count - success_count)) 个测试失败"
- echo "请检查服务器状态和配置"
-fi
-
-echo ""
-echo "=================================="
\ No newline at end of file
diff --git a/backend/test_upload_download_api.py b/backend/test_upload_download_api.py
deleted file mode 100644
index 00d6493..0000000
--- a/backend/test_upload_download_api.py
+++ /dev/null
@@ -1,114 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-"""
-接口级上传下载测试
-"""
-
-import requests
-import json
-import sys
-import io
-
-# 设置stdout编码为utf-8
-sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding='utf-8')
-
-BASE_URL = "http://localhost:8000/api/v1"
-
-def test_upload_download():
- print("=== 测试文件上传下载 ===")
-
- # 1. 先创建测试用户
- print("1. 创建测试用户...")
- register_data = {
- "username": "testuser456",
- "email": "test456@example.com",
- "password": "Test123456!",
- "confirm_password": "Test123456!"
- }
-
- try:
- response = requests.post(f"{BASE_URL}/auth/register", json=register_data)
- print(f"注册响应状态: {response.status_code}")
- print(f"注册响应内容: {response.text}")
-
- if response.status_code == 201:
- user_id = response.json()["data"]["user"]["id"]
- print(f"[OK] 用户创建成功,ID: {user_id}")
- else:
- # 创建另一个用户
- register_data = {
- "username": f"testuser{hash('test') % 10000}",
- "email": f"test{hash('test') % 10000}@example.com",
- "password": "Test123456!",
- "confirm_password": "Test123456!"
- }
- response = requests.post(f"{BASE_URL}/auth/register", json=register_data)
- if response.status_code == 201:
- user_id = response.json()["data"]["user"]["id"]
- print(f"[OK] 新用户创建成功,ID: {user_id}")
- else:
- print(f"[ERROR] 用户创建失败")
- return
- except Exception as e:
- print(f"[ERROR] 请求异常: {e}")
- return
-
- # 2. 上传文件
- print("\n2. 上传测试文件...")
- test_content = "这是测试文件内容\nTest file content\n你好世界!"
-
- files = {'file': ('test.txt', test_content, 'text/plain')}
- data = {
- 'user_id': str(user_id),
- 'description': '测试文件',
- 'tags': 'test',
- 'is_public': 'false'
- }
-
- try:
- upload_resp = requests.post(f"{BASE_URL}/files/upload", files=files, data=data)
- print(f"上传状态码: {upload_resp.status_code}")
- print(f"上传响应: {upload_resp.text}")
-
- if upload_resp.status_code == 201:
- file_id = upload_resp.json()["data"]["file"]["id"]
- print(f"[OK] 上传成功,文件ID: {file_id}")
- else:
- print("[ERROR] 上传失败")
- return
- except Exception as e:
- print(f"[ERROR] 上传异常: {e}")
- return
-
- # 3. 下载文件
- print(f"\n3. 下载文件 ID: {file_id}...")
- download_data = {
- "file_id": file_id,
- "user_id": user_id
- }
-
- try:
- download_resp = requests.post(f"{BASE_URL}/files/download", json=download_data)
- print(f"下载状态码: {download_resp.status_code}")
- print(f"下载响应头: {dict(download_resp.headers)}")
-
- if download_resp.status_code == 200:
- downloaded_content = download_resp.text
- print(f"[OK] 下载成功")
- print(f"下载内容: {downloaded_content}")
- print(f"内容长度: {len(downloaded_content)}")
-
- # 验证内容
- if test_content == downloaded_content:
- print("[OK] 内容一致")
- else:
- print("[ERROR] 内容不一致")
- print(f"原始: {repr(test_content)}")
- print(f"下载: {repr(downloaded_content)}")
- else:
- print(f"[ERROR] 下载失败: {download_resp.text}")
- except Exception as e:
- print(f"[ERROR] 下载异常: {e}")
-
-if __name__ == "__main__":
- test_upload_download()
\ No newline at end of file
diff --git a/backend/uninstall.sh b/backend/uninstall.sh
deleted file mode 100644
index 515da38..0000000
--- a/backend/uninstall.sh
+++ /dev/null
@@ -1,85 +0,0 @@
-#!/bin/bash
-# 云盘后端服务卸载脚本
-
-set -e
-
-# 配置变量
-SERVICE_NAME="cloud-drive"
-SERVICE_USER="cloud-drive"
-INSTALL_DIR="/opt/cloud-drive"
-
-echo "=== 云盘后端服务卸载脚本 ==="
-
-# 检查是否为root用户
-if [ "$EUID" -ne 0 ]; then
- echo "错误: 请使用root权限运行此脚本"
- exit 1
-fi
-
-# 停止并禁用服务
-echo "停止服务..."
-if systemctl is-active --quiet "$SERVICE_NAME"; then
- systemctl stop "$SERVICE_NAME"
- echo "✓ 服务已停止"
-fi
-
-echo "禁用服务..."
-if systemctl is-enabled --quiet "$SERVICE_NAME"; then
- systemctl disable "$SERVICE_NAME"
- echo "✓ 服务已禁用"
-fi
-
-# 删除systemd服务文件
-echo "删除systemd服务..."
-if [ -f "/etc/systemd/system/$SERVICE_NAME.service" ]; then
- rm -f "/etc/systemd/system/$SERVICE_NAME.service"
- systemctl daemon-reload
- echo "✓ systemd服务文件已删除"
-fi
-
-# 删除防火墙规则
-echo "删除防火墙规则..."
-if command -v firewall-cmd &> /dev/null; then
- firewall-cmd --permanent --remove-port=8000/tcp 2>/dev/null || true
- firewall-cmd --reload 2>/dev/null || true
- echo "✓ 防火墙规则已删除 (firewalld)"
-elif command -v ufw &> /dev/null; then
- ufw delete allow 8000/tcp 2>/dev/null || true
- echo "✓ 防火墙规则已删除 (ufw)"
-fi
-
-# 删除日志轮转配置
-echo "删除日志轮转配置..."
-if [ -f "/etc/logrotate.d/cloud-drive" ]; then
- rm -f "/etc/logrotate.d/cloud-drive"
- echo "✓ 日志轮转配置已删除"
-fi
-
-# 询问是否删除数据
-echo ""
-read -p "是否删除所有数据和配置文件?(y/N): " -n 1 -r
-echo
-if [[ $REPLY =~ ^[Yy]$ ]]; then
- # 删除安装目录
- echo "删除安装目录..."
- if [ -d "$INSTALL_DIR" ]; then
- rm -rf "$INSTALL_DIR"
- echo "✓ 安装目录已删除"
- fi
-
- # 删除服务用户
- echo "删除服务用户..."
- if id "$SERVICE_USER" &>/dev/null; then
- userdel "$SERVICE_USER" 2>/dev/null || true
- echo "✓ 服务用户已删除"
- fi
-
- echo "✓ 所有数据已删除"
-else
- echo "保留数据目录: $INSTALL_DIR"
- echo "如需手动删除,请运行: rm -rf $INSTALL_DIR"
-fi
-
-echo ""
-echo "=== 卸载完成 ==="
-echo "云盘后端服务已从系统中完全移除"
\ No newline at end of file
diff --git a/backend/working_server.py b/backend/working_server.py
deleted file mode 100644
index cc731f5..0000000
--- a/backend/working_server.py
+++ /dev/null
@@ -1,102 +0,0 @@
-#!/usr/bin/env python3
-print("🚀 启动云盘应用服务器...")
-
-# 检查Python环境
-import sys
-print(f"Python版本: {sys.version}")
-
-# 尝试导入FastAPI
-try:
- from fastapi import FastAPI
- from fastapi.middleware.cors import CORSMiddleware
- import uvicorn
- print("✅ FastAPI依赖可用")
-
- # 创建FastAPI应用
- app = FastAPI(
- title="云盘应用 API",
- description="现代化的云存储Web应用后端API",
- version="1.0.0",
- docs_url="/docs",
- redoc_url="/redoc"
- )
-
- # 添加CORS中间件
- app.add_middleware(
- CORSMiddleware,
- allow_origins=["*"],
- allow_credentials=True,
- allow_methods=["*"],
- allow_headers=["*"],
- )
-
- # 定义路由
- @app.get("/")
- async def root():
- return {
- "message": "云盘应用 API",
- "version": "1.0.1",
- "docs": "/docs",
- "health": "/api/v1/health"
- }
-
- @app.get("/health")
- async def health():
- return {"status": "healthy"}
-
- @app.get("/api/v1/health")
- async def api_health():
- import time
- return {
- "status": "healthy",
- "timestamp": time.time(),
- "version": "1.0.0"
- }
-
- @app.get("/test")
- async def test():
- return {"test": "ok", "server": "working"}
-
- # 尝试导入app模块以提供完整功能
- try:
- from app.core.config import settings
- print("✅ 完整app模块可用")
- mode = "full"
- except ImportError:
- print("⚠️ 使用简化模式")
- mode = "simplified"
-
- @app.get("/info")
- async def info():
- return {
- "mode": mode,
- "python_version": str(sys.version),
- "status": "running"
- }
-
- print("=" * 50)
- print("📍 服务器地址:")
- print(" http://localhost:8080")
- print(" http://localhost:8080/docs")
- print(" http://localhost:8080/api/v1/health")
- print("=" * 50)
- print("按 Ctrl+C 停止服务")
- print()
-
- # 启动服务器
- uvicorn.run(
- app,
- host="0.0.0.0",
- port=8080,
- reload=False,
- access_log=True,
- log_level="info"
- )
-
-except ImportError as e:
- print(f"❌ 依赖导入失败: {e}")
- print("请运行: pip install fastapi uvicorn")
- sys.exit(1)
-except Exception as e:
- print(f"❌ 启动失败: {e}")
- sys.exit(1)
\ No newline at end of file
diff --git a/final_test.txt b/final_test.txt
deleted file mode 100644
index 77a64d9..0000000
--- a/final_test.txt
+++ /dev/null
@@ -1,3 +0,0 @@
-这是最终测试文件,用于验证文件上传修复完全成功。
-时间戳:2025-10-13 15:03
-内容:唯一内容,确保不会触发去重机制。
\ No newline at end of file
diff --git a/frontend-test-new.txt b/frontend-test-new.txt
deleted file mode 100644
index 49d8899..0000000
--- a/frontend-test-new.txt
+++ /dev/null
@@ -1,6 +0,0 @@
-新的测试文件 - 前后端联调测试
-创建时间: 2025-10-13
-内容包括中文字符和数字:12345
-This is a test file for frontend-backend integration testing.
-特殊符号测试:!@#$%^&*()
-测试内容完整性验证。
\ No newline at end of file
diff --git a/frontend-test.txt b/frontend-test.txt
deleted file mode 100644
index af221ef..0000000
--- a/frontend-test.txt
+++ /dev/null
@@ -1,10 +0,0 @@
-这是一个测试文件,用于验证前后端文件上传功能。
-
-内容包括:
-- 中文字符测试
-- English characters test
-- 数字: 123456
-- 特殊符号: !@#$%^&*()
-
-创建时间: 2025-10-13
-测试目的: 验证云盘上传下载功能是否正常工作
\ No newline at end of file
diff --git a/new_test_0.txt b/new_test_0.txt
deleted file mode 100644
index c128c1f..0000000
--- a/new_test_0.txt
+++ /dev/null
@@ -1 +0,0 @@
-Completely new file content at
diff --git a/success_test.txt b/success_test.txt
deleted file mode 100644
index a281f4b..0000000
--- a/success_test.txt
+++ /dev/null
@@ -1,4 +0,0 @@
-最终成功测试文件!
-时间:2025-10-13 15:05:30
-内容:这是用来验证文件上传修复成功的测试文件。
-状态:应该能成功上传!
\ No newline at end of file
diff --git a/test_upload.txt b/test_upload.txt
deleted file mode 100644
index 873bba5..0000000
--- a/test_upload.txt
+++ /dev/null
@@ -1,5 +0,0 @@
-这是一个测试文件,用于验证文件上传功能是否正常工作。
-文件内容包含中文和英文,以及一些特殊字符:!@#$%^&*()
-
-Created at: 2025-10-13
-Purpose: 测试文件上传修复
\ No newline at end of file
diff --git a/test_upload_v2.txt b/test_upload_v2.txt
deleted file mode 100644
index 17edd88..0000000
--- a/test_upload_v2.txt
+++ /dev/null
@@ -1,5 +0,0 @@
-这是第二个测试文件,用于验证文件上传功能完全正常。
-内容与第一个文件不同,所以不会触发去重机制。
-
-测试时间:2025-10-13 14:58
-测试状态:验证上传修复是否成功
\ No newline at end of file
diff --git a/ultimate_test.txt b/ultimate_test.txt
deleted file mode 100644
index ca9afab..0000000
--- a/ultimate_test.txt
+++ /dev/null
@@ -1 +0,0 @@
-Completely new file content at Mon, Oct 13, 2025 3:13:24 PM
diff --git a/unique_test_1760339196.txt b/unique_test_1760339196.txt
deleted file mode 100644
index e8f6de3..0000000
--- a/unique_test_1760339196.txt
+++ /dev/null
@@ -1 +0,0 @@
-Unique content 1760339195