From dc0bc5b34208f843fe1034e9c94d311e0a23bf05 Mon Sep 17 00:00:00 2001 From: Rob Johnston Date: Wed, 10 Oct 2018 19:14:55 -0400 Subject: [PATCH] Feat: Deserialize message frame payload into object and include classes for public responses. --- README.md | 158 +++++++++++------- src/AlphaPoint.Api/Models/Enums/ActionType.cs | 23 +++ src/AlphaPoint.Api/Models/Enums/ErrorCode.cs | 35 ++++ .../Models/Enums/InstrumentType.cs | 18 ++ .../Models/Enums/ProductType.cs | 19 +++ .../Models/Enums/SessionStatus.cs | 11 ++ src/AlphaPoint.Api/Models/Enums/Side.cs | 28 ++++ src/AlphaPoint.Api/Models/MessageFrame.cs | 10 ++ .../Models/Responses/GenericResponse.cs | 40 +++++ .../Models/Responses/Instrument.cs | 96 +++++++++++ .../Models/Responses/Level2Snapshot.cs | 92 ++++++++++ src/AlphaPoint.Api/Models/Responses/Pong.cs | 13 ++ .../Models/Responses/Product.cs | 51 ++++++ 13 files changed, 535 insertions(+), 59 deletions(-) create mode 100644 src/AlphaPoint.Api/Models/Enums/ActionType.cs create mode 100644 src/AlphaPoint.Api/Models/Enums/ErrorCode.cs create mode 100644 src/AlphaPoint.Api/Models/Enums/InstrumentType.cs create mode 100644 src/AlphaPoint.Api/Models/Enums/ProductType.cs create mode 100644 src/AlphaPoint.Api/Models/Enums/SessionStatus.cs create mode 100644 src/AlphaPoint.Api/Models/Enums/Side.cs create mode 100644 src/AlphaPoint.Api/Models/Responses/GenericResponse.cs create mode 100644 src/AlphaPoint.Api/Models/Responses/Instrument.cs create mode 100644 src/AlphaPoint.Api/Models/Responses/Level2Snapshot.cs create mode 100644 src/AlphaPoint.Api/Models/Responses/Pong.cs create mode 100644 src/AlphaPoint.Api/Models/Responses/Product.cs diff --git a/README.md b/README.md index ec99c77..6876cc2 100644 --- a/README.md +++ b/README.md @@ -9,8 +9,10 @@ A future version will use this as a base to more easily consume API methods and ```csharp using AlphaPoint.Api; using AlphaPoint.Api.Models; +using AlphaPoint.Api.Models.Responses; using Newtonsoft.Json; using System; +using System.Collections.Generic; using System.Threading; using System.Threading.Tasks; @@ -28,7 +30,7 @@ namespace ConsoleApp1 task.Wait(); // Keep the console window open. - Console.WriteLine("Press key to exit."); + Console.WriteLine("\nPress key to exit."); ConsoleKeyInfo keyInfo = Console.ReadKey(); while (keyInfo.Key != ConsoleKey.Enter) keyInfo = Console.ReadKey(); @@ -54,7 +56,26 @@ namespace ConsoleApp1 Console.WriteLine(" m > " + e.MessageFrameResponse.MessageType); Console.WriteLine(" i > " + e.MessageFrameResponse.SequenceNumber); Console.WriteLine(" n > " + e.MessageFrameResponse.FunctionName); - Console.WriteLine(" o > " + e.MessageFrameResponse.Payload); + //Console.WriteLine(" o > " + e.MessageFrameResponse.Payload); + Console.WriteLine(); + + // Demo how to work with the result. + if (e.MessageFrameResponse.FunctionName == "GetL2Snapshot") + { + var l2 = e.MessageFrameResponse.PayloadAs>(); + + Console.WriteLine($"{"Date/Time",22} |{"Type",8} |{"Price",10} |{ "Quantity",11} |{"Side",5}"); + Console.WriteLine(new string('-', 65)); + + foreach (var item in l2) + { + Console.WriteLine($"{PosixTimeStampToDateTime(item.ActionDateTime),22} |" + + $"{item.ActionType,8} |" + + $"{item.Price.ToString("N2"),10} |" + + $"{item.Quantity.ToString("N8"),11} |" + + $"{item.Side,5}"); + } + } ExitEvent.Set(); }; @@ -81,6 +102,13 @@ namespace ConsoleApp1 ExitEvent.WaitOne(); } } + + public static DateTime PosixTimeStampToDateTime(double timeStamp) + { + DateTime dt = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc); + dt = dt.AddMilliseconds(timeStamp).ToLocalTime(); + return dt; + } } } ``` @@ -92,64 +120,76 @@ MessageFrame received: m > Reply i > 2 n > GetL2Snapshot - o > [[33653795,1,1539134020119,0,8550,1,8449.81,1,7,0], -[33653795,1,1539134020119,0,8550,1,8449.43,1,1.21310602,0], -[33653795,1,1539134020119,0,8550,1,8448.67,1,0.07465268,0], -[33653795,1,1539134020119,0,8550,1,8448.29,1,0.14189868,0], -[33653795,1,1539134020119,0,8550,1,8448.16,1,2.95022608,0], -[33653795,1,1539134020119,0,8550,1,8447.27,1,0.00253175,0], -[33653795,1,1539134020119,0,8550,1,8447.14,1,0.93315848,0], -[33653795,1,1539134020119,0,8550,1,8446.76,1,0.01014973,0], -[33653795,1,1539134020119,0,8550,1,8446.38,1,2.23211508,0], -[33653795,1,1539134020119,0,8550,1,8446.25,1,0.00922703,0], -[33653795,1,1539134020119,0,8550,1,8446,1,1.39973772,0], -[33653795,1,1539134020119,0,8550,1,8444.35,1,4.54448179,0], -[33653795,1,1539134020119,0,8550,1,8444.22,1,0.1403765,0], -[33653795,1,1539134020119,0,8550,1,8443.71,1,0.13997377,0], -[33653795,1,1539134020119,0,8550,1,8443.46,1,1.17992127,0], -[33653795,1,1539134020119,0,8550,1,8443.2,1,7,0], -[33653795,1,1539134020119,0,8550,1,8443.07,1,0.56167038,0], -[33653795,1,1539134020119,0,8550,1,8442.82,1,1.27881168,0], -[33653795,1,1539134020119,0,8550,1,8442.69,1,3.82594977,0], -[33653795,1,1539134020119,0,8550,1,8442.18,1,0.21066443,0], -[33653795,1,1539134020119,0,8550,1,8441.93,1,2.3328962,0], -[33653795,1,1539134020119,0,8550,1,8441.8,1,0.84265773,0], -[33653795,1,1539134020119,0,8550,1,8441.68,1,0.37326339,0], -[33653795,1,1539134020119,0,8550,1,8441.55,1,2.26066101,0], -[33653795,1,1539134020119,0,8550,1,8441.42,1,0.1866317,0], -[33653795,1,1539134020119,0,8550,1,8349.0077,1,1.67684598,0], -[33653795,2,1539134020119,0,8550,2,8200,1,0.21392684,0], -[33653795,0,1539134020119,0,8550,1,0.01,1,31,0], -[33653795,1,1539134020119,0,8550,1,8550,1,1.62613,1], -[33653795,1,1539134020119,0,8550,1,8600,1,2,1], -[33653795,1,1539134020119,0,8550,1,8700,1,2,1], -[33653795,1,1539134020119,0,8550,1,8751.73,1,7,1], -[33653795,1,1539134020119,0,8550,1,8751.86,1,0.38479167,1], -[33653795,1,1539134020119,0,8550,1,8752.25,1,0.1,1], -[33653795,1,1539134020119,0,8550,1,8752.38,1,0.12,1], -[33653795,1,1539134020119,0,8550,1,8752.78,1,0.41444587,1],[ -33653795,1,1539134020119,0,8550,1,8753.96,1,0.011,1], -[33653795,1,1539134020119,0,8550,1,8754.1,1,1.20780263,1], -[33653795,1,1539134020119,0,8550,1,8754.23,1,0.01,1], -[33653795,1,1539134020119,0,8550,1,8756.2,1,0.17919283,1], -[33653795,1,1539134020119,0,8550,1,8756.33,1,0.4,1], -[33653795,1,1539134020119,0,8550,1,8756.47,1,0.27796986,1], -[33653795,1,1539134020119,0,8550,1,8756.6,1,0.63324654,1], -[33653795,1,1539134020119,0,8550,1,8756.73,1,0.18190475,1], -[33653795,1,1539134020119,0,8550,1,8757.26,1,0.02199081,1], -[33653795,1,1539134020119,0,8550,1,8757.39,1,1.98,1], -[33653795,1,1539134020119,0,8550,1,8757.52,1,0.28644275,1], -[33653795,1,1539134020119,0,8550,1,8757.65,1,0.12800312,1], -[33653795,1,1539134020119,0,8550,1,8757.78,1,0.3,1], -[33653795,1,1539134020119,0,8550,1,8757.92,1,0.026,1], -[33653795,1,1539134020119,0,8550,1,8758.05,1,0.22575335,1], -[33653795,1,1539134020119,0,8550,1,8758.18,1,7,1], -[33653795,1,1539134020119,0,8550,1,8758.44,1,0.2,1], -[33653795,1,1539134020119,0,8550,1,8758.57,1,0.13885664,1], -[33653795,1,1539134020119,0,8550,1,8758.71,1,0.65440634,1], -[33653795,1,1539134020119,0,8550,1,8758.84,1,0.1772403,1], -[33653795,1,1539134020119,0,8550,1,8800,1,2,1]] + + Date/Time | Type | Price | Quantity | Side +----------------------------------------------------------------- + 2018-10-10 6:52:31 PM | New | 8,530.00 | 0.70344880 | Buy + 2018-10-10 6:52:31 PM | New | 8,500.00 | 0.01300000 | Buy + 2018-10-10 6:52:31 PM | New | 8,460.01 | 0.63737062 | Buy + 2018-10-10 6:52:31 PM | New | 8,459.89 | 0.57906748 | Buy + 2018-10-10 6:52:31 PM | New | 8,459.37 | 0.02523204 | Buy + 2018-10-10 6:52:31 PM | New | 8,459.12 | 0.13396543 | Buy + 2018-10-10 6:52:31 PM | New | 8,458.86 | 0.39436493 | Buy + 2018-10-10 6:52:31 PM | New | 8,458.48 | 0.00572819 | Buy + 2018-10-10 6:52:31 PM | New | 8,457.97 | 0.21305503 | Buy + 2018-10-10 6:52:31 PM | New | 8,457.84 | 0.07534153 | Buy + 2018-10-10 6:52:31 PM | New | 8,457.33 | 0.18856173 | Buy + 2018-10-10 6:52:31 PM | New | 8,457.07 | 0.00572370 | Buy + 2018-10-10 6:52:31 PM | New | 8,456.82 | 0.49919611 | Buy + 2018-10-10 6:52:31 PM | New | 8,456.69 | 0.03960801 | Buy + 2018-10-10 6:52:31 PM | New | 8,456.30 | 0.38466649 | Buy + 2018-10-10 6:52:31 PM | New | 8,456.18 | 0.07527020 | Buy + 2018-10-10 6:52:31 PM | New | 8,455.66 | 1.60153236 | Buy + 2018-10-10 6:52:31 PM | New | 8,455.28 | 0.75478451 | Buy + 2018-10-10 6:52:31 PM | New | 8,455.15 | 1.49758832 | Buy + 2018-10-10 6:52:31 PM | New | 8,455.03 | 7.00000000 | Buy + 2018-10-10 6:52:31 PM | New | 8,453.87 | 0.16392300 | Buy + 2018-10-10 6:52:31 PM | New | 8,453.36 | 0.99839222 | Buy + 2018-10-10 6:52:31 PM | New | 8,453.23 | 0.49919611 | Buy + 2018-10-10 6:52:31 PM | New | 8,453.11 | 1.95684874 | Buy + 2018-10-10 6:52:31 PM | New | 8,452.98 | 2.25353822 | Buy + 2018-10-10 6:52:31 PM | New | 8,452.08 | 0.49919611 | Buy + 2018-10-10 6:52:31 PM | New | 8,451.96 | 0.03801526 | Buy + 2018-10-10 6:52:31 PM | New | 8,246.70 | 0.41800000 | Buy + 2018-10-10 6:52:31 PM | New | 8,246.45 | 0.25000000 | Buy + 2018-10-10 6:52:31 PM | New | 8,238.48 | 0.51100000 | Buy + 2018-10-10 6:52:31 PM | New | 8,238.23 | 0.32000000 | Buy + 2018-10-10 6:52:31 PM | New | 8,237.60 | 0.30000000 | Buy + 2018-10-10 6:52:31 PM | New | 8,200.00 | 0.21392684 | Buy + 2018-10-10 6:52:31 PM | New | 0.01 |31.00000000 | Buy + 2018-10-10 6:52:31 PM | New | 8,671.92 | 0.10826416 | Sell + 2018-10-10 6:52:31 PM | New | 8,672.05 | 1.42836521 | Sell + 2018-10-10 6:52:31 PM | New | 8,672.19 | 2.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,672.32 | 0.72176110 | Sell + 2018-10-10 6:52:31 PM | New | 8,672.59 | 2.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,762.29 | 7.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,762.42 | 2.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,762.55 | 0.06077132 | Sell + 2018-10-10 6:52:31 PM | New | 8,762.69 | 0.76951331 | Sell + 2018-10-10 6:52:31 PM | New | 8,762.82 | 0.00999000 | Sell + 2018-10-10 6:52:31 PM | New | 8,763.75 | 0.02879279 | Sell + 2018-10-10 6:52:31 PM | New | 8,764.14 | 0.03079200 | Sell + 2018-10-10 6:52:31 PM | New | 8,764.28 | 3.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,765.34 | 1.00000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,765.60 | 3.20000000 | Sell + 2018-10-10 6:52:31 PM | New | 8,765.73 | 2.42500103 | Sell + 2018-10-10 6:52:31 PM | New | 8,765.87 | 0.06077132 | Sell + 2018-10-10 6:52:31 PM | New | 8,766.00 | 1.13603811 | Sell + 2018-10-10 6:52:31 PM | New | 8,766.53 | 0.48787545 | Sell + 2018-10-10 6:52:31 PM | New | 8,766.66 | 0.14720710 | Sell + 2018-10-10 6:52:31 PM | New | 8,766.79 | 0.19520208 | Sell + 2018-10-10 6:52:31 PM | New | 8,767.46 | 0.07479691 | Sell + 2018-10-10 6:52:31 PM | New | 8,767.59 | 0.54720711 | Sell + 2018-10-10 6:52:31 PM | New | 8,767.72 | 0.73224120 | Sell + 2018-10-10 6:52:31 PM | New | 8,768.38 | 0.68658606 | Sell + 2018-10-10 6:52:31 PM | New | 8,768.52 | 0.41307854 | Sell + 2018-10-10 6:52:31 PM | New | 8,768.65 | 0.19520208 | Sell + 2018-10-10 6:52:31 PM | New | 8,769.44 | 0.19651065 | Sell + 2018-10-10 6:52:31 PM | New | 8,769.71 | 0.41720609 | Sell + 2018-10-10 6:52:31 PM | New | 8,769.84 | 7.00000000 | Sell + Press key to exit. + ``` ## My related projects diff --git a/src/AlphaPoint.Api/Models/Enums/ActionType.cs b/src/AlphaPoint.Api/Models/Enums/ActionType.cs new file mode 100644 index 0000000..f30e027 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/ActionType.cs @@ -0,0 +1,23 @@ +namespace AlphaPoint.Api.Models +{ + /// + /// Represents the type of L2 information price data. + /// + public enum ActionType + { + /// + /// New data. + /// + New = 0, + + /// + /// Updated data. + /// + Update = 1, + + /// + /// Deleted data. + /// + Delete = 2, + } +} diff --git a/src/AlphaPoint.Api/Models/Enums/ErrorCode.cs b/src/AlphaPoint.Api/Models/Enums/ErrorCode.cs new file mode 100644 index 0000000..55c539e --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/ErrorCode.cs @@ -0,0 +1,35 @@ +namespace AlphaPoint.Api.Models +{ + /// + /// Return value indicating successful or unsuccessful receipt of a call. + /// + public enum ErrorCode + { + Success = 0, + + /// + /// Not authorized (error code 20) + /// + NotAuthorized = 20, + + /// + /// Invalid request (error code 100) + /// + InvalidRequest = 100, + + /// + /// Operation failed (error code 101) + /// + OperationFailed = 101, + + /// + /// Server error (error code 102) + /// + ServerError = 102, + + /// + /// Resource not found (error code 104). + /// + ResourceNotFound = 104, + } +} diff --git a/src/AlphaPoint.Api/Models/Enums/InstrumentType.cs b/src/AlphaPoint.Api/Models/Enums/InstrumentType.cs new file mode 100644 index 0000000..59982ef --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/InstrumentType.cs @@ -0,0 +1,18 @@ +namespace AlphaPoint.Api.Models +{ + /// + /// Represents the type of the instrument. + /// + public enum InstrumentType + { + /// + /// Unknown. An error condition. + /// + Unknown, + + /// + /// An exchange of one product for another. + /// + Standard, + } +} diff --git a/src/AlphaPoint.Api/Models/Enums/ProductType.cs b/src/AlphaPoint.Api/Models/Enums/ProductType.cs new file mode 100644 index 0000000..36dc19e --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/ProductType.cs @@ -0,0 +1,19 @@ +namespace AlphaPoint.Api.Models +{ + /// + /// The nature of the product. + /// + public enum ProductType + { + /// + /// Unknown. An error condition. + /// + Unknown = 0, + + NationalCurrency = 1, + + CryptoCurrency = 2, + + Contract = 3 + } +} diff --git a/src/AlphaPoint.Api/Models/Enums/SessionStatus.cs b/src/AlphaPoint.Api/Models/Enums/SessionStatus.cs new file mode 100644 index 0000000..b67a7ff --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/SessionStatus.cs @@ -0,0 +1,11 @@ +namespace AlphaPoint.Api.Models +{ + public enum SessionStatus + { + Unknown = 0, + Running = 1, + Paused = 2, + Stopped = 3, + Starting = 4, + } +} diff --git a/src/AlphaPoint.Api/Models/Enums/Side.cs b/src/AlphaPoint.Api/Models/Enums/Side.cs new file mode 100644 index 0000000..eb976d5 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Enums/Side.cs @@ -0,0 +1,28 @@ +namespace AlphaPoint.Api.Models +{ + /// + /// Represents one side of a trade. Every trade has two sides. + /// + public enum Side + { + /// + /// The buy side of a trade.. + /// + Buy = 0, + + /// + /// The sell side of a trade. + /// + Sell = 1, + + /// + /// Short (reserved for future use). + /// + Short = 2, + + /// + /// Unknown (error condition). + /// + Unknown = 3 + } +} diff --git a/src/AlphaPoint.Api/Models/MessageFrame.cs b/src/AlphaPoint.Api/Models/MessageFrame.cs index 615d495..e24c21f 100644 --- a/src/AlphaPoint.Api/Models/MessageFrame.cs +++ b/src/AlphaPoint.Api/Models/MessageFrame.cs @@ -36,5 +36,15 @@ public class MessageFrame /// [JsonProperty("o")] public string Payload { get; set; } + + /// + /// Deserialized the Payload to an object of arbitrary type . + /// + /// The type of the payload. + /// The Payload deserialized to the specified type. + public T PayloadAs() + { + return JsonConvert.DeserializeObject(Payload); + } } } \ No newline at end of file diff --git a/src/AlphaPoint.Api/Models/Responses/GenericResponse.cs b/src/AlphaPoint.Api/Models/Responses/GenericResponse.cs new file mode 100644 index 0000000..dd28341 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Responses/GenericResponse.cs @@ -0,0 +1,40 @@ +using Newtonsoft.Json; + +namespace AlphaPoint.Api.Models.Responses +{ + /// + /// A generic response to an API call that verifies that the call was received. + /// + public class GenericResponse + { + /// + /// If the call has been successfully received by the Order Management System, result is true; otherwise, it is false. + /// + [JsonProperty("result")] + bool Result { get; set; } + + /// + /// A successful receipt of the call returns null; the errormsg parameter for an unsuccessful call returns one of the following messages: + /// Not Authorized (errorcode 20) + /// Invalid Request (errorcode 100) + /// Operation Failed (errorcode 101) + /// Server Error (errorcode 102) + /// Resource Not Found (errorcode 104) + /// + [JsonProperty("errormsg")] + string ErrorMsg { get; set; } + + /// + /// A successful receipt of the call returns 0. + /// An unsuccessful receipt of the call returns one of the errorcodes shown in the errormsg list. + /// + [JsonProperty("errorcode")] + ErrorCode ErrorCode { get; set; } + + /// + /// Message text that the system may send. The content of this parameter is usually null. + /// + [JsonProperty("detail")] + string Detail { get; set; } + } +} diff --git a/src/AlphaPoint.Api/Models/Responses/Instrument.cs b/src/AlphaPoint.Api/Models/Responses/Instrument.cs new file mode 100644 index 0000000..b7420b5 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Responses/Instrument.cs @@ -0,0 +1,96 @@ +using System; + +namespace AlphaPoint.Api.Models.Responses +{ + public class Instrument + { + /// + /// The ID of the Order Management System on which the instrument is traded. + /// + public int OmsId { get; set; } + + /// + /// The ID of the instrument. + /// + public int InstrumentId { get; set; } + + /// + /// Trading symbol of the instrument. + /// + public string Symbol { get; set; } + + /// + /// The first product comprising the instrument. For example, USD in a USD/BitCoin instrument. + /// + public int Product1 { get; set; } + + /// + /// The symbol for Product 1 on the trading venue. For example, USD. + /// + public string Product1Symbol { get; set; } + + /// + /// The second product comprising the instrument. For example, BitCoin in a USD/BitCoin instrument. + /// + public int Product2 { get; set; } + + /// + /// The symbol for Product 2 on the trading venue. For example, BTC. + /// + public string Product2Symbol { get; set; } + + /// + /// The type of the instrument. All instrument types currently are standard, an exchange of one product for another (or unknown, an error condition), but this may expand to new types in the future. + /// + public InstrumentType InstrumentType { get; set; } + + /// + /// If the instrument trades on another trading venue to which the user has access, this value is the instrument ID on that other venue. + /// + /// + public long VenueInstrumentId { get; set; } + + /// + /// The ID of the trading venue on which the instrument trades, if not this venue. + /// + /// + public int VenueId { get; set; } + + /// + /// The numerical position in which to sort the returned list of instruments on a visual display. + /// + /// + /// If the call returns information about a single instrument, SortIndex should return 0. + /// + public int SortIndex { get; set; } + + /// + /// Is the market for this instrument currently open and operational? + /// + public SessionStatus SessionStatus { get; set; } + + /// + /// What was the previous session status for this instrument? + /// + public SessionStatus PreviousSessionStatus { get; set; } + + /// + /// The time and date at which the session status was reported, in ISO 8601 format. + /// + public DateTime SessionStatusDateTime { get; set; } + + /// + /// An account trading with itself still incurs fees. If this instrument prevents an account from trading the instrument with itself, the value returns true; otherwise defaults to false. + /// + public bool SelfTradePrevention { get; set; } + + /// + /// The number of decimal places for the smallest quantity of the instrument that can trade (analogous to smallest lot size). + /// + /// + /// For example, the smallest increment of a US Dollar that can trade is 0.01 (one cent, or 2 decimal places). + /// Current maximum is 8 decimal places. The default is 0. + /// + public decimal QuantityIncrement { get; set; } + } +} diff --git a/src/AlphaPoint.Api/Models/Responses/Level2Snapshot.cs b/src/AlphaPoint.Api/Models/Responses/Level2Snapshot.cs new file mode 100644 index 0000000..6cffb83 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Responses/Level2Snapshot.cs @@ -0,0 +1,92 @@ +using Newtonsoft.Json; +using Newtonsoft.Json.Linq; +using System; + +namespace AlphaPoint.Api.Models.Responses +{ + [JsonConverter(typeof(Level2SnapshotConverter))] + public class Level2Snapshot + { + /// + /// Market Data Update ID. This sequential ID identifies the order in which the update was created. + /// + public int MdUpdateId { get; set; } + + /// + /// The number of accounts that have orders at this price level. + /// + public int Accounts { get; set; } + + /// + /// ActionDateTime identifies the time and date that the snapshot was taken or the event occurred, in POSIX format X 1000 (milliseconds since 1 January 1970). + /// + public long ActionDateTime { get; set; } + + /// + /// L2 information provides price data. This value shows whether this data is new, an update, or a deletion. + /// + public ActionType ActionType { get; set; } + + /// + /// The price at which the instrument was last traded. + /// + public decimal LastTradePrice { get; set; } + + /// + /// The number of orders at this price point. Whether it is a Buy or Sell order is shown by . + /// + public int Orders { get; set; } + + /// + /// Bid or Ask price for the Quantity (). + /// + public decimal Price { get; set; } + + /// + /// ProductPairCode is the same value and used for the same purpose as InstrumentID. + /// + public int ProductPairCode { get; set; } + + /// + /// Quantity available at a given Bid or Ask price (). + /// + public decimal Quantity { get; set; } + + /// + /// One of: 0 Buy, 1 Sell, 2 Short (reserved for future use), 3 Unknown (error condition). + /// + public Side Side { get; set; } + + private class Level2SnapshotConverter : JsonConverter + { + public override bool CanConvert(Type objectType) + { + throw new NotImplementedException(); + } + + public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + { + JArray ja = JArray.Load(reader); + Level2Snapshot data = new Level2Snapshot + { + MdUpdateId = (int)ja[0], + Accounts = (int)ja[1], + ActionDateTime = (long)ja[2], + ActionType = (ActionType)Enum.Parse(typeof(ActionType), (string)ja[3]), + LastTradePrice = (decimal)ja[4], + Orders = (int)ja[5], + Price = (decimal)ja[6], + ProductPairCode = (int)ja[7], + Quantity = (decimal)ja[8], + Side = (Side)Enum.Parse(typeof(Side), (string)ja[9]), + }; + return data; + } + + public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) + { + throw new NotImplementedException(); + } + } + } +} diff --git a/src/AlphaPoint.Api/Models/Responses/Pong.cs b/src/AlphaPoint.Api/Models/Responses/Pong.cs new file mode 100644 index 0000000..bc7b04c --- /dev/null +++ b/src/AlphaPoint.Api/Models/Responses/Pong.cs @@ -0,0 +1,13 @@ +using Newtonsoft.Json; + +namespace AlphaPoint.Api.Models.Responses +{ + /// + /// Represents the response of a ping request. + /// + public class Pong + { + [JsonProperty("msg")] + public string Msg { get; set; } + } +} diff --git a/src/AlphaPoint.Api/Models/Responses/Product.cs b/src/AlphaPoint.Api/Models/Responses/Product.cs new file mode 100644 index 0000000..b19fb71 --- /dev/null +++ b/src/AlphaPoint.Api/Models/Responses/Product.cs @@ -0,0 +1,51 @@ +using Newtonsoft.Json; + +namespace AlphaPoint.Api.Models.Responses +{ + public class Product + { + /// + /// The ID of the Order Management System that offers the product + /// + public int OmsId { get; set; } + + /// + /// The ID of the product. + /// + public long ProductId { get; set; } + + /// + /// “Nickname” or shortened name of the product. For example, NZD (New Zealand Dollar). + /// + [JsonProperty("Product")] + public string Nickname { get; set; } + + /// + /// Full and official name of the product. For example, New Zealand Dollar. + /// + public string ProductFullName { get; set; } + + /// + /// The nature of the product. + /// + public ProductType ProductType { get; set; } + + /// + /// The number of decimal places in which the product is divided.. + /// + public int DecimalPlaces { get; set; } + + /// + /// Minimum tradable quantity of the product. + /// + /// + /// See also GetInstrumentAsync, where this value is called QuantityIncrement. + /// + public decimal TickSize { get; set; } + + /// + /// Shows whether trading the product incurs fees. + /// + public bool NoFees { get; set; } + } +}