# 交易相关

# Q1:模拟交易相关

A:

# 概述

模拟交易是在真实的市场环境中,用虚拟资金做交易,不会对您的真实账户的资产造成影响。

# 交易时间

模拟交易仅支持在常规交易时段交易,不支持在非交易时段、美股盘前盘后时段、A股港股盘前盘后竞价时段交易。详情可点击 模拟交易规则

# 支持品类

OpenAPI 支持模拟交易的品类请参考 这里

# 解锁

与真实交易不同,模拟交易无需对账户进行解锁,即可下单或改单撤单。

# 订单

  1. 订单类型:限价单和市价单。
  2. 改单操作类型:模拟交易不支持使生效、使失效、删除,仅支持支持修改订单、 撤单。
  3. 成交:模拟交易不支持成交相关操作,包括 查询今日成交查询历史成交响应成交推送回调
  4. 有效期限:模拟交易有效期限仅支持当日有效。
  5. 卖空:期权和期货支持卖空。股票仅美股支持卖空。

# 操作平台

  1. 移动端:我的 — 模拟交易

sim-page

  1. 桌面端:左侧模拟 tab

sim-page

  1. 网页端:模拟交易界面

  2. OpenAPI:在调用接口时,设置参数交易环境为模拟环境即可。详见 如何使用 OpenAPI 进行模拟交易

提示

  • 以上四种方式只是操作平台不同,四种方式操作的模拟账户是共通的。

# 如何使用 OpenAPI 进行模拟交易?

# 创建连接

先根据交易品种 创建相应的连接 。当交易品种是股票或期权时,请使用 OpenSecTradeContext。当交易品种是期货时,请使用 OpenFutureTradeContext

# 获取交易业务账户列表

使用 获取交易业务账户列表 查看交易账户(包括模拟账户、真实账户)。以 Python 为例:返回字段交易环境 trd_envSIMULATE,表示模拟账户。

  • Example:Stocks and Options
from futu import *
trd_ctx = OpenSecTradeContext(filter_trdmarket=TrdMarket.HK, host='127.0.0.1', port=11111, security_firm=SecurityFirm.FUTUSECURITIES)
#trd_ctx = OpenFutureTradeContext(host='127.0.0.1', port=11111, is_encrypt=None, security_firm=SecurityFirm.FUTUSECURITIES)
ret, data = trd_ctx.get_acc_list()
if ret == RET_OK:
    print(data)
    print(data['acc_id'][0])  # get the first account id
    print(data['acc_id'].values.tolist())  # convert to list format
else:
    print('get_acc_list error: ', data)
trd_ctx.close()
1
2
3
4
5
6
7
8
9
10
11
  • Output
               acc_id   trd_env acc_type          card_num   security_firm  \
0  281756480572583411      REAL   MARGIN  1001318721909873  FUTUSECURITIES   
1             9053218  SIMULATE     CASH               N/A             N/A   
2             9048221  SIMULATE   MARGIN               N/A             N/A   

  sim_acc_type  trdmarket_auth  
0          N/A  [HK, US, HKCC]  
1        STOCK            [HK]  
2       OPTION            [HK] 
1
2
3
4
5
6
7
8
9

提示

  • 模拟交易中,区分股票账户和期权账户,股票账户只能交易股票,期权账户只能交易期权;以 Python 为例:返回字段中模拟账户类型 sim_acc_typeSTOCK,表示股票账户;为OPTION,表示期权账户。
  • Example: Futures
from futu import *
#trd_ctx = OpenSecTradeContext(filter_trdmarket=TrdMarket.HK, host='127.0.0.1', port=11111, security_firm=SecurityFirm.FUTUSECURITIES)
trd_ctx = OpenFutureTradeContext(host='127.0.0.1', port=11111, is_encrypt=None, security_firm=SecurityFirm.FUTUSECURITIES)
ret, data = trd_ctx.get_acc_list()
if ret == RET_OK:
    print(data)
    print(data['acc_id'][0])  # get the first account id
    print(data['acc_id'].values.tolist())  # convert to list format
else:
    print('get_acc_list error: ', data)
trd_ctx.close()
1
2
3
4
5
6
7
8
9
10
11
  • Output
    acc_id   trd_env acc_type card_num security_firm sim_acc_type  \
0  9497808  SIMULATE   MARGIN      N/A           N/A      FUTURES   
1  9497809  SIMULATE   MARGIN      N/A           N/A      FUTURES   
2  9497810  SIMULATE   MARGIN      N/A           N/A      FUTURES   
3  9497811  SIMULATE   MARGIN      N/A           N/A      FUTURES   

          trdmarket_auth  
0  [FUTURES_SIMULATE_HK]  
1  [FUTURES_SIMULATE_US]  
2  [FUTURES_SIMULATE_SG]  
3  [FUTURES_SIMULATE_JP]  
1
2
3
4
5
6
7
8
9
10
11

# 下单

使用 下单接口 时,设置交易环境为模拟环境即可。以 Python 为例:trd_env = TrdEnv.SIMULATE

  • Example
from futu import *
trd_ctx = OpenHKTradeContext(host='127.0.0.1', port=11111, security_firm=SecurityFirm.FUTUSECURITIES)
ret, data = trd_ctx.place_order(price=510.0, qty=100, code="HK.00700", trd_side=TrdSide.BUY, trd_env=TrdEnv.SIMULATE)
if ret == RET_OK:
    print(data)
else:
    print('place_order error: ', data)
trd_ctx.close()
1
2
3
4
5
6
7
8
  • Output
	code	stock_name	trd_side	order_type	order_status	order_id	qty	price	create_time	updated_time	dealt_qty	dealt_avg_price	last_err_msg	remark	time_in_force	fill_outside_rth
0	HK.00700	腾讯控股	BUY	NORMAL	SUBMITTING	4642000476506964749	100.0	510.0	2021-10-09 11:34:54	2021-10-09 11:34:54	0.0	0.0			DAY	N/A
1
2

# 撤单改单

使用 撤单接口 时,设置交易环境为模拟环境即可。以 Python 为例: trd_env = TrdEnv.SIMULATE

  • Example
from futu import *
trd_ctx = OpenHKTradeContext(host='127.0.0.1', port=11111, security_firm=SecurityFirm.FUTUSECURITIES)
order_id = "4642000476506964749"
ret, data = trd_ctx.modify_order(ModifyOrderOp.CANCEL, order_id, 0, 0, trd_env=TrdEnv.SIMULATE)
if ret == RET_OK:
    print(data)
else:
    print('modify_order error: ', data)
trd_ctx.close()
1
2
3
4
5
6
7
8
9
  • Output
    trd_env             order_id
0  SIMULATE  4642000476506964749
1
2

# 查询历史订单

使用 查询历史订单接口 时,设置交易环境为模拟环境即可。以 Python 为例:trd_env = TrdEnv.SIMULATE

  • Example
from futu import *
trd_ctx = OpenHKTradeContext(host='127.0.0.1', port=11111, security_firm=SecurityFirm.FUTUSECURITIES)
ret, data = trd_ctx.history_order_list_query(trd_env=TrdEnv.SIMULATE)
if ret == RET_OK:
    print(data)
else:
    print('history_order_list_query error: ', data)
trd_ctx.close()
1
2
3
4
5
6
7
8
  • Output
	code	stock_name	trd_side	order_type	order_status	order_id	qty	price	create_time	updated_time	dealt_qty	dealt_avg_price	last_err_msg	remark	time_in_force	fill_outside_rth
0	HK.00700	腾讯控股	BUY	ABSOLUTE_LIMIT	CANCELLED_ALL	4642000476506964749	100.0	510.0	2021-10-09 11:34:54	2021-10-09 11:37:08	0.0	0.0			DAY	N/A
1
2

# 如何重置模拟账户?

目前 OpenAPI 不支持重置模拟账户,您可在移动端使用复活卡重置指定模拟账户,重置后账户资金将恢复至初始值,历史订单将会被清空。

# 具体操作

移动端:我的 — 模拟交易 — 我的头像 — 我的道具 — 复活卡。 sim-page

# Q2:是否支持 A 股交易?

A: 模拟交易支持 A 股交易。但真实交易仅可通过 A 股通交易部分 A 股,具体详见 A 股通名单

# Q3:各市场支持的交易方向

A: 除了期货,其他股票都只支持传入 BUY 和 SELL 两个交易方向。在空仓情况下传入 SELL,产生的订单交易方向是卖空。

# Q4:真实交易中,各市场支持的订单类型

A:

市场 品种 限价单 市价单 竞价限价单 竞价市价单 绝对限价单 特别限价单 特别限价且要求
全部成交订单
止损市价单 止损限价单 触及市价单(止盈) 触及限价单(止盈) 跟踪止损市价单 跟踪止损限价单
香港市场 证券类产品(含股票、ETFs、
窝轮、牛熊、界内证)
期权 X - - - - - X X X
期货 - - - - X X X
美国市场 证券类产品(含股票、ETFs) - - - - -
期权 - - - - -
期货 - - - - - X X X
A 股通市场 证券类产品(含股票、ETFs) X - - - - - X X X
新加坡市场 期货 X - - - - - X X X
日本市场 期货 X - - - - - X X X

# Q5:各市场支持的订单操作

A:

  • 港股支持改单、撤单、生效、失效、删除
  • 美股仅支持改单和撤单
  • A 股通仅支持撤单
  • 期货支持改单、撤单、删除

# Q6:OpenD 启动参数 future_trade_api_time_zone 如何使用?

A:由于期货账户支持交易的品种分布在全球多个交易所,交易所的所属时区各有不同,因此期货交易 API 的时间显示就成为了一个问题。
OpenD 启动参数中新增了 future_trade_api_time_zone 这一参数,供全球不同地区的期货交易者灵活指定时区。默认时区为 UTC+8,如果您更习惯美东时间,只需将此参数配置为 UTC-5 即可。

提示

  • 此参数仅会对期货交易接口类对象生效。港股交易、美股交易、A 股通交易接口类对象的时区,仍然按照交易所所在的时区进行显示。
  • 此参数会影响的接口包括:响应订单推送回调,响应成交推送回调,查询今日订单,查询历史订单,查询当日成交,查询历史成交,下单。

# Q7:通过 OpenAPI 下的订单,能在 APP 上面看到吗?

A:可以看到。
通过 OpenAPI 成功发出下单指令后,您可以在 APP 的 交易 页面,查看今日订单、订单状态、成交情况等等,也可以在 消息—订单消息 中收到成交提醒的通知。

# Q8:哪些品类支持在非交易时段下单?

A:所有的订单,都需要在开盘期间才能够成交。
OpenAPI 仅对一部分品类,支持了 非交易时段下单 的功能(APP 上支持更多品类的非交易时段下单功能)。具体请参考下表:

市场 标的类型 模拟交易 真实交易
富途证券(香港) moomoo证券(美国) moomoo证券(新加坡) 富途证券(澳大利亚)
香港市场 证券类产品
(含股票、ETFs、窝轮、牛熊、界内证)
X
期权 X X X X
期货 X X X X X
美国市场 证券类产品(含股票、ETFs) X X X X
期权 X X X X
期货 X X X X X
A 股市场 A 股通股票 X X X X
非 A 股通股票 X X X X
新加坡市场 期货 X X X X X
日本市场 期货 X X X X X

提示

  • ✓:支持非交易时段下单
  • X:暂不支持非交易时段下单(或暂不支持交易)

# Q9:对于下单接口,各订单类型对应的必传参数

A:

参数 限价单 市价单 竞价限价单 竞价市价单 绝对限价单 特别限价单 特别限价且要求
全部成交订单
止损市价单 止损限价单 触及市价单(止盈) 触及限价单(止盈) 跟踪止损市价单 跟踪止损限价单
price
qty
code
trd_side
order_type
trd_env
aux_price
trail_type
trail_value
trail_spread

Python 用户 注意,place_order 并未对 price 设置默认值,对于上述五类订单类型,仍需对 price 传参,price 可以传入任意值。

# Q10:对于改单接口,修改订单时,各订单类型对应的必传参数

A:

参数 限价单 市价单 竞价限价单 竞价市价单 绝对限价单 特别限价单 特别限价且要求
全部成交订单
止损市价单 止损限价单 触及市价单(止盈) 触及限价单(止盈) 跟踪止损市价单 跟踪止损限价单
modify_order_op
order_id
price
qty
trd_env
aux_price
trail_type
trail_value
trail_spread

Python 用户 注意,modify_order 并未对 price 设置默认值,对于上述五类订单类型,仍需对 price 传参,price 可以传入任意值。

# Q11:交易接口返回“当前证券业务账户尚未同意免责协议”?

A:
点击下方链接完成协议确认,重启 OpenD 即可正常使用交易功能。

所属券商 协议确认
富途证券(香港) 点击这里
moomoo证券(美国) 点击这里
moomoo证券(新加坡) 点击这里
富途证券(澳大利亚) 点击这里

# Q12:典型日内交易者(PDT)相关

# 概述

客户使用moomoo证券(美国) 账户进行日内交易时,会受到美国 FINRA 的监管限制(此为美国券商受到的监管要求,与交易股票的所属市场无关。其他国家或地区的券商

的交易账户则不受此限制)。若用户在任意连续的5个交易日内,进行日内交易 3 次以上,则会被标记为典型日内交易者(PDT)。
更多详情,点击这里

# 进行日内交易的流程图

PDT_process

# 我愿意被标记为 PDT,且不希望程式交易被打断,如何关闭“防止被标记为 PDT”?

A:
当您在连续的 5 个交易日内,进行第 4 次日内交易时,为了防止您被无意识地标记为 PDT,服务器会对此交易进行拦截。若您主动想被标记为 PDT,并且不希望服务器拦截,可以采取以下措施:
命令行 Futu OpenD 中配置参数,将启动参数 pdt_protection 的值修改为 0,以关闭“防止被标记为日内交易者”的功能。

US_para
注意:若您被标记 PDT,当您的账户权益小于$25000时,您将无法开仓。

# 如何关闭 DTCall 预警提醒?

A:
您被标记为 PDT 后,需要留意账户的日内交易购买力(DTBP),日内交易超出 DTBP 时将收到日内交易保证金追缴(DTCall)。服务器会在您即将开仓下单超出剩余日内交易购买力前,阻止您的下单。若您仍然希望进行下单,并且不希望服务器拦截,可以采取以下措施:
命令行 Futu OpenD 中配置参数,将启动参数 dtcall_confirmation 的值修改为 0,以关闭“日内交易保证金追缴预警”的功能。

US_para2
注意:若您开仓订单的市值大于您的剩余日内交易购买力,并且在今日平仓当前标的,您将会收到日内交易保证金追缴通知(Day-Trading Call),只能通过存入资金才能解除。

# 如何查看 DTBP 的值?

A:
通过 查询账户资金 接口,可以获取日内交易相关的返回值,如:剩余日内交易次数、初始日内交易购买力、剩余日内交易购买力等。

# Q13:如何跟踪订单成交状态

A: 下单后,可使用以下接口跟踪订单成交状态:

交易环境 接口
真实交易 响应订单推送回调响应成交推送回调
模拟交易 响应订单推送回调

注意:对于非 python 语言用户,在使用上述两个接口之前,需要先进行 订阅交易推送

# 响应订单推送回调 的特点:

反馈 整个订单 的信息变动。当以下 8 个字段发生变化时,会触发订单推送:
订单状态订单价格订单数量成交数量触发价格跟踪类型跟踪金额/百分比指定价差

因此,当您进行下单、改单,撤单、使生效、使失效操作,或者订单在市场中发生了高级订单被触发、有成交变动的情况,都会触发订单推送。您只需要调用 响应成交推送回调,即可监听这些信息。

# 响应成交推送回调 的特点:

只反馈 单笔成交 的信息。当以下 1 个字段发生变化时,会触发订单推送:
成交状态

举例:假设一笔限价单订单 900 股,分成了 3 次才完全成交,每次成交分别是:200、300、400 股。
example

# Q14:下单接口返回“订单价格不在价位上”?

A:
对于不同市场的标的,交易所有着不同的最小变动单位要求。如果提交的订单价格不符合要求,订单将会被拒绝。各市场价位规则如下:

# 价位规则

# 香港市场

以港交所官方说明为准,点击 这里

# A 股市场

股票价位:0.01。

# 美国市场

股票价位:

合约价格 价位
$1 以下 $0.0001
$1 以上 $0.01

期权价位:

合约价格 价位
$0.10 - $3.00 $0.01 或者 $0.05
$3.00 以上 $0.05 或者 $0.10

期货价位:不同合约价位规则不同。可以通过 获取期货合约资料 接口的返回字段 最小变动的单位 查看。

# 怎么避免订单价格不在价位上?

  • 方法一:通过 获取实时摆盘 接口,获取合法的交易价格。交易所摆盘上的价位一定是合法的价位。

  • 方法二:通过 下单 接口的参数 价格微调幅度,将传入价格自动调整到合法的交易价格上。

    例如:假设腾讯控股当前市价为 359.600,根据价位规则,对应的最小变动价位为 0.200。

    假设您的下单传入订单价格为 359.678,价格微调幅度为 0.0015,代表接受 OpenD 对传入价格自动向上调整到最近的合法价位,且不能超过 0.15%。此情景下,向上最近的合法价格为 359.800,价格实际需要调整的幅度为 0.034%,符合价格微调幅度的要求,因此最终提交的订单价格为 359.800。

    若价格微调幅度设置数值小于实际需要调整的幅度,OpenD 自动调整价位失败,订单仍会返回报错“订单价格不在价位上”。

# Q15:我的购买力足够,为什么下市价单会返回“购买力不足”?

A:

# 为什么市价单会提示购买力不足

  • 出于风控考量,系统给了市价单较高的购买力系数。在所有订单参数都相同的情况下,选择市价单会比限价单占用更多的购买力。
  • 而且对于不同的品种,和不同的市场情况,风控系统会对市价单的购买力系数做动态调整。所以在下市价单时,若您通过最大购买力去计算最大可买数量,计算的结果很可能是不准确的。

# 如何计算正确的可买数量

不建议自己计算,您可以通过 查询最大可买可卖 接口获取正确的可买数量。

# 如何尽可能买更多

您可以用价格为对价的限价单,替代市价单进行交易。
其中,对价:买1价(下卖单时)或 卖1价(下买单时)