Broker 模块架构文档
本文档描述 Broker(券商)模块的架构设计、业务逻辑、数据模型和配置管理。
概述
Broker 模块负责管理券商配置和交易费用计算,是 Fire 量化交易系统与外部券商交互的核心模块。系统支持多券商管理,每个券商有独立的认证信息和费用配置,支持美股和港股的标准费率计算。
核心功能
券商管理
- 多券商支持: 每个用户可配置多个券商账户
- 认证管理: 安全存储和管理券商 API 密钥
- 状态控制: 启用/禁用券商配置
- 连接测试: 验证券商配置有效性
费用管理
- 标准费率: 支持美股和港股标准费率配置
- 精确计算: 使用 Decimal 类型确保计算精度
- 分项计算: 平台费、交易费、交收费、审计费分别计算
- 方向敏感: 买入和卖出费用区别处理
安全保障
- 访问控制: 用户只能访问自己的券商配置
- 数据隔离: 通过 user_id 实现多租户数据隔离
组件
组件架构图
graph TD
subgraph "API层"
API[BrokerAPI<br/>券商接口]
FAPI[FeeAPI<br/>费用接口]
end
subgraph "服务层"
BS[BrokerService<br/>券商服务]
FCS[FeeCalculationService<br/>费用计算服务]
VS[ValidationService<br/>配置验证服务]
end
subgraph "数据层"
BR[BrokerRepository<br/>券商仓库]
BM[BrokerModel<br/>券商模型]
FC[FeeConfig<br/>费用配置]
end
API --> BS
FAPI --> FCS
BS --> BR
BS --> VS
FCS --> FC
BR --> BM
style BS fill:#e1f5ff
style BR fill:#e8f5e9
核心组件说明
BrokerService (券商服务)
- 职责: 管理券商配置的业务逻辑
- 实现类:
backend.core.services.broker_service.BrokerService - 主要方法:
create_broker(): 创建券商配置update_broker(): 更新券商配置test_connection(): 测试券商连接get_user_brokers(): 获取用户的所有券商
- 状态管理: 无状态
BrokerRepository (券商仓库)
- 职责: 券商数据的持久化和查询
- 实现类:
backend.core.repositories.broker_repository.BrokerRepository - 主要方法:
save(): 保存券商配置find_by_user_id(): 查询用户的券商find_active_broker(): 获取激活的券商delete(): 删除券商配置
- 状态管理: 依赖数据库连接
FeeCalculationService (费用计算服务)
- 职责: 计算交易费用
- 实现类:
backend.core.services.fee_calculation_service.FeeCalculationService - 主要功能:
- 美股费用计算
- 港股费用计算
- 费用明细生成
- 精度控制(保留2位小数)
依赖关系
内部依赖
| 模块名 | 用途 |
|---|---|
core.models.broker |
Broker 数据模型定义 |
core.repositories.broker_repository |
Broker 数据持久化 |
core.trading.utils.fee_calculator |
费用计算器 |
infrastructure.database.redis_client |
Redis 数据库连接 |
外部依赖
| 库名 | 版本要求 | 用途 |
|---|---|---|
pydantic |
≥2.6.0 | 数据验证 |
redis |
≥5.0.0 | 数据存储 |
数据流
券商配置流程
sequenceDiagram
participant User as 用户
participant API as API层
participant Service as BrokerService
participant Repo as BrokerRepository
participant Redis as Redis数据库
User->>API: 创建券商配置
API->>Service: create_broker()
Service->>Service: 验证用户权限
Service->>Service: 验证券商代码唯一性
Service->>Repo: create_broker()
Repo->>Redis: 保存券商数据
Redis-->>Repo: 确认保存
Repo-->>Service: 返回Broker对象
Service-->>API: 返回结果
API-->>User: 配置创建成功
费用计算流程
flowchart LR
Start([开始]) --> Input[输入参数<br/>数量/价格/方向]
Input --> GetConfig[获取费率配置]
GetConfig --> CalcPlatform[计算平台费]
CalcPlatform --> CheckSide{卖出?}
CheckSide -->|是| CalcActivity[计算交易活动费]
CheckSide -->|否| CalcClearing[计算交收费]
CalcActivity --> CalcClearing
CalcClearing --> CalcAudit[计算审计费]
CalcAudit --> Round[四舍五入到2位]
Round --> End([返回费用])
style GetConfig fill:#e1f5ff
style CalcPlatform fill:#fff4e6
数据结构
输入数据格式
券商配置 (BrokerConfig):
@dataclass
class BrokerConfig:
name: str # 券商名称
type: BrokerType # 券商类型
config: Dict[str, Any] # API配置
fee_config: FeeConfig # 费用配置
status: BrokerStatus # 状态
输出数据格式
费用计算结果 (FeeCalculation):
@dataclass
class FeeCalculation:
platform_fee: Decimal # 平台费
activity_fee: Decimal # 交易活动费
clearing_fee: Decimal # 交收费
audit_fee: Decimal # 审计费
total_fee: Decimal # 总费用
# 所有费用保留2位小数
接口
Python API
BrokerService 接口
class BrokerService:
"""券商服务接口"""
async def create_broker(
self,
user_id: str,
config: BrokerConfig
) -> Broker:
"""创建券商配置"""
pass
async def update_broker(
self,
broker_id: str,
updates: Dict[str, Any]
) -> Broker:
"""更新券商配置"""
pass
async def test_connection(
self,
broker_id: str
) -> ConnectionTestResult:
"""测试券商连接"""
pass
FeeCalculation 使用示例
from backend.core.services.fee_calculation_service import FeeCalculationService
from backend.core.models.broker import USFeeConfig
from decimal import Decimal
# 创建服务
service = FeeCalculationService()
# 美股费用计算
fee = service.calculate_us_fees(
quantity=Decimal("100"),
price=Decimal("150.50"),
side="buy",
fee_config=USFeeConfig()
)
print(f"总费用: ${fee.total_fee}")
REST API
券商管理端点
| 端点 | 方法 | 描述 |
|---|---|---|
/api/v1/brokers |
GET | 获取券商列表 |
/api/v1/brokers |
POST | 创建券商配置 |
/api/v1/brokers/{id} |
GET | 获取券商详情 |
/api/v1/brokers/{id} |
PUT | 更新券商配置 |
/api/v1/brokers/{id} |
DELETE | 删除券商配置 |
/api/v1/brokers/{id}/test |
POST | 测试券商连接 |
费用计算端点
| 端点 | 方法 | 描述 |
|---|---|---|
/api/v1/brokers/{id}/fee-config |
GET | 获取费用配置 |
/api/v1/brokers/{id}/fee-config |
PUT | 更新费用配置 |
/api/v1/brokers/{id}/fee-config/calculate |
POST | 计算预估费用 |
扩展点
自定义券商适配器
from backend.core.brokers import BrokerAdapter
class CustomBrokerAdapter(BrokerAdapter):
"""自定义券商适配器"""
def __init__(self, config: Dict[str, Any]):
self.config = config
async def connect(self) -> bool:
"""建立连接"""
# 自定义连接逻辑
pass
async def place_order(self, order: Order) -> OrderResult:
"""下单接口"""
# 自定义下单逻辑
pass
注册自定义券商
from backend.core.brokers import BrokerRegistry
# 注册适配器
BrokerRegistry.register(
broker_type="custom",
adapter_class=CustomBrokerAdapter
)
配置
费用配置模型
FeeConfig(费用配置)
class FeeConfig(BaseModel):
"""交易费用配置"""
us_fees: USFeeConfig # 美股费用配置
hk_fees: HKFeeConfig # 港股费用配置
USFeeConfig(美股费用配置)
class USFeeConfig(BaseModel):
"""美股交易费用配置"""
# 平台费用
platform_fee_per_share: Decimal = Decimal('0.005') # 平台费 0.005美元/股
platform_fee_minimum: Decimal = Decimal('1.0') # 最低收取1美元
# 交易活动费用 (仅在卖出时收取)
activity_fee_per_share: Decimal = Decimal('0.000166') # 0.000166美元/股
activity_fee_maximum: Decimal = Decimal('8.3') # 最高8.3美元
# 交收费
clearing_fee_per_share: Decimal = Decimal('0.003') # 0.003美元/股
clearing_fee_max_pct: Decimal = Decimal('0.07') # 最高7%
# 综合审计费
audit_fee_per_share: Decimal = Decimal('0.000046') # 0.000046美元/股
audit_fee_minimum: Decimal = Decimal('0.01') # 最低0.01美元
HKFeeConfig(港股费用配置)
class HKFeeConfig(BaseModel):
"""港股交易费用配置(结构与美股相同)"""
# 平台费用
platform_fee_per_share: Decimal = Decimal('0.005')
platform_fee_minimum: Decimal = Decimal('1.0')
# 交易活动费用 (仅在卖出时收取)
activity_fee_per_share: Decimal = Decimal('0.000166')
activity_fee_maximum: Decimal = Decimal('8.3')
# 交收费
clearing_fee_per_share: Decimal = Decimal('0.003')
clearing_fee_max_pct: Decimal = Decimal('0.07')
# 综合审计费
audit_fee_per_share: Decimal = Decimal('0.000046')
audit_fee_minimum: Decimal = Decimal('0.01')
FeeCalculator 接口
class FeeCalculator:
"""交易费用计算器接口"""
def __init__(self, fee_config: Optional[FeeConfig] = None):
"""
初始化费用计算器
Args:
fee_config: 费用配置(包含美股和港股配置),如果为None则使用默认配置
"""
pass
def calculate_fee(
self,
quantity: Decimal,
price: Decimal,
side: str,
market: str
) -> TradingFee:
"""
计算交易费用
Args:
quantity: 成交数量
price: 成交价格
side: 买卖方向 ('buy' | 'sell')
market: 市场类型 ('US' | 'HK')
Returns:
TradingFee: 费用明细对象
"""
pass
TradingFee(费用明细)
class TradingFee(BaseModel):
"""交易费用明细"""
platform_fee: Decimal = Decimal('0') # 平台费
activity_fee: Decimal = Decimal('0') # 交易活动费
clearing_fee: Decimal = Decimal('0') # 交收费
audit_fee: Decimal = Decimal('0') # 综合审计费
total_fee: Decimal = Decimal('0') # 总费用
currency: str = 'USD' # 币种
calculation_details: Dict[str, Any] = {} # 计算详情
数据存储设计
Redis 数据存储
Broker 数据结构
券商数据存储在 Redis 中,使用 JSON 格式:
# Redis Key: broker:{broker_id}
{
"id": "broker_id",
"user_id": "user_id",
"code": "longport",
"name": "长桥证券",
"type": "longport",
"status": "active",
"config": {
"api_config": {
"app_key": "...",
"app_secret": "...",
"access_token": "..."
},
"fee_config": {
"us_fees": {
"platform_fee_per_share": "0.005",
"platform_fee_minimum": "1.0",
"activity_fee_per_share": "0.000166",
"activity_fee_maximum": "8.3",
"clearing_fee_per_share": "0.003",
"clearing_fee_max_pct": "0.07",
"audit_fee_per_share": "0.000046",
"audit_fee_minimum": "0.01"
},
"hk_fees": {
"platform_fee_per_share": "0.005",
"platform_fee_minimum": "1.0",
"activity_fee_per_share": "0.000166",
"activity_fee_maximum": "8.3",
"clearing_fee_per_share": "0.003",
"clearing_fee_max_pct": "0.07",
"audit_fee_per_share": "0.000046",
"audit_fee_minimum": "0.01"
}
}
},
"created_at": "2025-11-18T10:00:00",
"updated_at": "2025-11-18T10:00:00"
}
Order 中的 trading_fee 字段
✅ 实现状态:
trading_fee字段已在core/models/trading.py的 Order 模型中实现
# backend/core/models/trading.py
class Order(BaseModel):
"""订单模型"""
symbol: str
side: OrderSide
order_type: OrderType
quantity: Decimal
price: Optional[Decimal]
session_id: str
order_id: Optional[str]
status: OrderStatus
trading_fee: Optional[Dict[str, Any]] # ✅ 已实现:交易费用明细
market_timestamp: Optional[datetime]
trading_fee 字段结构(Dict[str, Any]):
{
"platform_fee": "1.50",
"activity_fee": "0.50",
"clearing_fee": "0.90",
"audit_fee": "0.14",
"total_fee": "3.04",
"currency": "USD",
"calculation_details": {
"quantity": 300,
"price": "150.25",
"side": "buy",
"market": "US"
}
}
Redis 缓存
# 券商费用配置缓存
key: f"broker:fee_config:{broker_id}"
value: {
"us_fees": {...},
"hk_fees": {...}
}
ttl: 3600 # 1小时
# 交易会话费用配置缓存
key: f"trading:session:fee_config:{session_id}"
value: {
"us_fees": {...},
"hk_fees": {...}
}
ttl: 86400 # 24小时
前端费用配置界面
费用配置表单接口
interface FeeConfigFormData {
us_fees: USFeeConfig;
hk_fees: HKFeeConfig;
}
interface USFeeConfig {
// 平台费用
platform_fee_per_share: number; // 平台费(美元/股)
platform_fee_minimum: number; // 最低收费(美元)
// 交易活动费用
activity_fee_per_share: number; // 交易活动费(美元/股)
activity_fee_maximum: number; // 最高收费(美元)
// 交收费
clearing_fee_per_share: number; // 交收费(美元/股)
clearing_fee_max_pct: number; // 最高收费百分比
// 综合审计费
audit_fee_per_share: number; // 综合审计费(美元/股)
audit_fee_minimum: number; // 最低收费(美元)
}
// HKFeeConfig 结构相同
表单字段说明
| 字段 | 说明 | 默认值 | Tooltip |
|---|---|---|---|
| 平台费(每股) | 每股交易平台费用,买入和卖出都收取 | 0.005 | 按成交股数计算,例如100股收取0.5美元 |
| 平台费(最低) | 每笔订单最低收取的平台费 | 1.0 | 即使按股计算不足1美元,也收取1美元 |
| 交易活动费(每股) | 每股交易活动费,仅卖出时收取 | 0.000166 | 按成交股数计算,仅适用于卖出订单 |
| 交易活动费(最高) | 每笔订单最高收取的交易活动费 | 8.3 | 即使按股计算超过8.3美元,也只收取8.3美元 |
| 交收费(每股) | 每股交收费用,买入和卖出都收取 | 0.003 | 按成交股数计算 |
| 交收费(最高百分比) | 交收费最高收取交易额的百分比 | 0.07 | 例如交易额1000美元,最高收取70美元 |
| 综合审计费(每股) | 每股综合审计费,买入和卖出都收取 | 0.000046 | 按成交股数计算 |
| 综合审计费(最低) | 每笔订单最低收取的综合审计费 | 0.01 | 即使按股计算不足0.01美元,也收取0.01美元 |
费用处理模式
模拟资产交易(实时交易 + 回测)
- 订单费用:在订单成交时实时计算费用,直接填入订单的
trading_fee字段 - 费用扣除:成交后立即从账户现金中扣除费用
- 资产更新:
- 买入:扣除交易金额和费用,增加持仓
- 卖出:增加交易金额,扣除费用,减少持仓
- 费用来源:基于券商费用配置实时计算
真实资产交易(实时交易)
- 订单费用:从券商API拉取的订单数据可能不包含费用明细
- 费用计算:系统模拟计算费用并填入订单的
trading_fee字段(仅用于展示和统计) - 费用扣除:不扣除费用,真实资产以券商数据为准
- 资产更新:完全基于券商API返回的账户数据,不做本地计算
- 费用来源:基于券商费用配置模拟计算(用于参考)
环境变量配置
基于实际的 backend/infrastructure/config/settings.py:
| 环境变量 | 说明 | 默认值 |
|---|---|---|
REDIS_HOST |
Redis 主机地址 | localhost |
REDIS_PORT |
Redis 端口 | 6379 |
REDIS_DB |
Redis 数据库编号 | 0 |
REDIS_PASSWORD |
Redis 密码 | None |
JWT_SECRET_KEY |
JWT 签名密钥 | your-jwt-secret-key-here |
相关文档
- Trading 模块架构 - 交易引擎详细设计
- Data Pipeline 模块架构 - 数据处理详细设计
- 风险管理模块架构 - 风险控制详细设计
- 基础架构文档 - 系统基础架构