Skip to main content

oanda_client/
transaction.rs

1//! OANDA transaction endpoint contracts.
2// Shared imports vary by capability; unused ones are deliberately allowed.
3#[allow(unused_imports)]
4use crate::Timestamp;
5#[allow(unused_imports)]
6use crate::ids::*;
7#[allow(unused_imports)]
8use crate::models::*;
9#[allow(unused_imports)]
10use crate::{Client, Result};
11#[allow(unused_imports)]
12use reqwest::Method;
13#[allow(unused_imports)]
14use rust_decimal::Decimal;
15#[allow(unused_imports)]
16use serde::{Deserialize, Serialize};
17
18/// Query parameters for `list_transactions`.
19#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
20#[serde(rename_all = "camelCase")]
21pub struct ListTransactionsQuery {
22    /// The starting time (inclusive) of the time range for the Transactions being queried. \[default=Account
23    /// Creation Time\] If the Account is created after the provided timestamp, the Account creation time will
24    /// be used as the starting time.
25    #[serde(rename = "from", default, skip_serializing_if = "Option::is_none")]
26    pub from: Option<Timestamp>,
27    /// The ending time (inclusive) of the time range for the Transactions being queried. \[default=Request
28    /// Time\]
29    #[serde(rename = "to", default, skip_serializing_if = "Option::is_none")]
30    pub to: Option<Timestamp>,
31    /// The number of Transactions to include in each page of the results. \[default=100, maximum=1000\]
32    #[serde(rename = "pageSize", default, skip_serializing_if = "Option::is_none")]
33    pub page_size: Option<i64>,
34    /// A filter for restricting the types of Transactions to retrieve.
35    #[serde(rename = "type", default, skip_serializing_if = "Option::is_none")]
36    pub r#type: Option<Vec<TransactionFilter>>,
37}
38
39/// Successful response for `list_transactions`.
40#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
41#[serde(rename_all = "camelCase")]
42pub struct ListTransactionsResponse {
43    /// The starting time provided in the request.
44    #[serde(rename = "from", default, skip_serializing_if = "Option::is_none")]
45    pub from: Option<Timestamp>,
46    /// The ending time provided in the request.
47    #[serde(rename = "to", default, skip_serializing_if = "Option::is_none")]
48    pub to: Option<Timestamp>,
49    /// The pageSize provided in the request
50    #[serde(rename = "pageSize", default, skip_serializing_if = "Option::is_none")]
51    pub page_size: Option<i64>,
52    /// The Transaction-type filter provided in the request
53    #[serde(rename = "type", default, skip_serializing_if = "Option::is_none")]
54    pub r#type: Option<Vec<TransactionFilter>>,
55    /// The number of Transactions that are contained in the pages returned
56    #[serde(rename = "count", default, skip_serializing_if = "Option::is_none")]
57    pub count: Option<i64>,
58    /// The list of URLs that represent idrange queries providing the data for each page in the query results
59    #[serde(rename = "pages", default, skip_serializing_if = "Option::is_none")]
60    pub pages: Option<Vec<String>>,
61    /// The ID of the most recent Transaction created for the Account
62    #[serde(
63        rename = "lastTransactionID",
64        default,
65        skip_serializing_if = "Option::is_none"
66    )]
67    pub last_transaction_id: Option<TransactionID>,
68}
69
70impl Client {
71    /// List transactions.
72    pub async fn list_transactions(
73        &self,
74        account_id: &AccountID,
75        query: Option<&ListTransactionsQuery>,
76    ) -> std::result::Result<
77        crate::ApiResponse<ListTransactionsResponse>,
78        crate::OperationError<crate::GenericRejection>,
79    > {
80        let account_id_encoded = crate::client::segment(account_id.as_str());
81        let path = format!("/v3/accounts/{account_id_encoded}/transactions");
82        self.execute(Method::GET, &path, query, None::<&()>, None, None)
83            .await
84    }
85}
86
87/// Successful response for `transaction_details`.
88#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
89#[serde(rename_all = "camelCase")]
90pub struct TransactionDetailsResponse {
91    /// The details of the Transaction requested
92    #[serde(
93        rename = "transaction",
94        default,
95        skip_serializing_if = "Option::is_none"
96    )]
97    pub transaction: Option<Transaction>,
98    /// The ID of the most recent Transaction created for the Account
99    #[serde(
100        rename = "lastTransactionID",
101        default,
102        skip_serializing_if = "Option::is_none"
103    )]
104    pub last_transaction_id: Option<TransactionID>,
105}
106
107impl Client {
108    /// Transaction details.
109    pub async fn transaction_details(
110        &self,
111        account_id: &AccountID,
112        transaction_id: &TransactionID,
113    ) -> std::result::Result<
114        crate::ApiResponse<TransactionDetailsResponse>,
115        crate::OperationError<crate::GenericRejection>,
116    > {
117        let account_id_encoded = crate::client::segment(account_id.as_str());
118        let transaction_id_encoded = crate::client::segment(transaction_id.as_str());
119        let path =
120            format!("/v3/accounts/{account_id_encoded}/transactions/{transaction_id_encoded}");
121        self.execute(Method::GET, &path, None::<&()>, None::<&()>, None, None)
122            .await
123    }
124}
125
126/// Query parameters for `transactions_by_id_range`.
127#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
128#[serde(rename_all = "camelCase")]
129pub struct TransactionsByIdRangeQuery {
130    /// The starting Transaction ID (inclusive) to fetch. \[required\]
131    #[serde(rename = "from")]
132    pub from: TransactionID,
133    /// The ending Transaction ID (inclusive) to fetch. \[required\]
134    #[serde(rename = "to")]
135    pub to: TransactionID,
136    /// The filter that restricts the types of Transactions to retrieve.
137    #[serde(rename = "type", default, skip_serializing_if = "Option::is_none")]
138    pub r#type: Option<Vec<TransactionFilter>>,
139}
140
141/// Successful response for `transactions_by_id_range`.
142#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
143#[serde(rename_all = "camelCase")]
144pub struct TransactionsByIdRangeResponse {
145    /// The list of Transactions that satisfy the request.
146    #[serde(
147        rename = "transactions",
148        default,
149        skip_serializing_if = "Option::is_none"
150    )]
151    pub transactions: Option<Vec<Transaction>>,
152    /// The ID of the most recent Transaction created for the Account
153    #[serde(
154        rename = "lastTransactionID",
155        default,
156        skip_serializing_if = "Option::is_none"
157    )]
158    pub last_transaction_id: Option<TransactionID>,
159}
160
161impl Client {
162    /// Transactions by id range.
163    pub async fn transactions_by_id_range(
164        &self,
165        account_id: &AccountID,
166        query: &TransactionsByIdRangeQuery,
167    ) -> std::result::Result<
168        crate::ApiResponse<TransactionsByIdRangeResponse>,
169        crate::OperationError<crate::GenericRejection>,
170    > {
171        let account_id_encoded = crate::client::segment(account_id.as_str());
172        let path = format!("/v3/accounts/{account_id_encoded}/transactions/idrange");
173        self.execute(Method::GET, &path, Some(query), None::<&()>, None, None)
174            .await
175    }
176}
177
178/// Query parameters for `transactions_since_id`.
179#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
180#[serde(rename_all = "camelCase")]
181pub struct TransactionsSinceIdQuery {
182    /// The ID of the last Transaction fetched. This query will return all Transactions newer than the
183    /// TransactionID. \[required\]
184    #[serde(rename = "id")]
185    pub id: TransactionID,
186    /// A filter for restricting the types of Transactions to retrieve.
187    #[serde(rename = "type", default, skip_serializing_if = "Option::is_none")]
188    pub r#type: Option<Vec<TransactionFilter>>,
189}
190
191/// Successful response for `transactions_since_id`.
192#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
193#[serde(rename_all = "camelCase")]
194pub struct TransactionsSinceIdResponse {
195    /// The list of Transactions that satisfy the request.
196    #[serde(
197        rename = "transactions",
198        default,
199        skip_serializing_if = "Option::is_none"
200    )]
201    pub transactions: Option<Vec<Transaction>>,
202    /// The ID of the most recent Transaction created for the Account
203    #[serde(
204        rename = "lastTransactionID",
205        default,
206        skip_serializing_if = "Option::is_none"
207    )]
208    pub last_transaction_id: Option<TransactionID>,
209}
210
211impl Client {
212    /// Transactions since id.
213    pub async fn transactions_since_id(
214        &self,
215        account_id: &AccountID,
216        query: &TransactionsSinceIdQuery,
217    ) -> std::result::Result<
218        crate::ApiResponse<TransactionsSinceIdResponse>,
219        crate::OperationError<crate::GenericRejection>,
220    > {
221        let account_id_encoded = crate::client::segment(account_id.as_str());
222        let path = format!("/v3/accounts/{account_id_encoded}/transactions/sinceid");
223        self.execute(Method::GET, &path, Some(query), None::<&()>, None, None)
224            .await
225    }
226}