ig_client/application/models/
order.rs1use crate::impl_json_display;
7use serde::{Deserialize, Serialize};
8
9#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Default)]
11#[serde(rename_all = "UPPERCASE")]
12pub enum Direction {
13 #[default]
15 Buy,
16 Sell,
18}
19
20impl_json_display!(Direction);
21
22#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Default)]
24#[serde(rename_all = "UPPERCASE")]
25pub enum OrderType {
26 #[default]
28 Limit,
29 Market,
31 Quote,
33 Stop,
35 StopLimit,
37}
38
39#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Default)]
44#[serde(rename_all = "UPPERCASE")]
45pub enum Status {
46 Amended,
48 Deleted,
50 #[serde(rename = "FULLY_CLOSED")]
52 FullyClosed,
53 Opened,
55 #[serde(rename = "PARTIALLY_CLOSED")]
57 PartiallyClosed,
58 Closed,
60 #[default]
62 Open,
63 Updated,
65 Accepted,
67 Rejected,
69 Working,
71 Filled,
73 Cancelled,
75 Expired,
77}
78
79#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Default)]
81pub enum TimeInForce {
82 #[serde(rename = "GOOD_TILL_CANCELLED")]
84 #[default]
85 GoodTillCancelled,
86 #[serde(rename = "GOOD_TILL_DATE")]
88 GoodTillDate,
89 #[serde(rename = "IMMEDIATE_OR_CANCEL")]
91 ImmediateOrCancel,
92 #[serde(rename = "FILL_OR_KILL")]
94 FillOrKill,
95}
96
97#[derive(Debug, Clone, Serialize)]
99pub struct CreateOrderRequest {
100 pub epic: String,
102 pub direction: Direction,
104 pub size: f64,
106 #[serde(rename = "orderType")]
108 pub order_type: OrderType,
109 #[serde(rename = "timeInForce")]
111 pub time_in_force: TimeInForce,
112 #[serde(rename = "level", skip_serializing_if = "Option::is_none")]
114 pub level: Option<f64>,
115 #[serde(rename = "guaranteedStop", skip_serializing_if = "Option::is_none")]
117 pub guaranteed_stop: Option<bool>,
118 #[serde(rename = "stopLevel", skip_serializing_if = "Option::is_none")]
120 pub stop_level: Option<f64>,
121 #[serde(rename = "stopDistance", skip_serializing_if = "Option::is_none")]
123 pub stop_distance: Option<f64>,
124 #[serde(rename = "limitLevel", skip_serializing_if = "Option::is_none")]
126 pub limit_level: Option<f64>,
127 #[serde(rename = "limitDistance", skip_serializing_if = "Option::is_none")]
129 pub limit_distance: Option<f64>,
130 #[serde(rename = "expiry", skip_serializing_if = "Option::is_none")]
132 pub expiry: Option<String>,
133 #[serde(rename = "dealReference", skip_serializing_if = "Option::is_none")]
135 pub deal_reference: Option<String>,
136 #[serde(rename = "forceOpen", skip_serializing_if = "Option::is_none")]
138 pub force_open: Option<bool>,
139}
140
141impl CreateOrderRequest {
142 pub fn market(epic: String, direction: Direction, size: f64) -> Self {
144 Self {
145 epic,
146 direction,
147 size,
148 order_type: OrderType::Market,
149 time_in_force: TimeInForce::FillOrKill,
150 level: None,
151 guaranteed_stop: None,
152 stop_level: None,
153 stop_distance: None,
154 limit_level: None,
155 limit_distance: None,
156 expiry: None,
157 deal_reference: None,
158 force_open: Some(true),
159 }
160 }
161
162 pub fn limit(epic: String, direction: Direction, size: f64, level: f64) -> Self {
164 Self {
165 epic,
166 direction,
167 size,
168 order_type: OrderType::Limit,
169 time_in_force: TimeInForce::GoodTillCancelled,
170 level: Some(level),
171 guaranteed_stop: None,
172 stop_level: None,
173 stop_distance: None,
174 limit_level: None,
175 limit_distance: None,
176 expiry: None,
177 deal_reference: None,
178 force_open: Some(true),
179 }
180 }
181
182 pub fn with_stop_loss(mut self, stop_level: f64) -> Self {
184 self.stop_level = Some(stop_level);
185 self
186 }
187
188 pub fn with_take_profit(mut self, limit_level: f64) -> Self {
190 self.limit_level = Some(limit_level);
191 self
192 }
193
194 pub fn with_reference(mut self, reference: String) -> Self {
196 self.deal_reference = Some(reference);
197 self
198 }
199}
200
201#[derive(Debug, Clone, Deserialize)]
203pub struct CreateOrderResponse {
204 #[serde(rename = "dealReference")]
206 pub deal_reference: String,
207}
208
209#[derive(Debug, Clone, Deserialize)]
211pub struct OrderConfirmation {
212 pub date: String,
214 pub status: Status,
216 pub reason: Option<String>,
218 #[serde(rename = "dealId")]
220 pub deal_id: Option<String>,
221 #[serde(rename = "dealReference")]
223 pub deal_reference: String,
224 #[serde(rename = "dealStatus")]
226 pub deal_status: Option<String>,
227 pub epic: Option<String>,
229 #[serde(rename = "expiry")]
231 pub expiry: Option<String>,
232 #[serde(rename = "guaranteedStop")]
234 pub guaranteed_stop: Option<bool>,
235 #[serde(rename = "level")]
237 pub level: Option<f64>,
238 #[serde(rename = "limitDistance")]
240 pub limit_distance: Option<f64>,
241 #[serde(rename = "limitLevel")]
243 pub limit_level: Option<f64>,
244 pub size: Option<f64>,
246 #[serde(rename = "stopDistance")]
248 pub stop_distance: Option<f64>,
249 #[serde(rename = "stopLevel")]
251 pub stop_level: Option<f64>,
252 #[serde(rename = "trailingStop")]
254 pub trailing_stop: Option<bool>,
255 pub direction: Option<Direction>,
257}
258
259#[derive(Debug, Clone, Serialize)]
261pub struct UpdatePositionRequest {
262 #[serde(rename = "stopLevel", skip_serializing_if = "Option::is_none")]
264 pub stop_level: Option<f64>,
265 #[serde(rename = "limitLevel", skip_serializing_if = "Option::is_none")]
267 pub limit_level: Option<f64>,
268 #[serde(rename = "trailingStop", skip_serializing_if = "Option::is_none")]
270 pub trailing_stop: Option<bool>,
271 #[serde(
273 rename = "trailingStopDistance",
274 skip_serializing_if = "Option::is_none"
275 )]
276 pub trailing_stop_distance: Option<f64>,
277}
278
279#[derive(Debug, Clone, Serialize)]
281pub struct ClosePositionRequest {
282 #[serde(rename = "dealId")]
284 pub deal_id: String,
285 pub direction: Direction,
287 pub size: f64,
289 #[serde(rename = "orderType")]
291 pub order_type: OrderType,
292 #[serde(rename = "timeInForce")]
294 pub time_in_force: TimeInForce,
295 #[serde(rename = "level", skip_serializing_if = "Option::is_none")]
297 pub level: Option<f64>,
298}
299
300impl ClosePositionRequest {
301 pub fn market(deal_id: String, direction: Direction, size: f64) -> Self {
303 Self {
304 deal_id,
305 direction,
306 size,
307 order_type: OrderType::Market,
308 time_in_force: TimeInForce::FillOrKill,
309 level: None,
310 }
311 }
312}
313
314#[derive(Debug, Clone, Deserialize)]
316pub struct ClosePositionResponse {
317 #[serde(rename = "dealReference")]
319 pub deal_reference: String,
320}