LCOV - code coverage report
Current view: top level - include/app/manager - risk_manager.hpp (source / functions) Coverage Total Hit
Test: coverage.info Lines: 100.0 % 13 13
Test Date: 2025-12-19 03:13:09 Functions: 100.0 % 4 4

            Line data    Source code
       1              : /**
       2              :  * @file risk_manager.hpp
       3              :  * @brief 风险控制模块
       4              :  *
       5              :  * 提供订单风控检查功能,包括资金检查、价格检查、持仓检查等。
       6              :  * 在订单提交到撮合引擎之前进行风险验证。
       7              :  */
       8              : 
       9              : #pragma once
      10              : 
      11              : #include <string>
      12              : #include <cstdint>
      13              : #include "app/model/order.hpp"
      14              : #include "app/model/account.hpp"
      15              : #include "app/model/position.hpp"
      16              : #include "app/model/instrument.hpp"
      17              : #include "app/model/market_data_snapshot.hpp"
      18              : 
      19              : namespace fix40 {
      20              : 
      21              : // ============================================================================
      22              : // 拒绝原因代码
      23              : // ============================================================================
      24              : 
      25              : /**
      26              :  * @enum RejectReason
      27              :  * @brief 订单拒绝原因代码
      28              :  *
      29              :  * 定义风控检查失败时的拒绝原因代码,与设计文档中的错误处理表对应。
      30              :  */
      31              : enum class RejectReason {
      32              :     NONE = 0,                   ///< 无错误(检查通过)
      33              :     INSTRUMENT_NOT_FOUND = 1,   ///< 合约不存在
      34              :     INSUFFICIENT_FUNDS = 2,     ///< 资金不足
      35              :     PRICE_OUT_OF_LIMIT = 3,     ///< 价格超限(超出涨跌停)
      36              :     INSUFFICIENT_POSITION = 4,  ///< 持仓不足(平仓数量超过持仓)
      37              :     NO_COUNTER_PARTY = 5,       ///< 无对手盘(市价单)
      38              :     ORDER_NOT_FOUND = 6         ///< 订单不存在(撤单时)
      39              : };
      40              : 
      41              : // ============================================================================
      42              : // 检查结果结构
      43              : // ============================================================================
      44              : 
      45              : /**
      46              :  * @struct CheckResult
      47              :  * @brief 风控检查结果
      48              :  *
      49              :  * 包含检查是否通过、拒绝原因代码和拒绝原因文本。
      50              :  */
      51              : struct CheckResult {
      52              :     bool passed;                ///< 检查是否通过
      53              :     RejectReason rejectReason;  ///< 拒绝原因代码
      54              :     std::string rejectText;     ///< 拒绝原因文本
      55              : 
      56              :     /**
      57              :      * @brief 默认构造函数(检查通过)
      58              :      */
      59          632 :     CheckResult()
      60          632 :         : passed(true)
      61          632 :         , rejectReason(RejectReason::NONE)
      62          632 :     {}
      63              : 
      64              :     /**
      65              :      * @brief 构造失败结果
      66              :      *
      67              :      * @param reason 拒绝原因代码
      68              :      * @param text 拒绝原因文本
      69              :      */
      70          514 :     CheckResult(RejectReason reason, const std::string& text)
      71          514 :         : passed(false)
      72          514 :         , rejectReason(reason)
      73          514 :         , rejectText(text)
      74          514 :     {}
      75              : 
      76              :     /**
      77              :      * @brief 创建成功结果
      78              :      *
      79              :      * @return 检查通过的结果
      80              :      */
      81          632 :     static CheckResult success() {
      82          632 :         return CheckResult();
      83              :     }
      84              : 
      85              :     /**
      86              :      * @brief 创建失败结果
      87              :      *
      88              :      * @param reason 拒绝原因代码
      89              :      * @param text 拒绝原因文本
      90              :      * @return 检查失败的结果
      91              :      */
      92          514 :     static CheckResult failure(RejectReason reason, const std::string& text) {
      93          514 :         return CheckResult(reason, text);
      94              :     }
      95              : };
      96              : 
      97              : // ============================================================================
      98              : // 开平标志
      99              : // ============================================================================
     100              : 
     101              : /**
     102              :  * @enum OffsetFlag
     103              :  * @brief 开平标志
     104              :  *
     105              :  * 用于区分开仓和平仓订单。
     106              :  */
     107              : enum class OffsetFlag {
     108              :     OPEN = 0,   ///< 开仓
     109              :     CLOSE = 1   ///< 平仓
     110              : };
     111              : 
     112              : // ============================================================================
     113              : // 风控管理器
     114              : // ============================================================================
     115              : 
     116              : /**
     117              :  * @class RiskManager
     118              :  * @brief 风险控制模块
     119              :  *
     120              :  * 负责订单提交前的风险检查,包括:
     121              :  * - 资金检查:验证可用资金是否足够支付保证金
     122              :  * - 价格检查:验证限价单价格是否在涨跌停范围内
     123              :  * - 持仓检查:验证平仓数量是否超过持仓
     124              :  *
     125              :  * @par 使用示例
     126              :  * @code
     127              :  * RiskManager riskMgr;
     128              :  * 
     129              :  * Order order;
     130              :  * order.symbol = "IF2601";
     131              :  * order.side = OrderSide::BUY;
     132              :  * order.ordType = OrderType::LIMIT;
     133              :  * order.price = 4000.0;
     134              :  * order.orderQty = 2;
     135              :  * 
     136              :  * Account account("user001", 1000000.0);
     137              :  * Position position("user001", "IF2601");
     138              :  * Instrument instrument("IF2601", "CFFEX", "IF", 0.2, 300, 0.12);
     139              :  * instrument.updateLimitPrices(4200.0, 3800.0);
     140              :  * MarketDataSnapshot snapshot("IF2601");
     141              :  * snapshot.askPrice1 = 4000.2;
     142              :  * 
     143              :  * CheckResult result = riskMgr.checkOrder(order, account, position, instrument, snapshot, OffsetFlag::OPEN);
     144              :  * if (result.passed) {
     145              :  *     // 提交到撮合引擎
     146              :  * } else {
     147              :  *     // 拒绝订单,返回 result.rejectText
     148              :  * }
     149              :  * @endcode
     150              :  *
     151              :  * @par 线程安全
     152              :  * 所有公共方法都是线程安全的(无状态类)。
     153              :  */
     154              : class RiskManager {
     155              : public:
     156              :     // -------------------------------------------------------------------------
     157              :     // 构造函数
     158              :     // -------------------------------------------------------------------------
     159              : 
     160              :     /**
     161              :      * @brief 默认构造函数
     162              :      */
     163              :     RiskManager() = default;
     164              : 
     165              :     // -------------------------------------------------------------------------
     166              :     // 主检查方法
     167              :     // -------------------------------------------------------------------------
     168              : 
     169              :     /**
     170              :      * @brief 订单风控检查
     171              :      *
     172              :      * 对订单进行完整的风控检查,包括资金、价格、持仓等。
     173              :      *
     174              :      * @param order 待检查的订单
     175              :      * @param account 账户信息
     176              :      * @param position 持仓信息
     177              :      * @param instrument 合约信息
     178              :      * @param snapshot 行情快照
     179              :      * @param offsetFlag 开平标志
     180              :      * @return 检查结果
     181              :      *
     182              :      * @par 检查顺序
     183              :      * 1. 价格检查(限价单)
     184              :      * 2. 资金检查(开仓)
     185              :      * 3. 持仓检查(平仓)
     186              :      * 4. 对手盘检查(市价单)
     187              :      */
     188              :     CheckResult checkOrder(
     189              :         const Order& order,
     190              :         const Account& account,
     191              :         const Position& position,
     192              :         const Instrument& instrument,
     193              :         const MarketDataSnapshot& snapshot,
     194              :         OffsetFlag offsetFlag
     195              :     ) const;
     196              : 
     197              :     // -------------------------------------------------------------------------
     198              :     // 子检查方法(公开以便单独测试)
     199              :     // -------------------------------------------------------------------------
     200              : 
     201              :     /**
     202              :      * @brief 检查可用资金是否足够
     203              :      *
     204              :      * 验证账户可用资金是否足够支付开仓所需的保证金。
     205              :      *
     206              :      * @param order 订单信息
     207              :      * @param account 账户信息
     208              :      * @param instrument 合约信息
     209              :      * @return 检查结果
     210              :      *
     211              :      * @par 计算公式
     212              :      * 所需保证金 = 价格 × 数量 × 合约乘数 × 保证金率
     213              :      *
     214              :      * @note 市价单使用涨停价(买单)或跌停价(卖单)计算保证金
     215              :      */
     216              :     CheckResult checkMargin(
     217              :         const Order& order,
     218              :         const Account& account,
     219              :         const Instrument& instrument
     220              :     ) const;
     221              : 
     222              :     /**
     223              :      * @brief 检查价格是否在涨跌停范围内
     224              :      *
     225              :      * 验证限价单的价格是否在当日涨跌停价格范围内。
     226              :      *
     227              :      * @param order 订单信息
     228              :      * @param instrument 合约信息
     229              :      * @return 检查结果
     230              :      *
     231              :      * @note 市价单不进行价格检查
     232              :      */
     233              :     CheckResult checkPrice(
     234              :         const Order& order,
     235              :         const Instrument& instrument
     236              :     ) const;
     237              : 
     238              :     /**
     239              :      * @brief 检查平仓数量是否超过持仓
     240              :      *
     241              :      * 验证平仓订单的数量是否超过当前持仓数量。
     242              :      *
     243              :      * @param order 订单信息
     244              :      * @param position 持仓信息
     245              :      * @return 检查结果
     246              :      *
     247              :      * @note 买单平空头持仓,卖单平多头持仓
     248              :      */
     249              :     CheckResult checkPosition(
     250              :         const Order& order,
     251              :         const Position& position
     252              :     ) const;
     253              : 
     254              :     /**
     255              :      * @brief 检查市价单是否有对手盘
     256              :      *
     257              :      * 验证市价单是否有可成交的对手盘。
     258              :      *
     259              :      * @param order 订单信息
     260              :      * @param snapshot 行情快照
     261              :      * @return 检查结果
     262              :      *
     263              :      * @note 买单需要有卖盘,卖单需要有买盘
     264              :      */
     265              :     CheckResult checkCounterParty(
     266              :         const Order& order,
     267              :         const MarketDataSnapshot& snapshot
     268              :     ) const;
     269              : 
     270              :     // -------------------------------------------------------------------------
     271              :     // 辅助方法
     272              :     // -------------------------------------------------------------------------
     273              : 
     274              :     /**
     275              :      * @brief 计算订单所需保证金
     276              :      *
     277              :      * @param order 订单信息
     278              :      * @param instrument 合约信息
     279              :      * @return 所需保证金金额
     280              :      *
     281              :      * @note 市价单使用涨停价(买单)或跌停价(卖单)计算
     282              :      */
     283              :     double calculateRequiredMargin(
     284              :         const Order& order,
     285              :         const Instrument& instrument
     286              :     ) const;
     287              : };
     288              : 
     289              : } // namespace fix40
        

Generated by: LCOV version 2.0-1