2011/06/29

MT4用EA開発時代 - なんで「ERR_NO_RESULT」やねん。。



さて前回は、共通部品「ahfw」ベータ版バージョンアップのお知らせをしました。今回は、予告と異なり、デモ口座で発生した「ERR_NO_RESULT」について書いてみたいと思います。


ぼちぼち「プロセス障害/サーバ障害対応」について書こうかなぁって思って就寝。
そして翌朝、MT4用EAからエラーメール受信。


致命的エラーで

新規発注停止状態に。
 
(これは致命的エラーであれば意図的にそうしてる)


さっそくログを見てみると、OrderSend()で、「ERR_NO_RESULT」返却されていた。。
このエラーコードをヘルプでは、本来OrderModify()でしか発生しないエラー。
逆に言うと、OrderSend()/OrderClose()/OrderDelete()で「ERR_NO_RESULT」が発生したらおかしいのでクリティカルエラーにしていた。

●「ERR_NO_RESULT
 OrderModify attempts to replace the values already set with the same values. 
  One or more values must be changed, then modification attempt can be repeated.
  OrderModify は、既に設定された値を同じ値に置換しようとしています。1つ、あるいはそれ
  以上の値が変更されることで、修正を再試行できます。







明らかにMT4のバグやん。。





でも、MT4のバグだからといって、発生しうるのであれば放っておく訳にもいかず、どうするか考えて見る事にした。

まずは、ログの内容。
EAのソースは、前回記事で公開したソースです。。。


【発生時のログの内容】
--------------------------
●「Expert」タブ上のログ
08:40:16 SmoothMADILong USDCHFfxf.,M5: [[DEBUG]](1.1R):Tick(140014609)FWModifyOrder():START!!
08:40:18 SmoothMADILong USDCHFfxf.,M5: modify #5693883 sell 0.47 USDCHFfxf. at 0.8359 sl: 0.8365 tp: 0.0000 ok
08:40:18 SmoothMADILong USDCHFfxf.,M5: [[DEBUG]](1.1R):Tick(140015156)FWModifyOrder():END!! SlPrice(0.83650000) , TargetPrice(0.00000000)
08:40:19 SmoothMADILong USDJPYfxf.,M5: [[DEBUG]](1.1R):Tick(140018296)[[CALLBACK]]:EAOnBarChanged was called
08:40:19 SmoothMADILong USDJPYfxf.,M5: [[DEBUG]](1.1R):Tick(140018296)FWModifyOrder():START!!
08:40:19 SmoothMADILong USDJPYfxf.,M5: [[DEBUG]](1.1R):Tick(140018296)FWModifyOrder():END!! : Specified SL price is far from previous SL 
08:40:19 Sample1 EURJPYfxf.,M5: [[DEBUG]](1.1R):Tick(140018312)FWToOrder() : Decided to order
08:40:19 Sample1 EURJPYfxf.,M5: [[DEBUG]](1.1R):Tick(140018312)FWSendOrderOrdinary():START!!
08:41:38 Sample1 EURJPYfxf.,M5: [[CRITICAL]][DEMO][FOREX.com Japan][TEST1]EURJPYfxf.(Sample1:51209945)(Ticket:5693883)SendOrder:Unknown error : cmd(-1),lots(0.01000000),openPrice(115.67000000),OrderSlippage(5),vSlPrice(115.78000000),Ask(115.71000000),Bid(115.67000000):errno:1:no error
●「操作履歴上」のログ
08:40:18 '143524': modify order #5693883 sell 0.47 USDCHFfxf. at 0.8359 sl: 0.8367 tp: 0.0000 -> sl: 0.8365 tp: 0.0000
08:40:19 '143524': request was accepted by server
08:40:19 '143524': request in process
08:40:19 '143524': order #5693883 sell 0.47 USDCHFfxf. at 0.8359 was modified -> sl: 0.8365 tp: 0.0000
08:40:22 '143524': instant order sell 0.01 EURJPYfxf. at 115.67 sl: 115.78 tp: 115.62
08:41:30 '143524': login
08:41:37 '143524': login
08:41:39 Mail: '[[CRITICAL]][DEMO][FOREX.com Japan][TEST1] EURJPYfxf.(5693883):SendOrder:Unknown error : cmd(-1),lots(0.01000000),openPrice(115' has been sent
08:41:41 '143524': modify order #5694006 buy 0.57 GBPUSDfxf. at 1.5982 sl: 1.5969 tp: 0.0000 -> sl: 1.5970 tp: 0.0000
08:41:41 '143524': request was accepted by server
08:41:41 '143524': request in process
08:41:41 '143524': order #5694006 buy 0.57 GBPUSDfxf. at 1.5982 was modified -> sl: 1.5970 tp: 0.0000
-----------------------------


「Expert」タブ上のログ最終行の「errno:1:no error」が、ERR_NO_RESULTの事。
対応する「操作履歴上」のログ上の箇所は、「Mail:・・・・」の行。

【考察】
------------------------------
まず一番不穏なのは、「操作履歴上」のログで検出した行の、直前の「login」2連発。
しかも通信障害であれば、普通connect failed [回線不通!]とか、cannot login [No connection]
が出力されるけど、それも出てない。当然、その後通常であれば出力される「request was accepted by server」も出力されてない。そして今回の事象が発生。








なんか、突然フラれて

しかもダマされた気分

 



ここからは仮説だけど、トレード操作時はセッションが生きてても毎回ログイン処理していて、サーバ側の障害か何かでログインに2連続で失敗。問題は、この時に「ERR_NO_RESULT」が返却されてしまう事。
よくよく「ERR_NO_RESULT」というエラーの本来の意味を考えると、クライアント上で持っているデータで判断できる様なエラー。

●発生条件の仮説
 事象の発生条件について仮説を立てると、オーダ操作時のログイン時に、通信異常以外の
 理由でエラー
が発生してリトライアウトすると、「ERR_NO_RESULT」になってしまうという MT4クライアント側のバグ。

ちなみに、発生したMT4は、以下。
 「FOREX.com Japan Version: 4.00 Build 229(26 Nov 2010)」

そして実は、LiveUpdateで「Build 401」ダウンロード画面が出る様になってたので、修正されてないかなぁって思って調べてみたけど、修正されてない。。

なので、アップデートしても治らない。
#しかも、「DLLクラッシュしてもMT4クライアントに影響出ない様に修正」みたいな事書かれてるから、これをインストールしちゃうと、
 MT4プロセス障害試験が
できなくなってしまう。。。。
------------------------------

さて、月並みだけど、共通部品「ahfw」でどう対処するか考えてみた。

共通部品「ahfw」での対処方法】
------------------------------
1.OrderSend()で発生した場合
  普通にリトライするのも手なんだけど、MT4側とはいえバグはバグ。
  バグが顕在化してるのに、発注で普通にリトライするのも少し怖いので、
  以前の「ERR_TRADE_TIMEOUT/142/143発生時の処理方式検討という記事で
  書いたのと似た様な方式にすることに。
  つまり、以下。
  一旦start()関数を抜けて、1分経過後再度OrderSend()する。
  OrderSend()成功したチケット以外に残存ゴミポジションが残っていたら削除する。
   そして今回はさらに、警告メールとログ出力して、新規発注停止にはしない様にした。

2.OrderClose() / OrderDelete()で発生した場合
  これは迷った。なぜなら、まだ発生してないから。最初は発生してから対処しようかとも
  思ったけど、PCが不安定で発生するエラーじゃないので、対処することにした。
  対処方法は以下。
  警告メールとログ出力。新規発注停止状態にはしない。
  一旦start()関数を抜けて、次ティックデータ受信時にリトライ
   発注とは違って、リスク増大の危険が少ないので。
   start()内で短時間でリトライすると、前述の警告メール大量受信しそうなので、
   あえて一旦start()を抜けて、次ティックデータを待つ事に。
------------------------------









しかし、これは良く知られた事象なんだろうか?

それとも、またしてもビックリ事象なんだろうか?




  
そして、レアケースなエラーを検出して喜びながら、「FXシステムトレード初心者奮闘記」の「MT4用EA開発時代」は、「プロセス障害/サーバ障害対応」と、今回の修正版リリースに進むのでした。
#修正作業自体は終わってるけど、リリースはせめて一晩はデモ口座で流してからしたいので。。。

0 件のコメント:

コメントを投稿