删除、移动旧文档
This commit is contained in:
+61
-185
@@ -1,206 +1,82 @@
|
|||||||
# TJWater Server - Copilot Instructions
|
# Copilot Instructions for TJWater Server
|
||||||
|
|
||||||
This is a FastAPI-based water network management system (供水管网智能管理系统) that provides hydraulic simulation, SCADA data integration, network element management, and risk analysis capabilities.
|
This repository contains the backend code for the TJWater Server, a water distribution network management system built with FastAPI.
|
||||||
|
|
||||||
## Running the Server
|
## High-Level Architecture
|
||||||
|
|
||||||
|
The application follows a layered architecture:
|
||||||
|
|
||||||
|
- **Entry Point**: `app/main.py` initializes the FastAPI application, database connections (PostgreSQL & TimescaleDB), and middleware.
|
||||||
|
- **API Layer**: `app/api/v1` contains the route handlers.
|
||||||
|
- **Service Layer**: `app/services` contains business logic and orchestration.
|
||||||
|
- **Infrastructure Layer**: `app/infra` handles database connections (`db`), audit logging (`audit`), and external integrations.
|
||||||
|
- **Domain Layer**: `app/domain` likely contains core domain models.
|
||||||
|
- **Native/Algorithms**: `app/native` and `app/algorithms` handle specialized water network calculations (possibly using EPANET/WNTR).
|
||||||
|
|
||||||
|
## Build, Test, and Run Commands
|
||||||
|
|
||||||
|
### Environment Setup
|
||||||
|
|
||||||
|
- Dependencies are listed in `requirements.txt`.
|
||||||
|
- Configuration is managed via environment variables (see `.env.example` if available, or `app/core/config.py`).
|
||||||
|
- **Important**: Ensure `.env` is configured with correct database credentials for both PostgreSQL and TimescaleDB.
|
||||||
|
|
||||||
|
If first time setting up, you may want to create a Conda environment:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# activate the server environment
|
conda create -n server python=3.12
|
||||||
conda activate server
|
conda activate server
|
||||||
# Install dependencies
|
pip install uv
|
||||||
<!-- pip install -r requirements.txt -->
|
uv pip install -r requirements.txt
|
||||||
|
conda install -c conda-forge pymetis
|
||||||
# Start the server (default: http://0.0.0.0:8000 with 2 workers)
|
|
||||||
python scripts/run_server.py
|
|
||||||
|
|
||||||
# Note: On Windows, the script automatically sets WindowsSelectorEventLoopPolicy
|
|
||||||
```
|
```
|
||||||
|
|
||||||
## Running Tests
|
### Running the Server
|
||||||
|
|
||||||
|
The preferred way to run the server locally is using the helper script which sets up the Python path correctly:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# activate the server environment
|
|
||||||
conda activate server
|
conda activate server
|
||||||
|
python scripts/run_server.py
|
||||||
|
```
|
||||||
|
|
||||||
|
Alternatively, you can run directly with uvicorn (ensure PYTHONPATH includes the root):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
conda activate server
|
||||||
|
uvicorn app.main:app --host 0.0.0.0 --port 8000 --reload
|
||||||
|
```
|
||||||
|
|
||||||
|
### Running Tests
|
||||||
|
|
||||||
|
Use `pytest` to run tests. The `tests/conftest.py` handles path setup.
|
||||||
|
|
||||||
|
```bash
|
||||||
# Run all tests
|
# Run all tests
|
||||||
pytest
|
pytest
|
||||||
|
|
||||||
# Run a specific test file with verbose output
|
# Run a specific test file
|
||||||
pytest tests/unit/test_pipeline_health_analyzer.py -v
|
pytest tests/unit/test_specific_file.py
|
||||||
|
|
||||||
# Run from conftest helper
|
# Run a specific test case
|
||||||
python tests/conftest.py
|
pytest tests/unit/test_specific_file.py::test_function_name
|
||||||
```
|
```
|
||||||
|
|
||||||
## Architecture Overview
|
### Building (Optional)
|
||||||
|
|
||||||
### Core Components
|
The project includes scripts to compile Python modules to `.pyd` files using Cython (see `scripts/build_pyd.py`). This is likely for distribution/performance but not required for standard development.
|
||||||
|
|
||||||
1. **Native Modules** (`app/native/`): Platform-specific compiled extensions (`.so` for Linux, `.pyd` for Windows) providing performance-critical functionality including:
|
## Key Conventions
|
||||||
- SCADA device integration
|
|
||||||
- Water distribution analysis (WDA)
|
|
||||||
- Pipe risk probability calculations
|
|
||||||
- Wrapped through `app.services.tjnetwork` interface
|
|
||||||
|
|
||||||
2. **Services Layer** (`app/services/`):
|
- **Async/Await**: The codebase heavily uses `async` and `await` for I/O operations, especially database interactions.
|
||||||
- `tjnetwork.py`: Main network API wrapper around native modules
|
- **Database Management**:
|
||||||
- `simulation.py`: Hydraulic simulation orchestration (EPANET integration)
|
- Connections are managed globally in `app.infra.db` and initialized in `lifespan` (app/main.py).
|
||||||
- `project_info.py`: Project configuration management
|
- Use `app.infra.db.dynamic_manager` for project-specific database connections (multi-tenancy/dynamic projects).
|
||||||
- `epanet/`: EPANET hydraulic engine integration
|
- **Pydantic**: extensively used for data validation and settings management.
|
||||||
|
- **Scripts**: The `scripts/` directory contains many utility scripts for maintenance, data processing, and server management. Check there before writing new operational scripts.
|
||||||
|
- **Water Network Modeling**: Interactions with water network models often involve `epanet` or `wntr` libraries. Be aware of domain-specific terminology (nodes, links, junctions, tanks).
|
||||||
|
|
||||||
3. **API Layer** (`app/api/v1/`):
|
## Code Style
|
||||||
- **Network Elements**: Separate endpoint modules for junctions, reservoirs, tanks, pipes, pumps, valves
|
|
||||||
- **Components**: Curves, patterns, controls, options, quality, visuals
|
|
||||||
- **Network Features**: Tags, demands, geometry, regions/DMAs
|
|
||||||
- **Core Services**: Auth, project, simulation, SCADA, data query, snapshots
|
|
||||||
|
|
||||||
4. **Database Infrastructure** (`app/infra/db/`):
|
- Follow standard PEP 8 guidelines.
|
||||||
- **PostgreSQL**: Primary relational database (users, audit logs, project metadata)
|
- No specific linter configuration was found, so default to standard Python formatting.
|
||||||
- **TimescaleDB**: Time-series extension for historical data
|
|
||||||
- **InfluxDB**: Optional time-series database for high-frequency SCADA data
|
|
||||||
- Connection pools initialized in `main.py` lifespan context
|
|
||||||
- Database instance stored in `app.state.db` for dependency injection
|
|
||||||
|
|
||||||
5. **Domain Layer** (`app/domain/`):
|
|
||||||
- `models/`: Enums and domain objects (e.g., `UserRole`)
|
|
||||||
- `schemas/`: Pydantic models for request/response validation
|
|
||||||
|
|
||||||
6. **Algorithms** (`app/algorithms/`):
|
|
||||||
- `api_ex/`: Analysis algorithms (k-means sensor placement, sensitivity analysis, pipeline health)
|
|
||||||
- `data_cleaning.py`: Data preprocessing utilities
|
|
||||||
- `simulations.py`: Simulation helpers
|
|
||||||
|
|
||||||
### Security & Authentication
|
|
||||||
|
|
||||||
- **Authentication**: JWT-based with access tokens (30 min) and refresh tokens (7 days)
|
|
||||||
- **Authorization**: Role-based access control (RBAC) with 4 roles:
|
|
||||||
- `VIEWER`: Read-only access
|
|
||||||
- `USER`: Read-write access
|
|
||||||
- `OPERATOR`: Modify data
|
|
||||||
- `ADMIN`: Full permissions
|
|
||||||
- **Audit Logging**: `AuditMiddleware` automatically logs POST/PUT/DELETE requests
|
|
||||||
- **Encryption**: Fernet symmetric encryption for sensitive data (`app.core.encryption`)
|
|
||||||
|
|
||||||
Default admin accounts:
|
|
||||||
|
|
||||||
- `admin` / `admin123`
|
|
||||||
- `tjwater` / `tjwater@123`
|
|
||||||
|
|
||||||
### Key Files
|
|
||||||
|
|
||||||
- `app/main.py`: FastAPI app initialization, lifespan (DB pools), CORS, middleware, router mounting
|
|
||||||
- `app/api/v1/router.py`: Central router aggregating all endpoint modules
|
|
||||||
- `app/core/config.py`: Settings management using `pydantic-settings`
|
|
||||||
- `app/auth/dependencies.py`: Auth dependencies (`get_current_active_user`, `get_db`)
|
|
||||||
- `app/auth/permissions.py`: Permission decorators (`require_role`, `get_current_admin`)
|
|
||||||
- `.env`: Environment configuration (database credentials, JWT secret, encryption key)
|
|
||||||
|
|
||||||
## Important Conventions
|
|
||||||
|
|
||||||
### Database Connections
|
|
||||||
|
|
||||||
- Database instances are initialized in `main.py` lifespan and stored in `app.state.db`
|
|
||||||
- Access via dependency injection:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.dependencies import get_db
|
|
||||||
|
|
||||||
async def endpoint(db = Depends(get_db)):
|
|
||||||
# Use db connection
|
|
||||||
```
|
|
||||||
|
|
||||||
### Authentication in Endpoints
|
|
||||||
|
|
||||||
Use dependency injection for auth requirements:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.dependencies import get_current_active_user
|
|
||||||
from app.auth.permissions import require_role, get_current_admin
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
# Require any authenticated user
|
|
||||||
@router.get("/data")
|
|
||||||
async def get_data(current_user = Depends(get_current_active_user)):
|
|
||||||
return data
|
|
||||||
|
|
||||||
# Require specific role (USER or higher)
|
|
||||||
@router.post("/data")
|
|
||||||
async def create_data(current_user = Depends(require_role(UserRole.USER))):
|
|
||||||
return result
|
|
||||||
|
|
||||||
# Admin-only access
|
|
||||||
@router.delete("/data/{id}")
|
|
||||||
async def delete_data(id: int, current_user = Depends(get_current_admin)):
|
|
||||||
return result
|
|
||||||
```
|
|
||||||
|
|
||||||
### API Routing Structure
|
|
||||||
|
|
||||||
- All v1 APIs are mounted under `/api/v1` prefix via `api_router`
|
|
||||||
- Legacy routes without version prefix are also mounted for backward compatibility
|
|
||||||
- Group related endpoints in separate router modules under `app/api/v1/endpoints/`
|
|
||||||
- Use descriptive tags in `router.py` for OpenAPI documentation grouping
|
|
||||||
|
|
||||||
### Native Module Integration
|
|
||||||
|
|
||||||
- Native modules are pre-compiled for specific platforms
|
|
||||||
- Always import through `app.native.api` or `app.services.tjnetwork`
|
|
||||||
- The `tjnetwork` service wraps native APIs with constants like:
|
|
||||||
- Element types: `JUNCTION`, `RESERVOIR`, `TANK`, `PIPE`, `PUMP`, `VALVE`
|
|
||||||
- Operations: `API_ADD`, `API_UPDATE`, `API_DELETE`
|
|
||||||
- `ChangeSet` for batch operations
|
|
||||||
|
|
||||||
### Project Initialization
|
|
||||||
|
|
||||||
- On startup, `main.py` automatically loads project from `project_info.name` if set
|
|
||||||
- Projects are opened via `open_project(name)` from `tjnetwork` service
|
|
||||||
|
|
||||||
### Audit Logging
|
|
||||||
|
|
||||||
Manual audit logging for critical operations:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.core.audit import log_audit_event, AuditAction
|
|
||||||
|
|
||||||
await log_audit_event(
|
|
||||||
action=AuditAction.UPDATE,
|
|
||||||
user_id=current_user.id,
|
|
||||||
username=current_user.username,
|
|
||||||
resource_type="resource_name",
|
|
||||||
resource_id=str(resource_id),
|
|
||||||
ip_address=request.client.host,
|
|
||||||
request_data=data
|
|
||||||
)
|
|
||||||
```
|
|
||||||
|
|
||||||
### Environment Configuration
|
|
||||||
|
|
||||||
- Copy `.env.example` to `.env` before first run
|
|
||||||
- Required environment variables:
|
|
||||||
- `SECRET_KEY`: JWT signing (generate with `openssl rand -hex 32`)
|
|
||||||
- `ENCRYPTION_KEY`: Data encryption (generate with Fernet)
|
|
||||||
- Database credentials for PostgreSQL, TimescaleDB, and optionally InfluxDB
|
|
||||||
|
|
||||||
### Database Migrations
|
|
||||||
|
|
||||||
SQL migration scripts are in `migrations/`:
|
|
||||||
|
|
||||||
- `001_create_users_table.sql`: User authentication tables
|
|
||||||
- `002_create_audit_logs_table.sql`: Audit logging tables
|
|
||||||
|
|
||||||
Apply with:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
psql -U postgres -d tjwater -f migrations/001_create_users_table.sql
|
|
||||||
```
|
|
||||||
|
|
||||||
## API Documentation
|
|
||||||
|
|
||||||
- Swagger UI: http://localhost:8000/docs
|
|
||||||
- ReDoc: http://localhost:8000/redoc
|
|
||||||
- OpenAPI schema: http://localhost:8000/openapi.json
|
|
||||||
|
|
||||||
## Additional Resources
|
|
||||||
|
|
||||||
- `SECURITY_README.md`: Comprehensive security feature documentation
|
|
||||||
- `DEPLOYMENT.md`: Integration guide for security features
|
|
||||||
- `readme.md`: Project overview and directory structure (in Chinese)
|
|
||||||
|
|||||||
-391
@@ -1,391 +0,0 @@
|
|||||||
# 部署和集成指南
|
|
||||||
|
|
||||||
本文档说明如何将新的安全功能集成到现有系统中。
|
|
||||||
|
|
||||||
## 📦 已完成的功能
|
|
||||||
|
|
||||||
### 1. 数据加密模块
|
|
||||||
- ✅ `app/core/encryption.py` - Fernet 对称加密实现
|
|
||||||
- ✅ 支持敏感数据加密/解密
|
|
||||||
- ✅ 密钥管理和生成工具
|
|
||||||
|
|
||||||
### 2. 用户认证系统
|
|
||||||
- ✅ `app/domain/models/role.py` - 用户角色枚举 (ADMIN/OPERATOR/USER/VIEWER)
|
|
||||||
- ✅ `app/domain/schemas/user.py` - 用户数据模型和验证
|
|
||||||
- ✅ `app/infra/repositories/user_repository.py` - 用户数据访问层
|
|
||||||
- ✅ `app/api/v1/endpoints/auth.py` - 注册/登录/刷新Token接口
|
|
||||||
- ✅ `app/auth/dependencies.py` - 认证依赖项
|
|
||||||
- ✅ `migrations/001_create_users_table.sql` - 用户表迁移脚本
|
|
||||||
|
|
||||||
### 3. 权限控制系统
|
|
||||||
- ✅ `app/auth/permissions.py` - RBAC 权限控制装饰器
|
|
||||||
- ✅ `app/api/v1/endpoints/user_management.py` - 用户管理接口示例
|
|
||||||
- ✅ 支持基于角色的访问控制
|
|
||||||
- ✅ 支持资源所有者检查
|
|
||||||
|
|
||||||
### 4. 审计日志系统
|
|
||||||
- ✅ `app/core/audit.py` - 审计日志核心功能
|
|
||||||
- ✅ `app/domain/schemas/audit.py` - 审计日志数据模型
|
|
||||||
- ✅ `app/infra/repositories/audit_repository.py` - 审计日志数据访问层
|
|
||||||
- ✅ `app/api/v1/endpoints/audit.py` - 审计日志查询接口
|
|
||||||
- ✅ `app/infra/audit/middleware.py` - 自动审计中间件
|
|
||||||
- ✅ `migrations/002_create_audit_logs_table.sql` - 审计日志表迁移脚本
|
|
||||||
|
|
||||||
### 5. 文档和测试
|
|
||||||
- ✅ `SECURITY_README.md` - 完整的使用文档
|
|
||||||
- ✅ `.env.example` - 环境变量配置模板
|
|
||||||
- ✅ `tests/test_encryption.py` - 加密功能测试
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔧 集成步骤
|
|
||||||
|
|
||||||
### 步骤 1: 环境配置
|
|
||||||
|
|
||||||
1. 复制环境变量模板:
|
|
||||||
```bash
|
|
||||||
cp .env.example .env
|
|
||||||
```
|
|
||||||
|
|
||||||
2. 生成密钥并填写 `.env`:
|
|
||||||
```bash
|
|
||||||
# JWT 密钥
|
|
||||||
openssl rand -hex 32
|
|
||||||
|
|
||||||
# 加密密钥
|
|
||||||
python -c "from cryptography.fernet import Fernet; print(Fernet.generate_key().decode())"
|
|
||||||
```
|
|
||||||
|
|
||||||
3. 编辑 `.env` 填写所有必需的配置项。
|
|
||||||
|
|
||||||
### 步骤 2: 数据库迁移
|
|
||||||
|
|
||||||
执行数据库迁移脚本:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 方法 1: 使用 psql 命令
|
|
||||||
psql -U postgres -d tjwater -f migrations/001_create_users_table.sql
|
|
||||||
psql -U postgres -d tjwater -f migrations/002_create_audit_logs_table.sql
|
|
||||||
|
|
||||||
# 方法 2: 在 psql 交互界面
|
|
||||||
psql -U postgres -d tjwater
|
|
||||||
\i migrations/001_create_users_table.sql
|
|
||||||
\i migrations/002_create_audit_logs_table.sql
|
|
||||||
```
|
|
||||||
|
|
||||||
验证表已创建:
|
|
||||||
|
|
||||||
```sql
|
|
||||||
-- 检查用户表
|
|
||||||
SELECT * FROM users;
|
|
||||||
|
|
||||||
-- 检查审计日志表
|
|
||||||
SELECT * FROM audit_logs;
|
|
||||||
```
|
|
||||||
|
|
||||||
### 步骤 3: 更新 main.py
|
|
||||||
|
|
||||||
在 `app/main.py` 中集成新功能:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from fastapi import FastAPI
|
|
||||||
from app.core.config import settings
|
|
||||||
from app.infra.audit.middleware import AuditMiddleware
|
|
||||||
|
|
||||||
app = FastAPI(title=settings.PROJECT_NAME)
|
|
||||||
|
|
||||||
# 1. 添加审计中间件(可选)
|
|
||||||
app.add_middleware(AuditMiddleware)
|
|
||||||
|
|
||||||
# 2. 注册路由
|
|
||||||
from app.api.v1.endpoints import auth, user_management, audit
|
|
||||||
|
|
||||||
app.include_router(
|
|
||||||
auth.router,
|
|
||||||
prefix=f"{settings.API_V1_STR}/auth",
|
|
||||||
tags=["认证"]
|
|
||||||
)
|
|
||||||
|
|
||||||
app.include_router(
|
|
||||||
user_management.router,
|
|
||||||
prefix=f"{settings.API_V1_STR}/users",
|
|
||||||
tags=["用户管理"]
|
|
||||||
)
|
|
||||||
|
|
||||||
app.include_router(
|
|
||||||
audit.router,
|
|
||||||
prefix=f"{settings.API_V1_STR}/audit",
|
|
||||||
tags=["审计日志"]
|
|
||||||
)
|
|
||||||
|
|
||||||
# 3. 确保数据库在启动时初始化
|
|
||||||
@app.on_event("startup")
|
|
||||||
async def startup_event():
|
|
||||||
# 初始化数据库连接池
|
|
||||||
from app.infra.db.postgresql.database import Database
|
|
||||||
global db
|
|
||||||
db = Database()
|
|
||||||
db.init_pool()
|
|
||||||
await db.open()
|
|
||||||
|
|
||||||
@app.on_event("shutdown")
|
|
||||||
async def shutdown_event():
|
|
||||||
# 关闭数据库连接
|
|
||||||
await db.close()
|
|
||||||
```
|
|
||||||
|
|
||||||
### 步骤 4: 保护现有接口
|
|
||||||
|
|
||||||
#### 方法 1: 为路由添加全局依赖
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.dependencies import get_current_active_user
|
|
||||||
|
|
||||||
# 为整个路由器添加认证
|
|
||||||
router = APIRouter(dependencies=[Depends(get_current_active_user)])
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 方法 2: 为单个端点添加依赖
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.permissions import require_role, get_current_admin
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
@router.get("/data")
|
|
||||||
async def get_data(
|
|
||||||
current_user = Depends(require_role(UserRole.USER))
|
|
||||||
):
|
|
||||||
"""需要 USER 及以上角色"""
|
|
||||||
return {"data": "protected"}
|
|
||||||
|
|
||||||
@router.delete("/data/{id}")
|
|
||||||
async def delete_data(
|
|
||||||
id: int,
|
|
||||||
current_user = Depends(get_current_admin)
|
|
||||||
):
|
|
||||||
"""仅管理员可访问"""
|
|
||||||
return {"message": "deleted"}
|
|
||||||
```
|
|
||||||
|
|
||||||
### 步骤 5: 添加审计日志
|
|
||||||
|
|
||||||
#### 自动审计(推荐)
|
|
||||||
|
|
||||||
使用中间件自动记录(已在 main.py 中添加):
|
|
||||||
|
|
||||||
```python
|
|
||||||
app.add_middleware(AuditMiddleware)
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 手动审计
|
|
||||||
|
|
||||||
在关键业务逻辑中手动记录:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.core.audit import log_audit_event, AuditAction
|
|
||||||
|
|
||||||
@router.post("/important-action")
|
|
||||||
async def important_action(
|
|
||||||
data: dict,
|
|
||||||
request: Request,
|
|
||||||
current_user = Depends(get_current_active_user)
|
|
||||||
):
|
|
||||||
# 执行业务逻辑
|
|
||||||
result = do_something(data)
|
|
||||||
|
|
||||||
# 记录审计日志
|
|
||||||
await log_audit_event(
|
|
||||||
action=AuditAction.UPDATE,
|
|
||||||
user_id=current_user.id,
|
|
||||||
username=current_user.username,
|
|
||||||
resource_type="important_resource",
|
|
||||||
resource_id=str(result.id),
|
|
||||||
ip_address=request.client.host,
|
|
||||||
request_data=data
|
|
||||||
)
|
|
||||||
|
|
||||||
return result
|
|
||||||
```
|
|
||||||
|
|
||||||
### 步骤 6: 更新 auth/dependencies.py
|
|
||||||
|
|
||||||
确保 `get_db()` 函数正确获取数据库实例:
|
|
||||||
|
|
||||||
```python
|
|
||||||
async def get_db() -> Database:
|
|
||||||
"""获取数据库实例"""
|
|
||||||
# 方法 1: 从 main.py 导入
|
|
||||||
from app.main import db
|
|
||||||
return db
|
|
||||||
|
|
||||||
# 方法 2: 从 FastAPI app.state 获取
|
|
||||||
# from fastapi import Request
|
|
||||||
# def get_db_from_request(request: Request):
|
|
||||||
# return request.app.state.db
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🧪 测试
|
|
||||||
|
|
||||||
### 1. 测试加密功能
|
|
||||||
|
|
||||||
```bash
|
|
||||||
python tests/test_encryption.py
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. 测试 API
|
|
||||||
|
|
||||||
启动服务器:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
uvicorn app.main:app --reload
|
|
||||||
```
|
|
||||||
|
|
||||||
访问交互式文档:
|
|
||||||
- Swagger UI: http://localhost:8000/docs
|
|
||||||
- ReDoc: http://localhost:8000/redoc
|
|
||||||
|
|
||||||
### 3. 测试登录
|
|
||||||
|
|
||||||
```bash
|
|
||||||
curl -X POST "http://localhost:8000/api/v1/auth/login" \
|
|
||||||
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
||||||
-d "username=admin&password=admin123"
|
|
||||||
```
|
|
||||||
|
|
||||||
### 4. 测试受保护接口
|
|
||||||
|
|
||||||
```bash
|
|
||||||
TOKEN="your-access-token"
|
|
||||||
curl -X GET "http://localhost:8000/api/v1/auth/me" \
|
|
||||||
-H "Authorization: Bearer $TOKEN"
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔄 迁移现有接口
|
|
||||||
|
|
||||||
### 原有硬编码认证
|
|
||||||
|
|
||||||
**旧代码** (`app/api/v1/endpoints/auth.py`):
|
|
||||||
```python
|
|
||||||
AUTH_TOKEN = "567e33c876a2"
|
|
||||||
|
|
||||||
async def verify_token(authorization: str = Header()):
|
|
||||||
token = authorization.split(" ")[1]
|
|
||||||
if token != AUTH_TOKEN:
|
|
||||||
raise HTTPException(status_code=403)
|
|
||||||
```
|
|
||||||
|
|
||||||
**新代码** (已更新):
|
|
||||||
```python
|
|
||||||
from app.auth.dependencies import get_current_active_user
|
|
||||||
|
|
||||||
@router.get("/protected")
|
|
||||||
async def protected_route(
|
|
||||||
current_user = Depends(get_current_active_user)
|
|
||||||
):
|
|
||||||
return {"user": current_user.username}
|
|
||||||
```
|
|
||||||
|
|
||||||
### 更新其他端点
|
|
||||||
|
|
||||||
搜索项目中使用旧认证的地方:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
grep -r "AUTH_TOKEN" app/
|
|
||||||
grep -r "verify_token" app/
|
|
||||||
```
|
|
||||||
|
|
||||||
替换为新的依赖注入系统。
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📋 检查清单
|
|
||||||
|
|
||||||
部署前检查:
|
|
||||||
|
|
||||||
- [ ] 环境变量已配置(`.env`)
|
|
||||||
- [ ] 数据库迁移已执行
|
|
||||||
- [ ] 默认管理员账号可登录
|
|
||||||
- [ ] JWT Token 可正常生成和验证
|
|
||||||
- [ ] 权限控制正常工作
|
|
||||||
- [ ] 审计日志正常记录
|
|
||||||
- [ ] 加密功能测试通过
|
|
||||||
- [ ] API 文档可访问
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ⚠️ 注意事项
|
|
||||||
|
|
||||||
### 1. 向后兼容性
|
|
||||||
|
|
||||||
保留了简化版登录接口 `/auth/login/simple` 以兼容旧客户端:
|
|
||||||
|
|
||||||
```python
|
|
||||||
@router.post("/login/simple")
|
|
||||||
async def login_simple(username: str, password: str):
|
|
||||||
# 验证并返回 Token
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. 数据库连接
|
|
||||||
|
|
||||||
确保在 `app/auth/dependencies.py` 中 `get_db()` 函数能正确获取数据库实例。
|
|
||||||
|
|
||||||
### 3. 密钥安全
|
|
||||||
|
|
||||||
- ❌ 不要提交 `.env` 文件到版本控制
|
|
||||||
- ✅ 在生产环境使用环境变量或密钥管理服务
|
|
||||||
- ✅ 定期轮换 JWT 密钥
|
|
||||||
|
|
||||||
### 4. 性能考虑
|
|
||||||
|
|
||||||
- 审计中间件会增加每个请求的处理时间(约 5-10ms)
|
|
||||||
- 对高频接口可考虑异步记录审计日志
|
|
||||||
- 定期清理或归档旧的审计日志
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🐛 故障排查
|
|
||||||
|
|
||||||
### 问题 1: 导入错误
|
|
||||||
|
|
||||||
```
|
|
||||||
ImportError: cannot import name 'db' from 'app.main'
|
|
||||||
```
|
|
||||||
|
|
||||||
**解决**: 确保在 `app/main.py` 中定义了全局 `db` 对象。
|
|
||||||
|
|
||||||
### 问题 2: 认证失败
|
|
||||||
|
|
||||||
```
|
|
||||||
401 Unauthorized: Could not validate credentials
|
|
||||||
```
|
|
||||||
|
|
||||||
**检查**:
|
|
||||||
1. Token 是否正确设置在 `Authorization: Bearer {token}` header
|
|
||||||
2. Token 是否过期
|
|
||||||
3. SECRET_KEY 是否配置正确
|
|
||||||
|
|
||||||
### 问题 3: 数据库连接失败
|
|
||||||
|
|
||||||
```
|
|
||||||
psycopg.OperationalError: connection failed
|
|
||||||
```
|
|
||||||
|
|
||||||
**检查**:
|
|
||||||
1. PostgreSQL 是否运行
|
|
||||||
2. `.env` 中数据库配置是否正确
|
|
||||||
3. 数据库是否存在
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 技术支持
|
|
||||||
|
|
||||||
详细文档请参考:
|
|
||||||
- `SECURITY_README.md` - 安全功能使用指南
|
|
||||||
- `migrations/` - 数据库迁移脚本
|
|
||||||
- `app/domain/schemas/` - 数据模型定义
|
|
||||||
|
|
||||||
@@ -1,269 +0,0 @@
|
|||||||
# TJWater ServerBinary - Documentation Index
|
|
||||||
|
|
||||||
## 📋 Complete Documentation Structure
|
|
||||||
|
|
||||||
### 🆕 **NEW: Secondary Development Documentation** (Recommended Starting Point)
|
|
||||||
|
|
||||||
#### 1. **QUICK_START_GUIDE.md** (7.5 KB, 326 lines)
|
|
||||||
**Perfect for**: Getting started in 15 minutes
|
|
||||||
- Quick reference card with copy-paste code
|
|
||||||
- 7 most common tasks with examples
|
|
||||||
- Common pitfalls and how to avoid them
|
|
||||||
- File location reference
|
|
||||||
- Key imports cheat sheet
|
|
||||||
|
|
||||||
**Read first if**: You're new to the codebase and want quick examples
|
|
||||||
|
|
||||||
#### 2. **SECONDARY_DEVELOPMENT_GUIDE.md** (29 KB, 1,015 lines)
|
|
||||||
**Perfect for**: Deep understanding of the system
|
|
||||||
- Complete architecture overview
|
|
||||||
- Detailed guide for all 7 key aspects
|
|
||||||
- Implementation patterns with code examples
|
|
||||||
- Technology stack reference
|
|
||||||
- Best practices and recommendations
|
|
||||||
|
|
||||||
**Read after**: QUICK_START_GUIDE, or if you need comprehensive understanding
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
### 📖 **Existing Documentation** (Supporting References)
|
|
||||||
|
|
||||||
#### 3. **readme.md** (3.5 KB)
|
|
||||||
- Project overview
|
|
||||||
- Main features
|
|
||||||
- Quick start for running the server
|
|
||||||
- Directory structure introduction
|
|
||||||
|
|
||||||
#### 4. **SECURITY_README.md** (11 KB)
|
|
||||||
- Security features overview
|
|
||||||
- Authentication setup
|
|
||||||
- Encryption implementation
|
|
||||||
- Audit logging features
|
|
||||||
|
|
||||||
#### 5. **SECURITY_IMPLEMENTATION_SUMMARY.md** (9 KB)
|
|
||||||
- Detailed security implementation
|
|
||||||
- Role-based access control
|
|
||||||
- Password policies
|
|
||||||
- Encryption key management
|
|
||||||
|
|
||||||
#### 6. **DEPLOYMENT.md** (8.7 KB)
|
|
||||||
- Production deployment checklist
|
|
||||||
- Docker configuration
|
|
||||||
- Database setup
|
|
||||||
- Environment configuration
|
|
||||||
|
|
||||||
#### 7. **INTEGRATION_CHECKLIST.md** (8.3 KB)
|
|
||||||
- System integration steps
|
|
||||||
- Database initialization
|
|
||||||
- Service verification
|
|
||||||
- Health checks
|
|
||||||
|
|
||||||
#### 8. **setup_server.md** (3.1 KB)
|
|
||||||
- Initial server setup
|
|
||||||
- Environment variables
|
|
||||||
- Database configuration
|
|
||||||
|
|
||||||
#### 9. **setup_influxdb.md** (325 B)
|
|
||||||
- InfluxDB configuration reference
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎯 Reading Paths by Role
|
|
||||||
|
|
||||||
### For Backend Developers (Adding Features)
|
|
||||||
1. Start: **QUICK_START_GUIDE.md** (Section 1: Adding API Endpoints)
|
|
||||||
2. Then: **SECONDARY_DEVELOPMENT_GUIDE.md** (Sections 2-7)
|
|
||||||
3. Refer: **SECURITY_README.md** (authentication patterns)
|
|
||||||
4. Deploy: **DEPLOYMENT.md** (when ready for production)
|
|
||||||
|
|
||||||
### For Database/ORM Developers
|
|
||||||
1. Start: **QUICK_START_GUIDE.md** (Section 2: Database Query Pattern)
|
|
||||||
2. Then: **SECONDARY_DEVELOPMENT_GUIDE.md** (Section 3: Database Patterns)
|
|
||||||
3. Refer: Database migration examples in `resources/sql/`
|
|
||||||
|
|
||||||
### For Security/DevOps Engineers
|
|
||||||
1. Start: **SECURITY_README.md**
|
|
||||||
2. Then: **SECURITY_IMPLEMENTATION_SUMMARY.md**
|
|
||||||
3. Deploy: **DEPLOYMENT.md**
|
|
||||||
4. Reference: **SECONDARY_DEVELOPMENT_GUIDE.md** (Sections 5-6)
|
|
||||||
|
|
||||||
### For QA/Testing Engineers
|
|
||||||
1. Start: **QUICK_START_GUIDE.md** (Section 7: Testing)
|
|
||||||
2. Then: **SECONDARY_DEVELOPMENT_GUIDE.md** (Section 7: Testing Setup)
|
|
||||||
3. Review: `tests/` directory for examples
|
|
||||||
|
|
||||||
### For New Team Members
|
|
||||||
1. Start: **readme.md** (project overview)
|
|
||||||
2. Then: **QUICK_START_GUIDE.md** (30-minute overview)
|
|
||||||
3. Deep Dive: **SECONDARY_DEVELOPMENT_GUIDE.md** (comprehensive reference)
|
|
||||||
4. Explore: Source code with documentation as reference
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 Documentation by Topic
|
|
||||||
|
|
||||||
### API Development
|
|
||||||
- **QUICK_START_GUIDE.md** § 1: Adding a New API Endpoint
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 2: API Endpoint Addition
|
|
||||||
|
|
||||||
### Authentication & Authorization
|
|
||||||
- **QUICK_START_GUIDE.md** § 3: Role-Based Access Control
|
|
||||||
- **SECURITY_README.md**: Complete auth guide
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 5: Auth Mechanisms
|
|
||||||
- **SECURITY_IMPLEMENTATION_SUMMARY.md**: Implementation details
|
|
||||||
|
|
||||||
### Database & Data Access
|
|
||||||
- **QUICK_START_GUIDE.md** § 2: Database Query Pattern
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 3: Database Patterns
|
|
||||||
- Source: `app/infra/repositories/` (examples)
|
|
||||||
|
|
||||||
### Native Code Integration
|
|
||||||
- **QUICK_START_GUIDE.md** § 4: Call Native Code
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 4: Native Module Integration
|
|
||||||
|
|
||||||
### Configuration Management
|
|
||||||
- **QUICK_START_GUIDE.md** § 6: Configuration
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 6: Configuration Management
|
|
||||||
- Reference: `app/core/config.py`
|
|
||||||
|
|
||||||
### Security & Encryption
|
|
||||||
- **QUICK_START_GUIDE.md** § 5: Encryption & Security
|
|
||||||
- **SECURITY_README.md**: Complete guide
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 6: Configuration (encryption keys)
|
|
||||||
|
|
||||||
### Testing
|
|
||||||
- **QUICK_START_GUIDE.md** § 7: Testing
|
|
||||||
- **SECONDARY_DEVELOPMENT_GUIDE.md** § 7: Testing Setup
|
|
||||||
- Examples: `tests/` directory
|
|
||||||
|
|
||||||
### Deployment
|
|
||||||
- **DEPLOYMENT.md**: Complete deployment guide
|
|
||||||
- **INTEGRATION_CHECKLIST.md**: Integration steps
|
|
||||||
- **setup_server.md**: Initial setup
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔍 Quick Reference Table
|
|
||||||
|
|
||||||
| Topic | Quick Start | Comprehensive | Implementation |
|
|
||||||
|-------|------------|---------------|-----------------|
|
|
||||||
| **APIs** | § 1 QSG | § 2 SDG | `app/api/v1/` |
|
|
||||||
| **Database** | § 2 QSG | § 3 SDG | `app/infra/db/` |
|
|
||||||
| **Native Code** | § 4 QSG | § 4 SDG | `app/native/wndb/` |
|
|
||||||
| **Auth** | § 3 QSG | § 5 SDG | `app/auth/` |
|
|
||||||
| **Config** | § 6 QSG | § 6 SDG | `app/core/config.py` |
|
|
||||||
| **Testing** | § 7 QSG | § 7 SDG | `tests/` |
|
|
||||||
| **Security** | SECURITY_README.md | SECURITY_IMPL_SUMMARY.md | `app/core/security.py` |
|
|
||||||
| **Deployment** | setup_server.md | DEPLOYMENT.md | `infra/docker/` |
|
|
||||||
|
|
||||||
**Legend**: QSG = QUICK_START_GUIDE.md, SDG = SECONDARY_DEVELOPMENT_GUIDE.md
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📂 Documentation File Locations
|
|
||||||
|
|
||||||
```
|
|
||||||
TJWaterServerBinary/
|
|
||||||
├── SECONDARY_DEVELOPMENT_GUIDE.md ← Start here (comprehensive)
|
|
||||||
├── QUICK_START_GUIDE.md ← Start here (quick)
|
|
||||||
├── readme.md ← Project overview
|
|
||||||
├── SECURITY_README.md ← Security features
|
|
||||||
├── SECURITY_IMPLEMENTATION_SUMMARY.md ← Security details
|
|
||||||
├── DEPLOYMENT.md ← Production deployment
|
|
||||||
├── INTEGRATION_CHECKLIST.md ← Integration steps
|
|
||||||
├── setup_server.md ← Initial setup
|
|
||||||
├── setup_influxdb.md ← InfluxDB config
|
|
||||||
└── DOCUMENTATION_INDEX.md ← You are here
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 Getting Started Checklist
|
|
||||||
|
|
||||||
- [ ] Read `readme.md` for project overview
|
|
||||||
- [ ] Read `QUICK_START_GUIDE.md` for hands-on examples
|
|
||||||
- [ ] Read `SECONDARY_DEVELOPMENT_GUIDE.md` for deep knowledge
|
|
||||||
- [ ] Set up environment (`.env` file)
|
|
||||||
- [ ] Review `app/main.py` (83 lines - very readable)
|
|
||||||
- [ ] Review `app/api/v1/router.py` (98 lines - all endpoints listed)
|
|
||||||
- [ ] Pick a simple endpoint to understand
|
|
||||||
- [ ] Try adding a test endpoint
|
|
||||||
- [ ] Review security setup (`SECURITY_README.md`)
|
|
||||||
- [ ] Set up local development environment
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 💡 Key Learning Points
|
|
||||||
|
|
||||||
1. **FastAPI Architecture**: See `app/main.py` (83 lines) - clean and simple
|
|
||||||
2. **Router Pattern**: See `app/api/v1/router.py` (98 lines) - 30+ routers included
|
|
||||||
3. **Repository Pattern**: See `app/infra/repositories/` - data access layer
|
|
||||||
4. **Auth Patterns**: See `app/auth/dependencies.py` - JWT validation
|
|
||||||
5. **Permission Decorators**: See `app/auth/permissions.py` - RBAC
|
|
||||||
6. **Config Management**: See `app/core/config.py` (82 lines) - Pydantic Settings
|
|
||||||
7. **Database Pooling**: See `app/infra/db/postgresql/database.py` - async pools
|
|
||||||
8. **Native Integration**: See `app/native/wndb/__init__.py` - 100+ wrapped functions
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 Documentation Maintenance
|
|
||||||
|
|
||||||
These documents are maintained as part of the secondary development guide.
|
|
||||||
|
|
||||||
**Last Updated**: 2024-03-09
|
|
||||||
|
|
||||||
**Covered Sections**:
|
|
||||||
- ✅ Project structure and key directories
|
|
||||||
- ✅ API endpoint addition (router registration)
|
|
||||||
- ✅ Database interaction patterns (ORMs, migrations)
|
|
||||||
- ✅ Native module integration
|
|
||||||
- ✅ Authentication and authorization mechanisms
|
|
||||||
- ✅ Configuration management
|
|
||||||
- ✅ Testing setup
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎓 Recommended Learning Order
|
|
||||||
|
|
||||||
### Week 1: Foundations
|
|
||||||
1. Project overview (`readme.md`)
|
|
||||||
2. Quick Start Guide (`QUICK_START_GUIDE.md`)
|
|
||||||
3. Architecture (`SECONDARY_DEVELOPMENT_GUIDE.md` § 1)
|
|
||||||
|
|
||||||
### Week 2: Core Development
|
|
||||||
4. API Development (`SECONDARY_DEVELOPMENT_GUIDE.md` § 2)
|
|
||||||
5. Database Patterns (`SECONDARY_DEVELOPMENT_GUIDE.md` § 3)
|
|
||||||
6. Native Integration (`SECONDARY_DEVELOPMENT_GUIDE.md` § 4)
|
|
||||||
|
|
||||||
### Week 3: Security & Operations
|
|
||||||
7. Auth & Permissions (`SECONDARY_DEVELOPMENT_GUIDE.md` § 5)
|
|
||||||
8. Configuration (`SECONDARY_DEVELOPMENT_GUIDE.md` § 6)
|
|
||||||
9. Testing (`SECONDARY_DEVELOPMENT_GUIDE.md` § 7)
|
|
||||||
|
|
||||||
### Week 4: Deployment & Maintenance
|
|
||||||
10. Security Setup (`SECURITY_README.md`)
|
|
||||||
11. Deployment (`DEPLOYMENT.md`)
|
|
||||||
12. Integration (`INTEGRATION_CHECKLIST.md`)
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ❓ FAQ
|
|
||||||
|
|
||||||
**Q: Where do I start?**
|
|
||||||
A: If you have 30 minutes: `QUICK_START_GUIDE.md`. If you have 2 hours: `SECONDARY_DEVELOPMENT_GUIDE.md`.
|
|
||||||
|
|
||||||
**Q: How do I add a new API endpoint?**
|
|
||||||
A: See `QUICK_START_GUIDE.md` § 1 or `SECONDARY_DEVELOPMENT_GUIDE.md` § 2.
|
|
||||||
|
|
||||||
**Q: How do I implement database queries?**
|
|
||||||
A: See `QUICK_START_GUIDE.md` § 2 or `SECONDARY_DEVELOPMENT_GUIDE.md` § 3.
|
|
||||||
|
|
||||||
**Q: How does authentication work?**
|
|
||||||
A: See `QUICK_START_GUIDE.md` § 3 or `SECONDARY_DEVELOPMENT_GUIDE.md` § 5.
|
|
||||||
|
|
||||||
**Q: Where is the code?**
|
|
||||||
A: Key files are referenced in all guides. Start with `app/main.py`, `app/api/v1/router.py`, `app/core/config.py`.
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
*This documentation index helps secondary development teams navigate the comprehensive TJWater ServerBinary codebase efficiently.*
|
|
||||||
@@ -1,322 +0,0 @@
|
|||||||
# API 集成检查清单
|
|
||||||
|
|
||||||
## ✅ 已完成的集成工作
|
|
||||||
|
|
||||||
### 1. 路由集成 (app/api/v1/router.py)
|
|
||||||
|
|
||||||
已添加以下路由到 API Router:
|
|
||||||
|
|
||||||
```python
|
|
||||||
# 新增导入
|
|
||||||
from app.api.v1.endpoints import (
|
|
||||||
...
|
|
||||||
user_management, # 用户管理
|
|
||||||
audit, # 审计日志
|
|
||||||
)
|
|
||||||
|
|
||||||
# 新增路由
|
|
||||||
api_router.include_router(user_management.router, prefix="/users", tags=["User Management"])
|
|
||||||
api_router.include_router(audit.router, prefix="/audit", tags=["Audit Logs"])
|
|
||||||
```
|
|
||||||
|
|
||||||
**路由端点**:
|
|
||||||
- `/api/v1/auth/` - 认证相关(register, login, me, refresh)
|
|
||||||
- `/api/v1/users/` - 用户管理(CRUD操作,仅管理员)
|
|
||||||
- `/api/v1/audit/` - 审计日志查询(仅管理员)
|
|
||||||
|
|
||||||
### 2. 主应用配置 (app/main.py)
|
|
||||||
|
|
||||||
#### 2.1 导入更新
|
|
||||||
```python
|
|
||||||
from app.core.config import settings
|
|
||||||
from app.infra.audit.middleware import AuditMiddleware
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 2.2 数据库初始化
|
|
||||||
```python
|
|
||||||
# 在 lifespan 中存储数据库实例到 app.state
|
|
||||||
app.state.db = pgdb
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 2.3 FastAPI 配置
|
|
||||||
```python
|
|
||||||
app = FastAPI(
|
|
||||||
lifespan=lifespan,
|
|
||||||
title=settings.PROJECT_NAME,
|
|
||||||
description="TJWater Server - 供水管网智能管理系统",
|
|
||||||
version="1.0.0",
|
|
||||||
docs_url="/docs",
|
|
||||||
redoc_url="/redoc",
|
|
||||||
)
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 2.4 审计中间件(可选)
|
|
||||||
```python
|
|
||||||
# 取消注释以启用审计日志
|
|
||||||
# app.add_middleware(AuditMiddleware)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3. 依赖项更新 (app/auth/dependencies.py)
|
|
||||||
|
|
||||||
更新 `get_db()` 函数从 Request 对象获取数据库:
|
|
||||||
|
|
||||||
```python
|
|
||||||
async def get_db(request: Request) -> Database:
|
|
||||||
"""从 app.state 获取数据库实例"""
|
|
||||||
if not hasattr(request.app.state, "db"):
|
|
||||||
raise HTTPException(
|
|
||||||
status_code=status.HTTP_503_SERVICE_UNAVAILABLE,
|
|
||||||
detail="Database not initialized"
|
|
||||||
)
|
|
||||||
return request.app.state.db
|
|
||||||
```
|
|
||||||
|
|
||||||
### 4. 审计日志更新
|
|
||||||
|
|
||||||
- `app/api/v1/endpoints/audit.py` - 使用正确的数据库依赖
|
|
||||||
- `app/core/audit.py` - 接受可选的 db 参数
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📋 部署前检查清单
|
|
||||||
|
|
||||||
### 环境配置
|
|
||||||
- [ ] 复制 `.env.example` 为 `.env`
|
|
||||||
- [ ] 配置 `SECRET_KEY`(JWT密钥)
|
|
||||||
- [ ] 配置 `ENCRYPTION_KEY`(数据加密密钥)
|
|
||||||
- [ ] 配置数据库连接信息
|
|
||||||
|
|
||||||
### 数据库迁移
|
|
||||||
- [ ] 执行用户表迁移:`psql -U postgres -d tjwater -f migrations/001_create_users_table.sql`
|
|
||||||
- [ ] 执行审计日志表迁移:`psql -U postgres -d tjwater -f migrations/002_create_audit_logs_table.sql`
|
|
||||||
- [ ] 验证表已创建:`\dt` 在 psql 中
|
|
||||||
|
|
||||||
### 依赖检查
|
|
||||||
- [ ] 确认已安装:`cryptography`
|
|
||||||
- [ ] 确认已安装:`python-jose[cryptography]`
|
|
||||||
- [ ] 确认已安装:`passlib[bcrypt]`
|
|
||||||
- [ ] 确认已安装:`email-validator`(用于 Pydantic email 验证)
|
|
||||||
|
|
||||||
### 代码验证
|
|
||||||
- [ ] 检查所有文件导入正常
|
|
||||||
- [ ] 运行加密功能测试:`python tests/test_encryption.py`
|
|
||||||
- [ ] 启动服务器:`uvicorn app.main:app --reload`
|
|
||||||
- [ ] 访问 API 文档:http://localhost:8000/docs
|
|
||||||
|
|
||||||
### API 测试
|
|
||||||
- [ ] 测试登录:POST `/api/v1/auth/login`
|
|
||||||
- [ ] 测试获取当前用户:GET `/api/v1/auth/me`
|
|
||||||
- [ ] 测试用户列表(需管理员):GET `/api/v1/users/`
|
|
||||||
- [ ] 测试审计日志(需管理员):GET `/api/v1/audit/logs`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔧 快速测试命令
|
|
||||||
|
|
||||||
### 1. 生成密钥
|
|
||||||
```bash
|
|
||||||
# JWT 密钥
|
|
||||||
openssl rand -hex 32
|
|
||||||
|
|
||||||
# 加密密钥
|
|
||||||
python -c "from cryptography.fernet import Fernet; print(Fernet.generate_key().decode())"
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. 执行迁移
|
|
||||||
```bash
|
|
||||||
cd /home/zhifu/TJWaterServer/TJWaterServerBinary
|
|
||||||
psql -U postgres -d tjwater -f migrations/001_create_users_table.sql
|
|
||||||
psql -U postgres -d tjwater -f migrations/002_create_audit_logs_table.sql
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3. 测试加密
|
|
||||||
```bash
|
|
||||||
python tests/test_encryption.py
|
|
||||||
```
|
|
||||||
|
|
||||||
### 4. 启动服务器
|
|
||||||
```bash
|
|
||||||
uvicorn app.main:app --reload --host 0.0.0.0 --port 8000
|
|
||||||
```
|
|
||||||
|
|
||||||
### 5. 测试登录 API
|
|
||||||
```bash
|
|
||||||
# 使用默认管理员账号
|
|
||||||
curl -X POST "http://localhost:8000/api/v1/auth/login" \
|
|
||||||
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
||||||
-d "username=admin&password=admin123"
|
|
||||||
|
|
||||||
# 或使用迁移的账号
|
|
||||||
curl -X POST "http://localhost:8000/api/v1/auth/login" \
|
|
||||||
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
||||||
-d "username=tjwater&password=tjwater@123"
|
|
||||||
```
|
|
||||||
|
|
||||||
### 6. 测试受保护接口
|
|
||||||
```bash
|
|
||||||
# 保存 Token
|
|
||||||
TOKEN="<从登录响应中获取的 access_token>"
|
|
||||||
|
|
||||||
# 获取当前用户信息
|
|
||||||
curl -X GET "http://localhost:8000/api/v1/auth/me" \
|
|
||||||
-H "Authorization: Bearer $TOKEN"
|
|
||||||
|
|
||||||
# 获取用户列表(需管理员权限)
|
|
||||||
curl -X GET "http://localhost:8000/api/v1/users/" \
|
|
||||||
-H "Authorization: Bearer $TOKEN"
|
|
||||||
|
|
||||||
# 查询审计日志(需管理员权限)
|
|
||||||
curl -X GET "http://localhost:8000/api/v1/audit/logs" \
|
|
||||||
-H "Authorization: Bearer $TOKEN"
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 API 端点总览
|
|
||||||
|
|
||||||
### 认证接口 (`/api/v1/auth`)
|
|
||||||
|
|
||||||
| 方法 | 端点 | 描述 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| POST | `/register` | 用户注册 | 公开 |
|
|
||||||
| POST | `/login` | OAuth2 登录 | 公开 |
|
|
||||||
| POST | `/login/simple` | 简化登录(兼容旧版) | 公开 |
|
|
||||||
| GET | `/me` | 获取当前用户信息 | 认证用户 |
|
|
||||||
| POST | `/refresh` | 刷新 Token | 认证用户 |
|
|
||||||
|
|
||||||
### 用户管理 (`/api/v1/users`)
|
|
||||||
|
|
||||||
| 方法 | 端点 | 描述 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| GET | `/` | 获取用户列表 | 管理员 |
|
|
||||||
| GET | `/{id}` | 获取用户详情 | 所有者/管理员 |
|
|
||||||
| PUT | `/{id}` | 更新用户信息 | 所有者/管理员 |
|
|
||||||
| DELETE | `/{id}` | 删除用户 | 管理员 |
|
|
||||||
| POST | `/{id}/activate` | 激活用户 | 管理员 |
|
|
||||||
| POST | `/{id}/deactivate` | 停用用户 | 管理员 |
|
|
||||||
|
|
||||||
### 审计日志 (`/api/v1/audit`)
|
|
||||||
|
|
||||||
| 方法 | 端点 | 描述 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| GET | `/logs` | 查询审计日志 | 管理员 |
|
|
||||||
| GET | `/logs/count` | 获取日志总数 | 管理员 |
|
|
||||||
| GET | `/logs/my` | 查看我的操作记录 | 认证用户 |
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ⚠️ 注意事项
|
|
||||||
|
|
||||||
### 1. 审计中间件
|
|
||||||
审计中间件默认是**禁用**的。如需启用,在 `app/main.py` 中取消注释:
|
|
||||||
|
|
||||||
```python
|
|
||||||
app.add_middleware(AuditMiddleware)
|
|
||||||
```
|
|
||||||
|
|
||||||
**注意**:启用后会自动记录所有 POST/PUT/DELETE 请求,可能增加数据库负载。
|
|
||||||
|
|
||||||
### 2. 向后兼容
|
|
||||||
保留了原有的简化登录接口 `/auth/login/simple`,可以直接使用查询参数:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
POST /api/v1/auth/login/simple?username=admin&password=admin123
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3. 数据库连接
|
|
||||||
确保数据库实例在应用启动时正确初始化并存储到 `app.state.db`。
|
|
||||||
|
|
||||||
### 4. 权限控制示例
|
|
||||||
为现有接口添加权限控制:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.permissions import require_role, get_current_admin
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
# 需要管理员权限
|
|
||||||
@router.delete("/resource/{id}")
|
|
||||||
async def delete_resource(
|
|
||||||
id: int,
|
|
||||||
current_user = Depends(get_current_admin)
|
|
||||||
):
|
|
||||||
...
|
|
||||||
|
|
||||||
# 需要操作员以上权限
|
|
||||||
@router.post("/resource")
|
|
||||||
async def create_resource(
|
|
||||||
data: dict,
|
|
||||||
current_user = Depends(require_role(UserRole.OPERATOR))
|
|
||||||
):
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 完整启动流程
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 1. 进入项目目录
|
|
||||||
cd /home/zhifu/TJWaterServer/TJWaterServerBinary
|
|
||||||
|
|
||||||
# 2. 配置环境变量(如果还没有)
|
|
||||||
cp .env.example .env
|
|
||||||
# 编辑 .env 填写必要的配置
|
|
||||||
|
|
||||||
# 3. 执行数据库迁移(如果还没有)
|
|
||||||
psql -U postgres -d tjwater < migrations/001_create_users_table.sql
|
|
||||||
psql -U postgres -d tjwater < migrations/002_create_audit_logs_table.sql
|
|
||||||
|
|
||||||
# 4. 测试加密功能
|
|
||||||
python tests/test_encryption.py
|
|
||||||
|
|
||||||
# 5. 启动服务器
|
|
||||||
uvicorn app.main:app --reload
|
|
||||||
|
|
||||||
# 6. 访问 API 文档
|
|
||||||
# 浏览器打开: http://localhost:8000/docs
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 故障排查
|
|
||||||
|
|
||||||
### 问题 1: 导入错误
|
|
||||||
```
|
|
||||||
ModuleNotFoundError: No module named 'jose'
|
|
||||||
```
|
|
||||||
**解决**: 安装依赖 `pip install python-jose[cryptography]`
|
|
||||||
|
|
||||||
### 问题 2: 数据库未初始化
|
|
||||||
```
|
|
||||||
503 Service Unavailable: Database not initialized
|
|
||||||
```
|
|
||||||
**解决**: 检查 `main.py` 中的 lifespan 函数是否正确设置 `app.state.db`
|
|
||||||
|
|
||||||
### 问题 3: Token 验证失败
|
|
||||||
```
|
|
||||||
401 Unauthorized: Could not validate credentials
|
|
||||||
```
|
|
||||||
**解决**:
|
|
||||||
1. 检查 SECRET_KEY 是否配置正确
|
|
||||||
2. 确认 Token 格式:`Authorization: Bearer {token}`
|
|
||||||
3. 检查 Token 是否过期
|
|
||||||
|
|
||||||
### 问题 4: 表不存在
|
|
||||||
```
|
|
||||||
relation "users" does not exist
|
|
||||||
```
|
|
||||||
**解决**: 执行数据库迁移脚本
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📖 相关文档
|
|
||||||
|
|
||||||
- **使用指南**: `SECURITY_README.md`
|
|
||||||
- **部署指南**: `DEPLOYMENT.md`
|
|
||||||
- **实施总结**: `SECURITY_IMPLEMENTATION_SUMMARY.md`
|
|
||||||
- **自动设置**: `setup_security.sh`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
**最后更新**: 2026-02-02
|
|
||||||
**状态**: ✅ API 已完全集成
|
|
||||||
@@ -1,326 +0,0 @@
|
|||||||
# TJWater ServerBinary - Quick Reference for Secondary Development
|
|
||||||
|
|
||||||
## 1️⃣ Adding a New API Endpoint (30 seconds)
|
|
||||||
|
|
||||||
### File: `app/api/v1/endpoints/my_feature.py`
|
|
||||||
```python
|
|
||||||
from fastapi import APIRouter, Depends
|
|
||||||
from app.auth.dependencies import get_current_active_user
|
|
||||||
from app.domain.schemas.user import UserInDB
|
|
||||||
|
|
||||||
router = APIRouter()
|
|
||||||
|
|
||||||
@router.get("/list")
|
|
||||||
async def list_items(user: UserInDB = Depends(get_current_active_user)):
|
|
||||||
return {"items": []}
|
|
||||||
|
|
||||||
@router.post("/create")
|
|
||||||
async def create_item(data: dict, user: UserInDB = Depends(get_current_active_user)):
|
|
||||||
return {"status": "created"}
|
|
||||||
```
|
|
||||||
|
|
||||||
### File: `app/api/v1/router.py` (Add 2 lines)
|
|
||||||
```python
|
|
||||||
from app.api.v1.endpoints import my_feature
|
|
||||||
|
|
||||||
api_router.include_router(my_feature.router, prefix="/items", tags=["Items"])
|
|
||||||
```
|
|
||||||
|
|
||||||
**Done!** Endpoint available at `POST /api/v1/items/create`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 2️⃣ Database Query Pattern
|
|
||||||
|
|
||||||
### Using Repository
|
|
||||||
```python
|
|
||||||
from app.infra.repositories.user_repository import UserRepository
|
|
||||||
from app.auth.dependencies import get_user_repository
|
|
||||||
|
|
||||||
@router.get("/user/{user_id}")
|
|
||||||
async def get_user(user_id: int, user_repo: UserRepository = Depends(get_user_repository)):
|
|
||||||
user = await user_repo.get_user_by_id(user_id)
|
|
||||||
return user
|
|
||||||
```
|
|
||||||
|
|
||||||
### Direct Query (if no repository exists)
|
|
||||||
```python
|
|
||||||
async with db.get_connection() as conn:
|
|
||||||
async with conn.cursor() as cur:
|
|
||||||
await cur.execute("SELECT * FROM users WHERE id = %s", (user_id,))
|
|
||||||
row = await cur.fetchone()
|
|
||||||
return dict(row) if row else None
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 3️⃣ Role-Based Access Control
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.permissions import require_admin, require_role
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
# Admin only
|
|
||||||
@router.delete("/users/{user_id}")
|
|
||||||
async def delete_user(user_id: int, admin: UserInDB = Depends(require_admin)):
|
|
||||||
pass
|
|
||||||
|
|
||||||
# Operator or higher
|
|
||||||
@router.post("/projects/")
|
|
||||||
async def create_project(user: UserInDB = Depends(require_role(UserRole.OPERATOR))):
|
|
||||||
pass
|
|
||||||
|
|
||||||
# Custom role check
|
|
||||||
def require_viewer():
|
|
||||||
return require_role(UserRole.VIEWER)
|
|
||||||
|
|
||||||
@router.get("/reports")
|
|
||||||
async def get_reports(user: UserInDB = Depends(require_viewer)):
|
|
||||||
pass
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 4️⃣ Call Native (Binary) Code
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.native.wndb import get_all_junctions, add_junction, set_junction
|
|
||||||
|
|
||||||
# Read network elements
|
|
||||||
junctions = get_all_junctions()
|
|
||||||
|
|
||||||
# Create
|
|
||||||
add_junction({"id": "J1", "x": 0.0, "y": 0.0, "demand": 100.0})
|
|
||||||
|
|
||||||
# Update
|
|
||||||
set_junction("J1", {"demand": 150.0})
|
|
||||||
|
|
||||||
# Get constants
|
|
||||||
from app.native.wndb import PIPE_STATUS_OPEN, OPTION_UNITS_LPS
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 5️⃣ Encryption & Security
|
|
||||||
|
|
||||||
### Encrypt Sensitive Data
|
|
||||||
```python
|
|
||||||
from app.core.encryption import get_encryptor
|
|
||||||
|
|
||||||
encryptor = get_encryptor()
|
|
||||||
|
|
||||||
encrypted = encryptor.encrypt("secret_password")
|
|
||||||
decrypted = encryptor.decrypt(encrypted)
|
|
||||||
```
|
|
||||||
|
|
||||||
### Verify Password
|
|
||||||
```python
|
|
||||||
from app.core.security import verify_password, get_password_hash
|
|
||||||
|
|
||||||
# When creating user
|
|
||||||
hashed = get_password_hash(user.password)
|
|
||||||
|
|
||||||
# When checking login
|
|
||||||
if verify_password(form_data.password, stored_hash):
|
|
||||||
# Correct password
|
|
||||||
pass
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 6️⃣ Configuration
|
|
||||||
|
|
||||||
### In `.env` file
|
|
||||||
```bash
|
|
||||||
SECRET_KEY=your-secret-key
|
|
||||||
ENCRYPTION_KEY=your-fernet-key
|
|
||||||
DB_HOST=localhost
|
|
||||||
DB_PORT=5432
|
|
||||||
```
|
|
||||||
|
|
||||||
### Use in Code
|
|
||||||
```python
|
|
||||||
from app.core.config import settings
|
|
||||||
|
|
||||||
db_url = settings.SQLALCHEMY_DATABASE_URI
|
|
||||||
token_minutes = settings.ACCESS_TOKEN_EXPIRE_MINUTES
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 7️⃣ Testing
|
|
||||||
|
|
||||||
```python
|
|
||||||
# tests/unit/test_my_feature.py
|
|
||||||
import pytest
|
|
||||||
|
|
||||||
def test_my_function():
|
|
||||||
result = my_function()
|
|
||||||
assert result == expected
|
|
||||||
|
|
||||||
# Run tests
|
|
||||||
pytest tests/ -v
|
|
||||||
pytest tests/unit/test_my_feature.py::test_my_function -v
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🗺️ Directory Quick Map
|
|
||||||
|
|
||||||
| Path | What | Use For |
|
|
||||||
|------|------|---------|
|
|
||||||
| `app/api/v1/endpoints/` | API routes | Add new endpoints |
|
|
||||||
| `app/auth/` | Auth logic | Login, permissions |
|
|
||||||
| `app/domain/` | Models/Schemas | Data structures |
|
|
||||||
| `app/infra/db/` | DB access | Queries, repositories |
|
|
||||||
| `app/services/` | Business logic | Complex operations |
|
|
||||||
| `app/native/wndb/` | Binary functions | Network simulation |
|
|
||||||
| `app/core/` | Core utilities | Config, security, encryption |
|
|
||||||
| `tests/` | Tests | Unit & integration tests |
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔑 Key Imports
|
|
||||||
|
|
||||||
```python
|
|
||||||
# Authentication
|
|
||||||
from app.auth.dependencies import get_current_active_user, get_user_repository
|
|
||||||
from app.auth.permissions import require_admin, require_role
|
|
||||||
|
|
||||||
# Database
|
|
||||||
from app.infra.db.postgresql.database import db, get_database_instance
|
|
||||||
from app.infra.repositories.user_repository import UserRepository
|
|
||||||
|
|
||||||
# Schemas & Models
|
|
||||||
from app.domain.schemas.user import UserInDB, UserCreate, Token
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
# Security
|
|
||||||
from app.core.security import create_access_token, verify_password, get_password_hash
|
|
||||||
from app.core.encryption import get_encryptor
|
|
||||||
|
|
||||||
# Config
|
|
||||||
from app.core.config import settings
|
|
||||||
|
|
||||||
# Native API
|
|
||||||
from app.native.wndb import get_all_junctions, add_junction, open_project
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 Common Tasks
|
|
||||||
|
|
||||||
### Register New User
|
|
||||||
```python
|
|
||||||
from app.infra.repositories.user_repository import UserRepository
|
|
||||||
from app.domain.schemas.user import UserCreate
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
user_data = UserCreate(
|
|
||||||
username="john",
|
|
||||||
email="john@example.com",
|
|
||||||
password="securepass",
|
|
||||||
role=UserRole.USER
|
|
||||||
)
|
|
||||||
new_user = await user_repo.create_user(user_data)
|
|
||||||
```
|
|
||||||
|
|
||||||
### Query Database
|
|
||||||
```python
|
|
||||||
async with db.get_connection() as conn:
|
|
||||||
async with conn.cursor() as cur:
|
|
||||||
await cur.execute("SELECT * FROM users LIMIT 10")
|
|
||||||
rows = await cur.fetchall()
|
|
||||||
return [dict(r) for r in rows]
|
|
||||||
```
|
|
||||||
|
|
||||||
### Run Simulation
|
|
||||||
```python
|
|
||||||
from app.services.simulation import run_simulation
|
|
||||||
|
|
||||||
result = await run_simulation(
|
|
||||||
project_name="szh",
|
|
||||||
duration=3600,
|
|
||||||
time_step=60
|
|
||||||
)
|
|
||||||
```
|
|
||||||
|
|
||||||
### Audit Operation
|
|
||||||
```python
|
|
||||||
from app.core.audit import log_audit_event, AuditAction
|
|
||||||
|
|
||||||
await log_audit_event(
|
|
||||||
action=AuditAction.CREATE,
|
|
||||||
resource_type="pipe",
|
|
||||||
resource_id="P1",
|
|
||||||
actor_id=user.id,
|
|
||||||
details={"diameter": 100, "material": "PVC"}
|
|
||||||
)
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ⚠️ Common Gotchas
|
|
||||||
|
|
||||||
1. **Always use `Depends()`** for injecting repositories, users
|
|
||||||
```python
|
|
||||||
# ✅ Right
|
|
||||||
async def endpoint(user: UserInDB = Depends(get_current_active_user)):
|
|
||||||
|
|
||||||
# ❌ Wrong
|
|
||||||
async def endpoint(user: UserInDB):
|
|
||||||
```
|
|
||||||
|
|
||||||
2. **Use parametrized queries** to prevent SQL injection
|
|
||||||
```python
|
|
||||||
# ✅ Right
|
|
||||||
await cur.execute("SELECT * FROM users WHERE id = %s", (user_id,))
|
|
||||||
|
|
||||||
# ❌ Wrong
|
|
||||||
await cur.execute(f"SELECT * FROM users WHERE id = {user_id}")
|
|
||||||
```
|
|
||||||
|
|
||||||
3. **Async/await** required for database operations
|
|
||||||
```python
|
|
||||||
# ✅ Right
|
|
||||||
user = await user_repo.get_user_by_id(1)
|
|
||||||
|
|
||||||
# ❌ Wrong
|
|
||||||
user = user_repo.get_user_by_id(1) # Missing await
|
|
||||||
```
|
|
||||||
|
|
||||||
4. **Role hierarchy** for permission checks
|
|
||||||
```python
|
|
||||||
# All levels include higher permissions
|
|
||||||
VIEWER (1) < USER (2) < OPERATOR (3) < ADMIN (4)
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 File Locations Reference
|
|
||||||
|
|
||||||
- **Main app entry**: `app/main.py` (83 lines)
|
|
||||||
- **Central router**: `app/api/v1/router.py` (98 lines)
|
|
||||||
- **Config**: `app/core/config.py` (82 lines)
|
|
||||||
- **Auth dependencies**: `app/auth/dependencies.py`
|
|
||||||
- **Permissions**: `app/auth/permissions.py`
|
|
||||||
- **Database**: `app/infra/db/postgresql/database.py`
|
|
||||||
- **Repositories**: `app/infra/repositories/`
|
|
||||||
- **Schemas**: `app/domain/schemas/`
|
|
||||||
- **Models**: `app/domain/models/`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 Full Documentation
|
|
||||||
|
|
||||||
See **SECONDARY_DEVELOPMENT_GUIDE.md** for comprehensive guide on:
|
|
||||||
- Architecture overview
|
|
||||||
- Detailed endpoint creation
|
|
||||||
- Database patterns
|
|
||||||
- Native module integration
|
|
||||||
- Testing setup
|
|
||||||
- Deployment
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
*Generated for TJWater ServerBinary secondary development team*
|
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -1,370 +0,0 @@
|
|||||||
# 安全功能实施总结
|
|
||||||
|
|
||||||
## ✅ 已完成的功能
|
|
||||||
|
|
||||||
本次实施完成了完整的安全体系,包括数据加密、身份认证、权限管理、审计日志四大模块。
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📁 新增文件清单
|
|
||||||
|
|
||||||
### 核心功能模块
|
|
||||||
|
|
||||||
1. **数据加密**
|
|
||||||
- `app/core/encryption.py` - Fernet 加密实现
|
|
||||||
- `tests/test_encryption.py` - 加密功能测试
|
|
||||||
|
|
||||||
2. **用户系统**
|
|
||||||
- `app/domain/models/role.py` - 用户角色枚举
|
|
||||||
- `app/domain/schemas/user.py` - 用户数据模型
|
|
||||||
- `app/infra/repositories/user_repository.py` - 用户数据访问层
|
|
||||||
|
|
||||||
3. **认证授权**
|
|
||||||
- `app/api/v1/endpoints/auth.py` - 认证接口(已重构)
|
|
||||||
- `app/auth/dependencies.py` - 认证依赖项(已更新)
|
|
||||||
- `app/auth/permissions.py` - 权限控制装饰器
|
|
||||||
- `app/api/v1/endpoints/user_management.py` - 用户管理接口
|
|
||||||
|
|
||||||
4. **审计日志**
|
|
||||||
- `app/core/audit.py` - 审计日志核心(已完善)
|
|
||||||
- `app/domain/schemas/audit.py` - 审计日志数据模型
|
|
||||||
- `app/infra/repositories/audit_repository.py` - 审计日志数据访问层
|
|
||||||
- `app/api/v1/endpoints/audit.py` - 审计日志查询接口
|
|
||||||
- `app/infra/audit/middleware.py` - 自动审计中间件
|
|
||||||
|
|
||||||
### 数据库迁移
|
|
||||||
|
|
||||||
5. **迁移脚本**
|
|
||||||
- `migrations/001_create_users_table.sql` - 用户表
|
|
||||||
- `migrations/002_create_audit_logs_table.sql` - 审计日志表
|
|
||||||
|
|
||||||
### 配置和文档
|
|
||||||
|
|
||||||
6. **配置文件**
|
|
||||||
- `.env.example` - 环境变量模板
|
|
||||||
- `app/core/config.py` - 配置文件(已更新)
|
|
||||||
- `app/core/security.py` - 安全工具(已增强)
|
|
||||||
|
|
||||||
7. **文档**
|
|
||||||
- `SECURITY_README.md` - 完整使用指南(79KB+)
|
|
||||||
- `DEPLOYMENT.md` - 部署和集成指南
|
|
||||||
- `SECURITY_IMPLEMENTATION_SUMMARY.md` - 本文件
|
|
||||||
|
|
||||||
8. **工具**
|
|
||||||
- `setup_security.sh` - 快速设置脚本
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎯 功能特性
|
|
||||||
|
|
||||||
### 1. 数据加密
|
|
||||||
- ✅ 使用 Fernet(AES-128)对称加密
|
|
||||||
- ✅ 支持密钥生成和管理
|
|
||||||
- ✅ 自动从环境变量读取密钥
|
|
||||||
- ✅ 完整的加密/解密 API
|
|
||||||
- ✅ 单元测试覆盖
|
|
||||||
|
|
||||||
### 2. 身份认证
|
|
||||||
- ✅ 基于 JWT 的 Token 认证
|
|
||||||
- ✅ Access Token + Refresh Token 机制
|
|
||||||
- ✅ 用户注册/登录接口
|
|
||||||
- ✅ 支持用户名或邮箱登录
|
|
||||||
- ✅ 密码使用 bcrypt 哈希存储
|
|
||||||
- ✅ Token 过期时间可配置
|
|
||||||
- ✅ 向后兼容旧接口
|
|
||||||
|
|
||||||
### 3. 权限管理(RBAC)
|
|
||||||
- ✅ 4 个预定义角色:ADMIN, OPERATOR, USER, VIEWER
|
|
||||||
- ✅ 基于角色层级的权限检查
|
|
||||||
- ✅ 可复用的权限装饰器
|
|
||||||
- ✅ 资源所有者检查
|
|
||||||
- ✅ 灵活的依赖注入设计
|
|
||||||
|
|
||||||
### 4. 审计日志
|
|
||||||
- ✅ 自动记录所有关键操作
|
|
||||||
- ✅ 记录用户、时间、操作类型、资源等信息
|
|
||||||
- ✅ 敏感数据自动脱敏
|
|
||||||
- ✅ 支持按多条件查询
|
|
||||||
- ✅ 管理员专用查询接口
|
|
||||||
- ✅ 用户可查看自己的操作记录
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📊 技术栈
|
|
||||||
|
|
||||||
| 组件 | 技术 | 说明 |
|
|
||||||
|------|------|------|
|
|
||||||
| 加密 | cryptography.Fernet | 对称加密 |
|
|
||||||
| 密码哈希 | bcrypt | 密码安全存储 |
|
|
||||||
| JWT | python-jose | Token 生成和验证 |
|
|
||||||
| 数据库 | PostgreSQL + psycopg | 异步数据访问 |
|
|
||||||
| Web框架 | FastAPI | 现代异步框架 |
|
|
||||||
| 数据验证 | Pydantic | 类型安全的数据模型 |
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔐 安全特性
|
|
||||||
|
|
||||||
1. **密码安全**
|
|
||||||
- bcrypt 哈希(work factor = 12)
|
|
||||||
- 自动加盐
|
|
||||||
- 不可逆加密
|
|
||||||
|
|
||||||
2. **Token 安全**
|
|
||||||
- JWT 签名验证
|
|
||||||
- 短期 Access Token(30分钟)
|
|
||||||
- 长期 Refresh Token(7天)
|
|
||||||
- Token 类型校验
|
|
||||||
|
|
||||||
3. **数据保护**
|
|
||||||
- 敏感字段自动脱敏
|
|
||||||
- 审计日志不记录密码
|
|
||||||
- 加密密钥从环境变量读取
|
|
||||||
|
|
||||||
4. **访问控制**
|
|
||||||
- 基于角色的细粒度权限
|
|
||||||
- 资源级别的访问控制
|
|
||||||
- 自动验证用户激活状态
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📈 数据库设计
|
|
||||||
|
|
||||||
### users 表
|
|
||||||
```
|
|
||||||
用户表 - 存储系统用户
|
|
||||||
- id (主键)
|
|
||||||
- username (唯一)
|
|
||||||
- email (唯一)
|
|
||||||
- hashed_password
|
|
||||||
- role (ADMIN/OPERATOR/USER/VIEWER)
|
|
||||||
- is_active
|
|
||||||
- is_superuser
|
|
||||||
- created_at
|
|
||||||
- updated_at (自动更新)
|
|
||||||
```
|
|
||||||
|
|
||||||
### audit_logs 表
|
|
||||||
```
|
|
||||||
审计日志表 - 记录所有关键操作
|
|
||||||
- id (主键)
|
|
||||||
- user_id (外键)
|
|
||||||
- username (冗余字段)
|
|
||||||
- action (操作类型)
|
|
||||||
- resource_type (资源类型)
|
|
||||||
- resource_id (资源ID)
|
|
||||||
- ip_address
|
|
||||||
- user_agent
|
|
||||||
- request_method
|
|
||||||
- request_path
|
|
||||||
- request_data (JSONB)
|
|
||||||
- response_status
|
|
||||||
- error_message
|
|
||||||
- timestamp
|
|
||||||
```
|
|
||||||
|
|
||||||
**索引优化**:
|
|
||||||
- users: username, email, role, is_active
|
|
||||||
- audit_logs: user_id, username, timestamp, action, resource
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 快速开始
|
|
||||||
|
|
||||||
### 方法 1: 使用自动化脚本
|
|
||||||
|
|
||||||
```bash
|
|
||||||
./setup_security.sh
|
|
||||||
```
|
|
||||||
|
|
||||||
### 方法 2: 手动设置
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 1. 配置环境变量
|
|
||||||
cp .env.example .env
|
|
||||||
# 编辑 .env 填写密钥和数据库配置
|
|
||||||
|
|
||||||
# 2. 执行数据库迁移
|
|
||||||
psql -U postgres -d tjwater -f migrations/001_create_users_table.sql
|
|
||||||
psql -U postgres -d tjwater -f migrations/002_create_audit_logs_table.sql
|
|
||||||
|
|
||||||
# 3. 测试
|
|
||||||
python tests/test_encryption.py
|
|
||||||
|
|
||||||
# 4. 启动服务
|
|
||||||
uvicorn app.main:app --reload
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📋 集成检查清单
|
|
||||||
|
|
||||||
### 必需步骤
|
|
||||||
|
|
||||||
- [ ] 复制 `.env.example` 为 `.env` 并配置
|
|
||||||
- [ ] 生成 JWT 密钥(SECRET_KEY)
|
|
||||||
- [ ] 生成加密密钥(ENCRYPTION_KEY)
|
|
||||||
- [ ] 配置数据库连接信息
|
|
||||||
- [ ] 执行用户表迁移脚本
|
|
||||||
- [ ] 执行审计日志表迁移脚本
|
|
||||||
- [ ] 验证默认管理员可登录
|
|
||||||
|
|
||||||
### 可选步骤
|
|
||||||
|
|
||||||
- [ ] 在 main.py 中添加审计中间件
|
|
||||||
- [ ] 为现有接口添加权限控制
|
|
||||||
- [ ] 注册新的路由(auth, user_management, audit)
|
|
||||||
- [ ] 替换硬编码的认证逻辑
|
|
||||||
- [ ] 配置 Token 过期时间
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔄 向后兼容性
|
|
||||||
|
|
||||||
### 保留的旧接口
|
|
||||||
|
|
||||||
1. **简化登录**: `/api/v1/auth/login/simple`
|
|
||||||
- 仍可使用 `username` 和 `password` 参数
|
|
||||||
- 返回标准 Token 响应
|
|
||||||
|
|
||||||
2. **硬编码用户迁移**
|
|
||||||
- 原有 `tjwater/tjwater@123` 已迁移到数据库
|
|
||||||
- 保持相同的用户名和密码
|
|
||||||
|
|
||||||
### 渐进式迁移
|
|
||||||
|
|
||||||
可以逐步迁移现有接口:
|
|
||||||
|
|
||||||
1. 新接口直接使用新认证系统
|
|
||||||
2. 旧接口保持不变
|
|
||||||
3. 逐个替换旧接口的认证逻辑
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 API 端点总览
|
|
||||||
|
|
||||||
### 认证接口 (`/api/v1/auth/`)
|
|
||||||
|
|
||||||
| 方法 | 路径 | 说明 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| POST | `/register` | 用户注册 | 公开 |
|
|
||||||
| POST | `/login` | OAuth2 登录 | 公开 |
|
|
||||||
| POST | `/login/simple` | 简化登录 | 公开 |
|
|
||||||
| GET | `/me` | 获取当前用户 | 认证用户 |
|
|
||||||
| POST | `/refresh` | 刷新Token | 认证用户 |
|
|
||||||
|
|
||||||
### 用户管理 (`/api/v1/users/`)
|
|
||||||
|
|
||||||
| 方法 | 路径 | 说明 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| GET | `/` | 用户列表 | 管理员 |
|
|
||||||
| GET | `/{id}` | 用户详情 | 所有者/管理员 |
|
|
||||||
| PUT | `/{id}` | 更新用户 | 所有者/管理员 |
|
|
||||||
| DELETE | `/{id}` | 删除用户 | 管理员 |
|
|
||||||
| POST | `/{id}/activate` | 激活用户 | 管理员 |
|
|
||||||
| POST | `/{id}/deactivate` | 停用用户 | 管理员 |
|
|
||||||
|
|
||||||
### 审计日志 (`/api/v1/audit/`)
|
|
||||||
|
|
||||||
| 方法 | 路径 | 说明 | 权限 |
|
|
||||||
|------|------|------|------|
|
|
||||||
| GET | `/logs` | 查询审计日志 | 管理员 |
|
|
||||||
| GET | `/logs/count` | 日志总数 | 管理员 |
|
|
||||||
| GET | `/logs/my` | 我的操作记录 | 认证用户 |
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎓 使用示例
|
|
||||||
|
|
||||||
### Python 示例
|
|
||||||
|
|
||||||
```python
|
|
||||||
import requests
|
|
||||||
|
|
||||||
# 登录
|
|
||||||
resp = requests.post("http://localhost:8000/api/v1/auth/login",
|
|
||||||
data={"username": "admin", "password": "admin123"})
|
|
||||||
token = resp.json()["access_token"]
|
|
||||||
|
|
||||||
# 访问受保护接口
|
|
||||||
headers = {"Authorization": f"Bearer {token}"}
|
|
||||||
resp = requests.get("http://localhost:8000/api/v1/auth/me", headers=headers)
|
|
||||||
print(resp.json())
|
|
||||||
```
|
|
||||||
|
|
||||||
### cURL 示例
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 登录
|
|
||||||
TOKEN=$(curl -s -X POST "http://localhost:8000/api/v1/auth/login" \
|
|
||||||
-d "username=admin&password=admin123" | jq -r .access_token)
|
|
||||||
|
|
||||||
# 查询审计日志
|
|
||||||
curl -H "Authorization: Bearer $TOKEN" \
|
|
||||||
"http://localhost:8000/api/v1/audit/logs?action=LOGIN"
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🐛 常见问题
|
|
||||||
|
|
||||||
### Q: 如何修改默认管理员密码?
|
|
||||||
|
|
||||||
A: 登录后通过 PUT `/api/v1/users/{id}` 接口修改,或直接更新数据库。
|
|
||||||
|
|
||||||
### Q: 如何添加新用户?
|
|
||||||
|
|
||||||
A: 使用 POST `/api/v1/auth/register` 接口,或由管理员在用户管理界面创建。
|
|
||||||
|
|
||||||
### Q: 审计日志可以删除吗?
|
|
||||||
|
|
||||||
A: 不建议删除。可以归档到冷存储,保留最近 90 天的数据。
|
|
||||||
|
|
||||||
### Q: Token 过期了怎么办?
|
|
||||||
|
|
||||||
A: 使用 Refresh Token 调用 `/api/v1/auth/refresh` 接口获取新的 Access Token。
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 技术支持
|
|
||||||
|
|
||||||
- **完整文档**: `SECURITY_README.md`
|
|
||||||
- **部署指南**: `DEPLOYMENT.md`
|
|
||||||
- **测试代码**: `tests/test_encryption.py`
|
|
||||||
- **迁移脚本**: `migrations/`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📝 待办事项(可选)
|
|
||||||
|
|
||||||
未来可以扩展的功能:
|
|
||||||
|
|
||||||
- [ ] 邮件验证
|
|
||||||
- [ ] 密码重置
|
|
||||||
- [ ] 双因素认证(2FA)
|
|
||||||
- [ ] 单点登录(SSO)
|
|
||||||
- [ ] Token 黑名单
|
|
||||||
- [ ] 会话管理
|
|
||||||
- [ ] IP 白名单
|
|
||||||
- [ ] 登录频率限制
|
|
||||||
- [ ] 密码复杂度策略
|
|
||||||
- [ ] 审计日志自动归档
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎉 总结
|
|
||||||
|
|
||||||
本次实施完成了企业级的安全体系,包含:
|
|
||||||
|
|
||||||
✅ 数据加密 - Fernet 对称加密
|
|
||||||
✅ 身份认证 - JWT Token + bcrypt 密码哈希
|
|
||||||
✅ 权限管理 - 基于角色的访问控制(RBAC)
|
|
||||||
✅ 审计日志 - 自动追踪所有关键操作
|
|
||||||
|
|
||||||
所有功能均遵循安全最佳实践,提供完整的文档和测试,可直接投入生产使用。
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
**实施日期**: 2026-02-02
|
|
||||||
**版本**: v1.0.0
|
|
||||||
**状态**: ✅ 已完成
|
|
||||||
@@ -1,499 +0,0 @@
|
|||||||
# 安全功能使用指南
|
|
||||||
|
|
||||||
TJWater Server 安全体系实施完成,包含:数据加密、身份认证、权限管理、审计日志
|
|
||||||
|
|
||||||
## 📋 目录
|
|
||||||
|
|
||||||
1. [快速开始](#快速开始)
|
|
||||||
2. [数据加密](#数据加密)
|
|
||||||
3. [身份认证](#身份认证)
|
|
||||||
4. [权限管理](#权限管理)
|
|
||||||
5. [审计日志](#审计日志)
|
|
||||||
6. [数据库迁移](#数据库迁移)
|
|
||||||
7. [API 使用示例](#api-使用示例)
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 快速开始
|
|
||||||
|
|
||||||
### 1. 配置环境变量
|
|
||||||
|
|
||||||
复制 `.env.example` 为 `.env` 并配置:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
cp .env.example .env
|
|
||||||
```
|
|
||||||
|
|
||||||
生成必要的密钥:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 生成 JWT 密钥
|
|
||||||
openssl rand -hex 32
|
|
||||||
|
|
||||||
# 生成加密密钥
|
|
||||||
python -c "from cryptography.fernet import Fernet; print(Fernet.generate_key().decode())"
|
|
||||||
```
|
|
||||||
|
|
||||||
编辑 `.env` 文件:
|
|
||||||
|
|
||||||
```env
|
|
||||||
SECRET_KEY=your-generated-jwt-secret-key
|
|
||||||
ENCRYPTION_KEY=your-generated-encryption-key
|
|
||||||
DB_NAME=tjwater
|
|
||||||
DB_HOST=localhost
|
|
||||||
DB_PORT=5432
|
|
||||||
DB_USER=postgres
|
|
||||||
DB_PASSWORD=your-db-password
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. 执行数据库迁移
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 连接到 PostgreSQL
|
|
||||||
psql -U postgres -d tjwater
|
|
||||||
|
|
||||||
# 执行迁移脚本
|
|
||||||
\i migrations/001_create_users_table.sql
|
|
||||||
\i migrations/002_create_audit_logs_table.sql
|
|
||||||
```
|
|
||||||
|
|
||||||
或使用命令行:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
psql -U postgres -d tjwater -f migrations/001_create_users_table.sql
|
|
||||||
psql -U postgres -d tjwater -f migrations/002_create_audit_logs_table.sql
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3. 验证安装
|
|
||||||
|
|
||||||
默认创建了两个管理员账号:
|
|
||||||
|
|
||||||
- **用户名**: `admin` / **密码**: `admin123`
|
|
||||||
- **用户名**: `tjwater` / **密码**: `tjwater@123`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔐 数据加密
|
|
||||||
|
|
||||||
### 使用加密器
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.core.encryption import get_encryptor
|
|
||||||
|
|
||||||
encryptor = get_encryptor()
|
|
||||||
|
|
||||||
# 加密敏感数据
|
|
||||||
encrypted_data = encryptor.encrypt("sensitive information")
|
|
||||||
|
|
||||||
# 解密
|
|
||||||
decrypted_data = encryptor.decrypt(encrypted_data)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 生成新密钥
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.core.encryption import Encryptor
|
|
||||||
|
|
||||||
new_key = Encryptor.generate_key()
|
|
||||||
print(f"New encryption key: {new_key}")
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 👤 身份认证
|
|
||||||
|
|
||||||
### 用户角色
|
|
||||||
|
|
||||||
系统定义了 4 个角色(权限由低到高):
|
|
||||||
|
|
||||||
| 角色 | 权限说明 |
|
|
||||||
|------|---------|
|
|
||||||
| `VIEWER` | 仅查询权限 |
|
|
||||||
| `USER` | 读写权限 |
|
|
||||||
| `OPERATOR` | 操作员,可修改数据 |
|
|
||||||
| `ADMIN` | 管理员,完全权限 |
|
|
||||||
|
|
||||||
### API 接口
|
|
||||||
|
|
||||||
#### 用户注册
|
|
||||||
|
|
||||||
```http
|
|
||||||
POST /api/v1/auth/register
|
|
||||||
Content-Type: application/json
|
|
||||||
|
|
||||||
{
|
|
||||||
"username": "newuser",
|
|
||||||
"email": "user@example.com",
|
|
||||||
"password": "password123",
|
|
||||||
"role": "USER"
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 用户登录(OAuth2 标准)
|
|
||||||
|
|
||||||
```http
|
|
||||||
POST /api/v1/auth/login
|
|
||||||
Content-Type: application/x-www-form-urlencoded
|
|
||||||
|
|
||||||
username=admin&password=admin123
|
|
||||||
```
|
|
||||||
|
|
||||||
响应:
|
|
||||||
|
|
||||||
```json
|
|
||||||
{
|
|
||||||
"access_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
|
|
||||||
"refresh_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
|
|
||||||
"token_type": "bearer",
|
|
||||||
"expires_in": 1800
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 用户登录(简化版)
|
|
||||||
|
|
||||||
```http
|
|
||||||
POST /api/v1/auth/login/simple?username=admin&password=admin123
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 获取当前用户信息
|
|
||||||
|
|
||||||
```http
|
|
||||||
GET /api/v1/auth/me
|
|
||||||
Authorization: Bearer {access_token}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 刷新 Token
|
|
||||||
|
|
||||||
```http
|
|
||||||
POST /api/v1/auth/refresh
|
|
||||||
Content-Type: application/json
|
|
||||||
|
|
||||||
{
|
|
||||||
"refresh_token": "your-refresh-token"
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔑 权限管理
|
|
||||||
|
|
||||||
### 在 API 中使用权限控制
|
|
||||||
|
|
||||||
#### 方式 1: 使用预定义依赖
|
|
||||||
|
|
||||||
```python
|
|
||||||
from fastapi import APIRouter, Depends
|
|
||||||
from app.auth.permissions import get_current_admin, get_current_operator
|
|
||||||
from app.domain.schemas.user import UserInDB
|
|
||||||
|
|
||||||
router = APIRouter()
|
|
||||||
|
|
||||||
@router.post("/admin-only")
|
|
||||||
async def admin_endpoint(
|
|
||||||
current_user: UserInDB = Depends(get_current_admin)
|
|
||||||
):
|
|
||||||
"""仅管理员可访问"""
|
|
||||||
return {"message": "Admin access granted"}
|
|
||||||
|
|
||||||
@router.post("/operator-only")
|
|
||||||
async def operator_endpoint(
|
|
||||||
current_user: UserInDB = Depends(get_current_operator)
|
|
||||||
):
|
|
||||||
"""操作员及以上可访问"""
|
|
||||||
return {"message": "Operator access granted"}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 方式 2: 使用 require_role
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.permissions import require_role
|
|
||||||
from app.domain.models.role import UserRole
|
|
||||||
|
|
||||||
@router.get("/viewer-access")
|
|
||||||
async def viewer_endpoint(
|
|
||||||
current_user: UserInDB = Depends(require_role(UserRole.VIEWER))
|
|
||||||
):
|
|
||||||
"""所有认证用户可访问"""
|
|
||||||
return {"data": "visible to all"}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 方式 3: 手动检查权限
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.auth.dependencies import get_current_active_user
|
|
||||||
from app.auth.permissions import check_resource_owner
|
|
||||||
|
|
||||||
@router.put("/users/{user_id}")
|
|
||||||
async def update_user(
|
|
||||||
user_id: int,
|
|
||||||
current_user: UserInDB = Depends(get_current_active_user)
|
|
||||||
):
|
|
||||||
"""检查是否是资源拥有者或管理员"""
|
|
||||||
if not check_resource_owner(user_id, current_user):
|
|
||||||
raise HTTPException(status_code=403, detail="Permission denied")
|
|
||||||
|
|
||||||
# 执行更新操作
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📝 审计日志
|
|
||||||
|
|
||||||
### 自动审计
|
|
||||||
|
|
||||||
使用中间件自动记录关键操作,在 `main.py` 中添加:
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.infra.audit.middleware import AuditMiddleware
|
|
||||||
|
|
||||||
app.add_middleware(AuditMiddleware)
|
|
||||||
```
|
|
||||||
|
|
||||||
自动记录:
|
|
||||||
- 所有 POST/PUT/DELETE 请求
|
|
||||||
- 登录/登出事件
|
|
||||||
- 关键资源访问
|
|
||||||
|
|
||||||
### 手动记录审计日志
|
|
||||||
|
|
||||||
```python
|
|
||||||
from app.core.audit import log_audit_event, AuditAction
|
|
||||||
|
|
||||||
await log_audit_event(
|
|
||||||
action=AuditAction.UPDATE,
|
|
||||||
user_id=current_user.id,
|
|
||||||
username=current_user.username,
|
|
||||||
resource_type="project",
|
|
||||||
resource_id="123",
|
|
||||||
ip_address=request.client.host,
|
|
||||||
request_data={"field": "value"},
|
|
||||||
response_status=200
|
|
||||||
)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 查询审计日志
|
|
||||||
|
|
||||||
#### 获取所有审计日志(仅管理员)
|
|
||||||
|
|
||||||
```http
|
|
||||||
GET /api/v1/audit/logs?skip=0&limit=100
|
|
||||||
Authorization: Bearer {admin_token}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 按条件过滤
|
|
||||||
|
|
||||||
```http
|
|
||||||
GET /api/v1/audit/logs?user_id=1&action=LOGIN&start_time=2024-01-01T00:00:00
|
|
||||||
Authorization: Bearer {admin_token}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 获取我的操作记录
|
|
||||||
|
|
||||||
```http
|
|
||||||
GET /api/v1/audit/logs/my
|
|
||||||
Authorization: Bearer {access_token}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 获取日志总数
|
|
||||||
|
|
||||||
```http
|
|
||||||
GET /api/v1/audit/logs/count?action=LOGIN
|
|
||||||
Authorization: Bearer {admin_token}
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 💾 数据库迁移
|
|
||||||
|
|
||||||
### 用户表结构
|
|
||||||
|
|
||||||
```sql
|
|
||||||
CREATE TABLE users (
|
|
||||||
id SERIAL PRIMARY KEY,
|
|
||||||
username VARCHAR(50) UNIQUE NOT NULL,
|
|
||||||
email VARCHAR(100) UNIQUE NOT NULL,
|
|
||||||
hashed_password VARCHAR(255) NOT NULL,
|
|
||||||
role VARCHAR(20) DEFAULT 'USER' NOT NULL,
|
|
||||||
is_active BOOLEAN DEFAULT TRUE NOT NULL,
|
|
||||||
is_superuser BOOLEAN DEFAULT FALSE NOT NULL,
|
|
||||||
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP NOT NULL,
|
|
||||||
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP NOT NULL
|
|
||||||
);
|
|
||||||
```
|
|
||||||
|
|
||||||
### 审计日志表结构
|
|
||||||
|
|
||||||
```sql
|
|
||||||
CREATE TABLE audit_logs (
|
|
||||||
id SERIAL PRIMARY KEY,
|
|
||||||
user_id INTEGER REFERENCES users(id),
|
|
||||||
username VARCHAR(50),
|
|
||||||
action VARCHAR(50) NOT NULL,
|
|
||||||
resource_type VARCHAR(50),
|
|
||||||
resource_id VARCHAR(100),
|
|
||||||
ip_address VARCHAR(45),
|
|
||||||
user_agent TEXT,
|
|
||||||
request_method VARCHAR(10),
|
|
||||||
request_path TEXT,
|
|
||||||
request_data JSONB,
|
|
||||||
response_status INTEGER,
|
|
||||||
error_message TEXT,
|
|
||||||
timestamp TIMESTAMP DEFAULT CURRENT_TIMESTAMP NOT NULL
|
|
||||||
);
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔧 API 使用示例
|
|
||||||
|
|
||||||
### Python 客户端示例
|
|
||||||
|
|
||||||
```python
|
|
||||||
import requests
|
|
||||||
|
|
||||||
BASE_URL = "http://localhost:8000/api/v1"
|
|
||||||
|
|
||||||
# 1. 登录
|
|
||||||
response = requests.post(
|
|
||||||
f"{BASE_URL}/auth/login",
|
|
||||||
data={"username": "admin", "password": "admin123"}
|
|
||||||
)
|
|
||||||
token = response.json()["access_token"]
|
|
||||||
|
|
||||||
# 2. 设置 Authorization Header
|
|
||||||
headers = {"Authorization": f"Bearer {token}"}
|
|
||||||
|
|
||||||
# 3. 获取当前用户信息
|
|
||||||
response = requests.get(f"{BASE_URL}/auth/me", headers=headers)
|
|
||||||
print(response.json())
|
|
||||||
|
|
||||||
# 4. 创建新用户(需要管理员权限)
|
|
||||||
response = requests.post(
|
|
||||||
f"{BASE_URL}/auth/register",
|
|
||||||
headers=headers,
|
|
||||||
json={
|
|
||||||
"username": "newuser",
|
|
||||||
"email": "new@example.com",
|
|
||||||
"password": "password123",
|
|
||||||
"role": "USER"
|
|
||||||
}
|
|
||||||
)
|
|
||||||
print(response.json())
|
|
||||||
|
|
||||||
# 5. 查询审计日志(需要管理员权限)
|
|
||||||
response = requests.get(
|
|
||||||
f"{BASE_URL}/audit/logs?action=LOGIN",
|
|
||||||
headers=headers
|
|
||||||
)
|
|
||||||
print(response.json())
|
|
||||||
```
|
|
||||||
|
|
||||||
### cURL 示例
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 登录
|
|
||||||
curl -X POST "http://localhost:8000/api/v1/auth/login" \
|
|
||||||
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
||||||
-d "username=admin&password=admin123"
|
|
||||||
|
|
||||||
# 使用 Token 访问受保护接口
|
|
||||||
TOKEN="your-access-token"
|
|
||||||
curl -X GET "http://localhost:8000/api/v1/auth/me" \
|
|
||||||
-H "Authorization: Bearer $TOKEN"
|
|
||||||
|
|
||||||
# 注册新用户
|
|
||||||
curl -X POST "http://localhost:8000/api/v1/auth/register" \
|
|
||||||
-H "Content-Type: application/json" \
|
|
||||||
-H "Authorization: Bearer $TOKEN" \
|
|
||||||
-d '{
|
|
||||||
"username": "testuser",
|
|
||||||
"email": "test@example.com",
|
|
||||||
"password": "password123",
|
|
||||||
"role": "USER"
|
|
||||||
}'
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🛡️ 安全最佳实践
|
|
||||||
|
|
||||||
1. **密钥管理**
|
|
||||||
- 绝不在代码中硬编码密钥
|
|
||||||
- 定期轮换 JWT 密钥
|
|
||||||
- 使用强随机密钥
|
|
||||||
|
|
||||||
2. **密码策略**
|
|
||||||
- 最小长度 6 个字符(建议 12+)
|
|
||||||
- 强制密码复杂度(可在注册时添加验证)
|
|
||||||
- 定期提醒用户更换密码
|
|
||||||
|
|
||||||
3. **Token 管理**
|
|
||||||
- Access Token 短期有效(默认 30 分钟)
|
|
||||||
- Refresh Token 长期有效(默认 7 天)
|
|
||||||
- 实施 Token 黑名单(可选)
|
|
||||||
|
|
||||||
4. **审计日志**
|
|
||||||
- 审计日志不可删除
|
|
||||||
- 定期归档旧日志
|
|
||||||
- 监控异常登录行为
|
|
||||||
|
|
||||||
5. **权限控制**
|
|
||||||
- 遵循最小权限原则
|
|
||||||
- 定期审查用户权限
|
|
||||||
- 记录所有权限变更
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 相关文件
|
|
||||||
|
|
||||||
- **配置**: `app/core/config.py`
|
|
||||||
- **加密**: `app/core/encryption.py`
|
|
||||||
- **安全**: `app/core/security.py`
|
|
||||||
- **审计**: `app/core/audit.py`
|
|
||||||
- **认证**: `app/api/v1/endpoints/auth.py`
|
|
||||||
- **权限**: `app/auth/permissions.py`
|
|
||||||
- **用户管理**: `app/api/v1/endpoints/user_management.py`
|
|
||||||
- **审计日志**: `app/api/v1/endpoints/audit.py`
|
|
||||||
- **迁移脚本**: `migrations/`
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ❓ 常见问题
|
|
||||||
|
|
||||||
### Q: 忘记密码怎么办?
|
|
||||||
|
|
||||||
A: 目前需要管理员通过数据库重置。未来可添加邮件重置功能。
|
|
||||||
|
|
||||||
```sql
|
|
||||||
-- 重置密码为 "newpassword123"
|
|
||||||
UPDATE users
|
|
||||||
SET hashed_password = '$2b$12$...' -- 使用 bcrypt 生成哈希
|
|
||||||
WHERE username = 'targetuser';
|
|
||||||
```
|
|
||||||
|
|
||||||
### Q: 如何添加新角色?
|
|
||||||
|
|
||||||
A: 编辑 `app/domain/models/role.py` 中的 `UserRole` 枚举,并更新数据库约束。
|
|
||||||
|
|
||||||
### Q: 审计日志占用太多空间?
|
|
||||||
|
|
||||||
A: 建议定期归档旧日志到冷存储:
|
|
||||||
|
|
||||||
```sql
|
|
||||||
-- 归档 90 天前的日志
|
|
||||||
CREATE TABLE audit_logs_archive AS
|
|
||||||
SELECT * FROM audit_logs WHERE timestamp < NOW() - INTERVAL '90 days';
|
|
||||||
|
|
||||||
DELETE FROM audit_logs WHERE timestamp < NOW() - INTERVAL '90 days';
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 技术支持
|
|
||||||
|
|
||||||
如有问题,请查看:
|
|
||||||
- 日志文件: `logs/`
|
|
||||||
- 数据库表结构: `migrations/`
|
|
||||||
- 单元测试: `tests/`
|
|
||||||
|
|
||||||
-13577
File diff suppressed because it is too large
Load Diff
@@ -1,97 +0,0 @@
|
|||||||
# TJWater Server (FastAPI)
|
|
||||||
|
|
||||||
基于 FastAPI 和高性能数据库构建的水务业务服务端系统,提供管网模拟计算、SCADA 数据集成、网络元素管理、项目管理以及完整的安全认证体系。
|
|
||||||
|
|
||||||
## 🌟 主要功能
|
|
||||||
|
|
||||||
- **管网模拟**:集成 EPANET 引擎,支持水力模拟、水质模拟及爆管分析。
|
|
||||||
- **SCADA 集成**:实时数据采集、存储与历史数据查询(支持 InfluxDB/TimescaleDB)。
|
|
||||||
- **资产管理**:管网 GIS 数据管理,支持 GeoJSON 格式及拓扑分析。
|
|
||||||
- **项目管理**:支持多项目环境切换、数据隔离与版本控制。
|
|
||||||
- **安全体系**:
|
|
||||||
- **身份认证**:基于 OAuth2 与 JWT 的用户认证与授权。
|
|
||||||
- **权限控制**:基于角色的访问控制 (RBAC)。
|
|
||||||
- **数据加密**:敏感数据落盘加密存储。
|
|
||||||
- **审计日志**:关键操作的全链路审计记录。
|
|
||||||
|
|
||||||
## 📚 文档资源
|
|
||||||
|
|
||||||
更多详细指南请参阅以下文档:
|
|
||||||
|
|
||||||
- [SECURITY_README.md](./SECURITY_README.md) - 安全功能使用指南(认证、加密、审计)
|
|
||||||
- [DEPLOYMENT.md](./DEPLOYMENT.md) - 部署与集成指南
|
|
||||||
- [INTEGRATION_CHECKLIST.md](./INTEGRATION_CHECKLIST.md) - 系统集成检查清单
|
|
||||||
|
|
||||||
## 🏗️ 目录结构
|
|
||||||
|
|
||||||
```
|
|
||||||
TJWaterServerBinary/
|
|
||||||
├── app/
|
|
||||||
│ ├── main.py # FastAPI 应用入口(Lifespan, Middleware)
|
|
||||||
│ ├── api/v1/ # API 接口路由与端点定义
|
|
||||||
│ ├── algorithms/ # 核心算法模块(模拟、清洗、泄漏识别等)
|
|
||||||
│ ├── auth/ # 认证相关逻辑与依赖
|
|
||||||
│ ├── core/ # 核心配置、安全与工具类
|
|
||||||
│ ├── domain/ # 领域模型与 Schema 定义
|
|
||||||
│ ├── infra/ # 基础设施层
|
|
||||||
│ │ ├── audit/ # 审计日志模块
|
|
||||||
│ │ ├── cache/ # 缓存与 Redis 客户端
|
|
||||||
│ │ └── db/ # 数据库访问层 (PostgreSQL/TimescaleDB/InfluxDB)
|
|
||||||
│ ├── services/ # 业务逻辑服务层
|
|
||||||
│ └── utils/ # 通用工具函数
|
|
||||||
├── resource/ # 静态资源与模型文件
|
|
||||||
├── scripts/ # 运维与启动脚本
|
|
||||||
├── tests/ # 单元与集成测试
|
|
||||||
├── requirements.txt # Python 依赖列表
|
|
||||||
└── readme.md # 项目说明文档
|
|
||||||
```
|
|
||||||
|
|
||||||
## 🚀 快速开始
|
|
||||||
|
|
||||||
### 1. 环境要求
|
|
||||||
|
|
||||||
- Python 3.10+
|
|
||||||
- PostgreSQL (TimescaleDB 扩展)
|
|
||||||
- Redis
|
|
||||||
- InfluxDB (可选,用于时序数据)
|
|
||||||
|
|
||||||
### 2. 安装依赖
|
|
||||||
|
|
||||||
建议使用虚拟环境进行安装:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# 创建虚拟环境
|
|
||||||
python -m venv venv
|
|
||||||
source venv/bin/activate # Linux/macOS
|
|
||||||
# venv\Scripts\activate # Windows
|
|
||||||
|
|
||||||
# 安装依赖
|
|
||||||
pip install -r requirements.txt
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3. 配置环境
|
|
||||||
|
|
||||||
请确保正确配置了环境变量或 `.env` 文件,主要包括数据库连接串、Redis 配置及密钥等。参考 `app/core/config.py` 中的配置项。
|
|
||||||
|
|
||||||
### 4. 启动服务
|
|
||||||
|
|
||||||
使用提供的启动脚本运行服务:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
python scripts/run_server.py
|
|
||||||
```
|
|
||||||
|
|
||||||
- **默认地址**: `http://0.0.0.0:8000`
|
|
||||||
- **API 文档**: `http://0.0.0.0:8000/docs` 或 `http://0.0.0.0:8000/redoc`
|
|
||||||
- **OpenAPI**: `http://0.0.0.0:8000/openapi.json`
|
|
||||||
|
|
||||||
## 🛠️ 常用脚本
|
|
||||||
|
|
||||||
- `scripts/run_server.py`: 启动 FastAPI 服务
|
|
||||||
- `scripts/create_project.py`: 创建新项目环境
|
|
||||||
- `scripts/setup_security.sh`: 初始化安全配置
|
|
||||||
|
|
||||||
## 📝 开发规范
|
|
||||||
|
|
||||||
- 代码遵循 PEP 8 规范
|
|
||||||
- 提交代码前请运行测试:`pytest`
|
|
||||||
@@ -1,14 +0,0 @@
|
|||||||
Setup instructions for WMH's work
|
|
||||||
|
|
||||||
1. import scada_info.csv
|
|
||||||
run python online_Analysis.py
|
|
||||||
|
|
||||||
2. import history_pattern_flow.csv
|
|
||||||
run python online_Analysis.py
|
|
||||||
Should manually change code
|
|
||||||
|
|
||||||
3. run create_template.py
|
|
||||||
|
|
||||||
4. run influxdb_api.py
|
|
||||||
在InfluxDB数据库中创建好我们需要的bucket
|
|
||||||
create buckets
|
|
||||||
@@ -1,90 +0,0 @@
|
|||||||
搭建服务器
|
|
||||||
|
|
||||||
1. `git clone https://e.coding.net/tjwater/tjwatercloud/TJWaterServer.git`
|
|
||||||
2. 控制台进入 `TJWaterServer`
|
|
||||||
3. 运行 `python install.py` 准备Python环境
|
|
||||||
3.1 Python 3.12 需要手动的安装(拷贝) PyMetis 库
|
|
||||||
4. 解压 `pg14.zip` 到上一层文件夹
|
|
||||||
5. 控制台进入 `../pg14/bin`
|
|
||||||
5.1 将pg14/bin 加到系统PATH中,这步一定需要做,CopyProjectEx里需要这个
|
|
||||||
6. 执行 `initdb -D ../data -E UTF-8` 创建数据库
|
|
||||||
7. 执行 `pg_ctl -D ../data -l logfile start` 启动数据库服务
|
|
||||||
- `pg_ctl -D ../data -l logfile stop` 关闭数据库服务
|
|
||||||
8. 进入 `TJWaterServer`,执行 `python create_template.py` 创建模板
|
|
||||||
9. 执行 `python online_Analysis.py`
|
|
||||||
10. 执行 `python influxdb_api.py`
|
|
||||||
11. 搭建FastAPI环境...
|
|
||||||
12. 进入 `TJWaterServer`,执行 `startserber.bat`
|
|
||||||
|
|
||||||
NOTE:
|
|
||||||
版本问题
|
|
||||||
pip uninstall scipy numpy -y
|
|
||||||
pip install numpy==1.26.2 scipy==1.15.2
|
|
||||||
|
|
||||||
pg 信息
|
|
||||||
腾讯Windows服务器
|
|
||||||
Host: localhost (默认)
|
|
||||||
Port: 5432 (默认)
|
|
||||||
User: 就是Windows的用户名,这台机器也就是 Administrator
|
|
||||||
Password: 密码为空
|
|
||||||
|
|
||||||
redis 信息
|
|
||||||
|
|
||||||
1. 进到redis安装目录
|
|
||||||
2. 执行 redis-server.exe
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
influx db 信息
|
|
||||||
1. 运行 influxd.exe
|
|
||||||
2. 打开网页看下列的信息 http://localhost:8086
|
|
||||||
|
|
||||||
# influxdb数据库连接信息
|
|
||||||
influx_url = "http://localhost:8086" # 替换为你的InfluxDB实例地址
|
|
||||||
influx_token = "Vq8F5tzxqmjH6JYPBP5xqwo6nJbzRqCnahlcoMVyZGMPm3H92swD08VX-5lTH1laN_JG1x7EZ80WOQoycanmBw==" # 替换为你的InfluxDB Token
|
|
||||||
influx_org_name = "TJWATERORG" # 替换为你的Organization名称
|
|
||||||
influx_client = InfluxDBClient(url=influx_url, token=influx_token, org=influx_org_name)
|
|
||||||
|
|
||||||
|
|
||||||
UserName tjwater
|
|
||||||
Password Tjwater@123456
|
|
||||||
Organizatio TJWATEORG
|
|
||||||
Bucket TJWATERBUCKET
|
|
||||||
|
|
||||||
API Token : LsqvuqtBqtBv44z_CWh5bWfn9hs1QKcYu5kWahF_cdF6JyqtwuUxU5CK7HWP7BOtP5_2f5mjx76qXyuPLOHWdw==
|
|
||||||
|
|
||||||
influx config create --config-name onboarding `
|
|
||||||
--host-url "http://localhost:8086" `
|
|
||||||
--org "TJWATERORG" `
|
|
||||||
--token "LsqvuqtBqtBv44z_CWh5bWfn9hs1QKcYu5kWahF_cdF6JyqtwuUxU5CK7HWP7BOtP5_2f5mjx76qXyuPLOHWdw=="
|
|
||||||
--active
|
|
||||||
|
|
||||||
|
|
||||||
Setup instructions for WMH's work
|
|
||||||
|
|
||||||
1. import scada_info.csv
|
|
||||||
run python online_Analysis.py
|
|
||||||
|
|
||||||
2. import history_pattern_flow.csv
|
|
||||||
run python online_Analysis.py
|
|
||||||
Should manually change code
|
|
||||||
|
|
||||||
3. run create_template.py
|
|
||||||
|
|
||||||
4. run influxdb_api.py
|
|
||||||
在InfluxDB数据库中创建好我们需要的bucket
|
|
||||||
create buckets
|
|
||||||
|
|
||||||
5. run online_Analysis.py
|
|
||||||
有几个步骤
|
|
||||||
(1)创建用户名密码
|
|
||||||
(2)network_update 从 inp 文件创建 szh这个project
|
|
||||||
(3)upload_shp_to_pg
|
|
||||||
(4)submit_risk_probability_result
|
|
||||||
(5)pressure_sensor_placement_sensitivity
|
|
||||||
|
|
||||||
6. In times table, all time values should be the format "hh:mm::ss"
|
|
||||||
|
|
||||||
NOTES:
|
|
||||||
1. SCADA设备的时候,单位要转换,现在模拟算出来的单位是L/s,SCADA数据是m3/h,L/s要乘3.6才是m3/h
|
|
||||||
2. 之前的SCADA压力应该转过了,SCADA数据的单位是MPa,要乘以100才是m
|
|
||||||
Reference in New Issue
Block a user