上周帮一个做黄金EA的朋友排查延迟问题,他跑的是马丁格尔策略,欧美盘经常出现订单流断层,结果一查MT5日志,发现滑点根本不是市场波动造成的,而是日志里藏着几个关键参数在作祟。这事让我想起自己刚入行时,也总以为滑点就是网络延迟或流动性不足,后来才发现,很多时候元凶就在MT5的日志文件里,只是我们没耐心去一行行翻。
先说个最典型的坑:很多老手喜欢用 OrderSendAsync() 异步下单,觉得能提升执行速度,但MT5的日志里,这类订单的返回状态经常是 TRADE_RETCODE_PLACED(10008) 而不是直接的成功代码。我遇到过好几次,EA在日志里显示订单已发送,但实际没成交,就是因为异步模式下,订单流被挂起,而EA的后续逻辑还在跑,导致重复下单或漏单。所以,排查时一定要先看日志里有没有 “OrderSendAsync” 字样,然后对比实际账户历史记录,看订单是否真的落地了。
如果日志里频繁出现 “Requote” 或 “Price changed” 提示,那就要小心了。这是MT5在告诉你,你EA里的当前报价和服务器撮合时的价格不一致。我见过有人把 SYMBOL_TRADE_EXECUTION 设成 EXECUTION_REQUEST 模式,结果在黄金波动大的时候,订单流里全是 Requote,滑点直接奔着3-5点去。正确做法是先去MT5的 “工具”->“选项”->“EA交易” 里,把 “允许实时自动交易” 勾上,然后检查 SymbolInfoInteger() 里的执行模式,如果是 EXECUTION_REQUEST,就得在代码里加 SYMBOL_TRADE_EXECUTION 的判断,或者改用 OrderSend() 同步模式,虽然慢点,但至少日志能直接反馈成交价。
具体排查步骤,我一般按这个顺序来:
还有一个容易被忽略的点:MT5的日志默认只保留 7天 的历史,但如果你用VPS,建议改成 30天 以上。在 “工具”->“选项”->“日志” 里调整 “日志存储天数”,这样能追溯更久前的订单流异常。我有个朋友跑英镑兑美元EA,日志里总是出现 “OrderDelete” 后跟 “OrderSend” 的时间差超过 500毫秒,结果查了30天前的日志才发现,是VPS的CPU被某个进程占满导致的。
最后说个实战技巧:如果你发现日志里 “OrderSend” 和 “OrderCheck” 之间间隔超过 100毫秒,那大概率是VPS或经纪商服务器的问题。可以用 Ping 命令测一下延迟,或者干脆换个低延迟的VPS。我自己用 AWS EC2 东京节点跑黄金EA,日志里订单流间隔基本在 20-50毫秒 内,滑点控制在1点以内。但如果你日志里全是 “Timeout” 或者 “Connection closed”,那就别指望日志能救你,直接换经纪商吧。
你们有没有遇到过日志里 “retcode” 是 10008 但订单没成交的情况?来分享一下排查过程,咱们一起讨论下怎么优化MT5的订单流监控。
先说个最典型的坑:很多老手喜欢用 OrderSendAsync() 异步下单,觉得能提升执行速度,但MT5的日志里,这类订单的返回状态经常是 TRADE_RETCODE_PLACED(10008) 而不是直接的成功代码。我遇到过好几次,EA在日志里显示订单已发送,但实际没成交,就是因为异步模式下,订单流被挂起,而EA的后续逻辑还在跑,导致重复下单或漏单。所以,排查时一定要先看日志里有没有 “OrderSendAsync” 字样,然后对比实际账户历史记录,看订单是否真的落地了。
如果日志里频繁出现 “Requote” 或 “Price changed” 提示,那就要小心了。这是MT5在告诉你,你EA里的当前报价和服务器撮合时的价格不一致。我见过有人把 SYMBOL_TRADE_EXECUTION 设成 EXECUTION_REQUEST 模式,结果在黄金波动大的时候,订单流里全是 Requote,滑点直接奔着3-5点去。正确做法是先去MT5的 “工具”->“选项”->“EA交易” 里,把 “允许实时自动交易” 勾上,然后检查 SymbolInfoInteger() 里的执行模式,如果是 EXECUTION_REQUEST,就得在代码里加 SYMBOL_TRADE_EXECUTION 的判断,或者改用 OrderSend() 同步模式,虽然慢点,但至少日志能直接反馈成交价。
具体排查步骤,我一般按这个顺序来:
- 第一步:打开MT5终端,按 Ctrl+T 调出“工具箱”,切换到“日志”选项卡,然后清空旧日志(右键点“清除”),再跑一次EA,只看新生成的日志。重点找 “OrderSend” 和 “OrderCheck” 开头的行,特别是 “retcode” 后面的数字,比如 10009(TRADE_RETCODE_TIMEOUT) 或 10015(TRADE_RETCODE_INVALID_PRICE)。
- 第二步:如果日志里出现 “Price is outdated”,说明你的EA引用了过时的报价。这时去检查 MarketInfo() 或 SymbolInfoTick() 的调用频率,别让EA在 OnTick() 里死循环。我习惯在策略里加个 static datetime lastTickTime 变量,确保每秒只读取一次报价,减少日志里的无效报错。
- 第三步:用 “Expert Advisor”->“属性”->“常用” 里的 “允许DLL调用” 和 “允许导入外部函数”,这两个选项如果没勾,日志里会报 “CALL_FUNCTION_NOT_ALLOWED” 错误,导致订单流卡死。我踩过这坑,当时EA跑得好好的,突然滑点暴增,一查日志全是被拒绝的DLL调用。
- 第四步:重点看 “OrderSend” 后的 “ticket” 值。如果日志里 ticket 是 “-1”,说明下单失败,要立刻去检查 GetLastError() 返回的代码,比如 4109(TRADE_RETCODE_INVALID_EXPIRATION) 或 4108(TRADE_RETCODE_INVALID_STOPS)。我遇到过最离谱的是因为止损设得太近,日志里全是 “Invalid stops”,滑点直接翻倍。
还有一个容易被忽略的点:MT5的日志默认只保留 7天 的历史,但如果你用VPS,建议改成 30天 以上。在 “工具”->“选项”->“日志” 里调整 “日志存储天数”,这样能追溯更久前的订单流异常。我有个朋友跑英镑兑美元EA,日志里总是出现 “OrderDelete” 后跟 “OrderSend” 的时间差超过 500毫秒,结果查了30天前的日志才发现,是VPS的CPU被某个进程占满导致的。
最后说个实战技巧:如果你发现日志里 “OrderSend” 和 “OrderCheck” 之间间隔超过 100毫秒,那大概率是VPS或经纪商服务器的问题。可以用 Ping 命令测一下延迟,或者干脆换个低延迟的VPS。我自己用 AWS EC2 东京节点跑黄金EA,日志里订单流间隔基本在 20-50毫秒 内,滑点控制在1点以内。但如果你日志里全是 “Timeout” 或者 “Connection closed”,那就别指望日志能救你,直接换经纪商吧。
你们有没有遇到过日志里 “retcode” 是 10008 但订单没成交的情况?来分享一下排查过程,咱们一起讨论下怎么优化MT5的订单流监控。