ส่งและรับข้อความ¶
บทนำ ¶
บทความนี้เป็นการแนะนำการใช้ FIX API สำหรับผู้ที่สนใจในการโต้ตอบกับ Spotware cServer โดยใช้ FIX
ในบทความนี้ เราจะใช้ตัวอย่าง C# เพื่ออธิบายหลักการในการสร้างข้อความ FIX ส่งไปยังเซิร์ฟเวอร์ และรับการตอบกลับอย่างละเอียด ตัวอย่างนี้ไม่ใช่แอปพลิเคชันที่สมบูรณ์แบบและถูกทำให้ง่ายที่สุดเท่าที่จะเป็นไปได้เพื่อให้โปรแกรมเมอร์เข้าใจแนวคิดของการใช้ข้อความ FIX API ได้ง่าย
เพื่อสร้างและรักษาการสื่อสารที่เหมาะสมกับเซิร์ฟเวอร์และการจัดการการตอบกลับที่เหมาะสม จำเป็นต้องมีฟังก์ชันการทำงานเพิ่มเติม ซึ่งถูกข้ามไปเพื่อความเรียบง่ายและชัดเจน เราจะจัดการกับหัวข้อเหล่านี้ในบทความในอนาคต
ตัวอย่างโค้ด ¶
คุณสามารถหาตัวอย่างโค้ดที่กล่าวถึงในบทความนี้ได้ที่ GitHub repository ของเรา
ภาพรวมของการสื่อสาร FIX ¶
ข้อความ FIX เป็นเพียงสตริงที่ประกอบด้วยชุดของแท็กตัวเลขและค่าที่คั่นด้วยเครื่องหมายแนวตั้ง (|) แต่ละแท็กแทนฟิลด์ที่แตกต่างกันซึ่งอนุญาตให้ใช้ค่าชุดหนึ่ง ด้านล่างนี้คุณสามารถเห็นตัวอย่างข้อความ FIX ที่ร้องขอการตรวจสอบสิทธิ์จากเซิร์ฟเวอร์
8=FIX.4.4|9=126|35=A|49=theBroker.12345|56=CSERVER|34=1|52=20170117- 08:03:04|57=TRADE|50=any_string|98=0|108=30|141=Y|553=12345|554=passw0rd!|10=131|
ดังที่คุณเห็น รูปแบบที่ซ้ำกันในแต่ละข้อความ FIX คือ:
Tag=Value|Tag=Value|Tag=Value|...
ขึ้นอยู่กับวัตถุประสงค์ของแต่ละข้อความ จำเป็นต้องใช้ชุดของแท็กและค่าที่แตกต่างกันในแต่ละครั้ง แท็กและค่าที่จำเป็นสำหรับแต่ละข้อความถูกอธิบายไว้อย่างละเอียดใน cTrader FIX engine Rules of Engagement (ตรวจสอบ rules of engagement ล่าสุดเสมอ)
ในทำนองเดียวกัน การตอบกลับจะถูกส่งกลับมาจากเซิร์ฟเวอร์ ด้านล่างนี้คุณสามารถเห็นการตอบกลับของเซิร์ฟเวอร์สำหรับข้อความข้างต้น
8=FIX.4.4|9=106|35=A|34=1|49=CSERVER|50=TRADE|52=20170117- 08:03:04.509|56=theBroker.12345|57=any_string|98=0|108=30|141=Y|10=066|
ขั้นตอนที่เกี่ยวข้องในกระบวนการสื่อสารกับเซิร์ฟเวอร์ FIX มีดังนี้:
-
สร้างข้อความ FIX
-
ส่งข้อความ FIX
-
รับข้อความ FIX
-
แยกวิเคราะห์ข้อความ FIX
ข้อความ FIX แบบดิบไม่ใช่รูปแบบที่อ่านง่ายนัก เนื่องจากถูกออกแบบมาโดยคำนึงถึงประสิทธิภาพมากกว่าความเข้าใจง่าย ดังนั้น สำหรับแต่ละแอปพลิเคชันซอฟต์แวร์ จะต้องมีกระบวนการแปลข้อมูลที่ให้มาเป็นข้อความ FIX ที่เกี่ยวข้องเสมอ
ในแอปพลิเคชันตัวอย่าง C# ของเรา เราได้สร้างคลาสสำหรับจัดการการสร้างข้อความ รวมถึงฟังก์ชันสำหรับสร้างข้อความ FIX ตามข้อมูลที่เกี่ยวข้อง
หลังจากสร้างข้อความแล้ว ข้อความจะถูกส่งระหว่างเซิร์ฟเวอร์และไคลเอ็นต์ผ่านอินเทอร์เน็ตโดยใช้ซ็อกเก็ตเครือข่าย เมื่อได้รับข้อความ จำเป็นต้องแยกวิเคราะห์เพื่อนำเสนอในรูปแบบที่อ่านได้
ในบทความนี้ เราจะครอบคลุมกระบวนการสร้าง การส่ง และการรับการตอบกลับ เราจะจัดการกับการแยกวิเคราะห์ในบทความในอนาคต
สร้างข้อความ FIX ¶
โครงสร้างข้อความ ¶
ในแอปพลิเคชันตัวอย่างของเรา เราได้สร้างคลาสที่รับผิดชอบในการสร้างข้อความ FIX คลาสนี้เรียกว่า MessageConstructor และสามารถพบได้ในโปรเจกต์ FIX API Library
MessageConstructor ถูกเริ่มต้นด้วยพารามิเตอร์ต่อไปนี้:
-
Host(*)– ที่อยู่ที่ cServer ของเราตั้งอยู่ -
Username(*)– หมายเลขบัญชี -
Password(*)– รหัสผ่าน -
SenderCompID(*)– มีให้ในแบบฟอร์ม FIX API ของ cTrader อยู่ในรูปแบบ -
SenderSubID*– เป็นส่วนที่สองของ SenderCompID -
TargetCompID(*)– มีให้ในแบบฟอร์ม FIX API ของ cTrader (โดยปกติคือ cServer)
คุณสามารถหาข้อมูลนี้ได้ในแบบฟอร์ม cTrader FIX API ของคุณ
หลังจากที่เราได้เริ่มต้น MessageConstructor แล้ว เราก็พร้อมที่จะสร้างข้อความ FIX API
ข้อความทั้งหมดถูกสร้างขึ้นในลักษณะที่คล้ายกัน ด้านล่างนี้เป็นตัวอย่างโค้ดของการสร้างข้อความ Logon
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 | |
คุณจะเห็นว่าเราสร้างส่วนของเนื้อหาก่อน จากนั้นเราส่งไปยังฟังก์ชันส่วนหัว และสุดท้ายเราส่งทั้งสองส่วนไปยังฟังก์ชันส่วนท้าย 3 ส่วนนี้มีรายละเอียดด้านล่าง
กระบวนการสร้างข้อความเป็นเพียงการเพิ่มแท็ก ค่า และตัวคั่นที่จำเป็นลงในสตริง
เนื้อหา ¶
ก่อนอื่นเราจะเริ่มด้วยการอธิบายการสร้างเนื้อหา เนื่องจากเนื้อหาของข้อความต้องถูกสร้างขึ้นก่อน เราสามารถเห็นตัวอย่างด้านบน (การสร้างข้อความ Logon)
เราเริ่มต้นด้วยการเริ่มต้นคลาส StringBuilder และเราเพิ่มแท็กทีละตัวตามอินพุตของฟังก์ชัน ขึ้นอยู่กับประเภทของข้อความ เนื้อหาต้องประกอบด้วยชุดของแท็กที่แตกต่างกัน บางส่วนเป็นแท็กที่จำเป็นและบางส่วนเป็นแท็กที่เลือกได้
คุณสามารถหาโครงสร้างของแต่ละข้อความได้ใน Rules of Engagement ของเรา (/FIX)
จากนั้นเราสร้างส่วนหัวสำหรับข้อความ Logon และเพิ่มเนื้อหาของข้อความเข้าไป สุดท้าย โดยใช้สตริง headerAndBody เราสร้างส่วนท้าย ต่อไปเราจะเห็นวิธีที่เราสร้างส่วนหัวและส่วนท้าย
ส่วนหัว ¶
ส่วนหัวเป็นส่วนแรกของข้อความ FIX และประกอบด้วยฟิลด์ต่อไปนี้ (เหมือนกันสำหรับทุกข้อความ):
BeginString– begin string กำหนดเวอร์ชันโปรโตคอล FIX และในกรณีของเราคือ FIX4.4BodyLength– body length ระบุความยาวของข้อความเป็นตัวอักษร ไม่รวมBeginString,BodyLengthและฟิลด์ส่วนท้ายMsgType– ในฟิลด์นี้เรากำหนดประเภทของข้อความ เพื่อให้ผู้รับรู้วิธีแยกวิเคราะห์เนื้อหาSenderCompID– ที่นี่เราตั้งค่าSenderCompIDTargetCompID– นี่คือเป้าหมายของข้อความของเรา ในกรณีของเรา จะเป็น cServer เสมอSenderSubID– การเข้าสู่ระบบของนักเทรดMsgSeqNum– นี่คือหมายเลขลำดับของข้อความ จำเป็นต้องเพิ่มขึ้นสำหรับแต่ละข้อความที่ส่งในเซสชันเดียวกันSending Time– เวลาที่ส่งข้อความ
ด้านล่างนี้คุณสามารถเห็นฟังก์ชัน ConstructHeader ที่รับผิดชอบในการสร้างส่วนหัว
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 | |
ส่วนท้าย ¶
ส่วนท้ายเป็นเพียงแท็กที่มีผลรวมตรวจสอบของส่วนที่เหลือของข้อความ
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | |
ข้อความระบบ ¶
ตัวอย่างของเรามีฟังก์ชันที่ส่งคืนข้อความระบบต่อไปนี้:
- การเต้นของหัวใจ:
MessageConstructor.HeartbeatMessage() - คำขอทดสอบ:
MessageConstructor.TestRequestMessage() - การเข้าสู่ระบบ:
MessageConstructor.LogonMessage() - การออกจากระบบ:
MessageConstructor.LogoutMessage() - คำขอส่งซ้ำ:
MessageConstructor.ResendMessage() - การปฏิเสธ:
MessageConstructor.RejectMessage() - การรีเซ็ตลำดับ:
MessageConstructor.SequenceReset
ข้อความของแอปพลิเคชัน ¶
ตัวอย่างของเราประกอบด้วยฟังก์ชันที่ส่งคืนข้อความระบบต่อไปนี้:
- คำขอข้อมูลตลาด:
MessageConstructor.HeartbeatMessage() - สแนปช็อตตลาด/รีเฟรชเต็มรูปแบบ:
MessageConstructor.MarketDataSnapshotMessage() - รีเฟรชข้อมูลตลาดแบบเพิ่มขึ้น:
MessageConstructor.MarketDataIncrementalRefreshMessage() - คำสั่งซื้อขายใหม่เดี่ยว:
MessageConstructor.NewOrderSingleMessage() - คำขอสถานะคำสั่งซื้อขาย:
MessageConstructor.OrderStatusRequest() - รายงานการดำเนินการ:
MessageConstructor.ExecutionReport() - การปฏิเสธข้อความทางธุรกิจ:
MessageConstructor.BusinessMessageReject() - คำขอสำหรับตำแหน่ง:
MessageConstructor.RequestForPositions() - รายงานตำแหน่ง:
MessageConstructor.PositionReport()
ส่งข้อความและรับการตอบกลับ ¶
ในการส่งข้อความ FIX ไปยัง cServer คุณต้องสร้างการเชื่อมต่อกับเซิร์ฟเวอร์ก่อน คุณสามารถทำได้โดยการสร้าง TcpClient ในกรณีของเรา เราสร้างไคลเอนต์สองตัว เนื่องจากข้อความการเสนอราคาและข้อความการซื้อขายจะถูกจัดการโดยพอร์ตที่แตกต่างกันบนเซิร์ฟเวอร์
จากนั้น เราต้องรับสตรีมสองสตรีมที่จะใช้ส่งข้อความ กระบวนการนี้เกิดขึ้นในคอนสตรักเตอร์ของฟอร์มดังที่แสดงด้านล่าง:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | |
ในคอนสตรักเตอร์ เรายังเริ่มต้นคลาส MessageConstructor ซึ่งจะใช้สำหรับการสร้างข้อความ
ต่อไป เพื่อส่งข้อความ เราได้สร้างฟังก์ชันสองฟังก์ชัน คือ SendPriceMessage() และ SendTradeMessage() แต่ละฟังก์ชันรับข้อความ FIX เป็นอินพุตและจากนั้นเรียกฟังก์ชัน SendMessage() โดยใช้ข้อความและสตรีมที่เกี่ยวข้องเป็นอินพุต
ฟังก์ชัน SendMessage() ทำงานดังนี้:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | |
ขั้นตอนโดยละเอียดมีดังนี้:
- เข้ารหัสข้อความเป็นอาร์เรย์ไบต์
- เขียนอาร์เรย์ไบต์ลงในสตรีม
- อ่านการตอบกลับจากสตรีม
- เพิ่มหมายเลขลำดับข้อความ
- เข้ารหัสข้อความเป็นสตริง
ฟังก์ชันควรส่งคืนข้อความ FIX ที่ส่งโดยเซิร์ฟเวอร์
ตามที่คุณคาดไว้ คุณไม่สามารถแสดงข้อความ FIX แบบดิบให้ผู้ใช้เห็นได้ ดังนั้นจึงควรพัฒนาขั้นตอนเพิ่มเติมในการแยกวิเคราะห์ข้อความขาเข้า
บทสรุป ¶
แอปพลิเคชันนี้เป็นการสาธิตสั้น ๆ เกี่ยวกับวิธีการสื่อสารกับ cServer โดยใช้ข้อความ FIX เป็นเพียงตัวอย่างที่แสดงแนวคิดของโปรโตคอล FIX และไม่ใช่เอ็นจิน FIX เต็มรูปแบบแต่อย่างใด หากคุณต้องการหลีกเลี่ยงการสร้างเอ็นจิน FIX ของคุณเอง คุณอาจพิจารณาใช้เอ็นจิน FIX ของบุคคลที่สามที่มีอยู่
หมายเหตุ
บทความนี้เป็นปัจจุบันเมื่อวันที่ 03/02/2017 และพัฒนาขึ้นโดยคำนึงถึงเอ็นจิน FIX ของ cTrader, Rules of Engagement v2.9.1