deltadefi 0.0.11__py3-none-any.whl → 0.1.1__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of deltadefi might be problematic. Click here for more details.

deltadefi/__init__.py CHANGED
@@ -1,2 +1,2 @@
1
1
  # flake8: noqa
2
- from .clients import ApiClient
2
+ from .clients import ApiClient, WebSocketClient
deltadefi/api.py CHANGED
@@ -3,10 +3,10 @@ import json
3
3
  import requests
4
4
 
5
5
  from deltadefi.error import ClientError, ServerError
6
- from deltadefi.lib.utils import clean_none_value, encoded_string
6
+ from deltadefi.utils import clean_none_value, encoded_string
7
7
 
8
8
 
9
- class API(object):
9
+ class API:
10
10
  def __init__(self, base_url=None, api_key=None, timeout=None, **kwargs):
11
11
  self.base_url = base_url
12
12
  self.api_key = api_key
@@ -73,10 +73,10 @@ class API(object):
73
73
  if 400 <= status_code < 500:
74
74
  try:
75
75
  err = json.loads(response.text)
76
- except json.JSONDecodeError:
76
+ except json.JSONDecodeError as e:
77
77
  raise ClientError(
78
78
  status_code, None, response.text, response.headers, None
79
- )
79
+ ) from e
80
80
  error_data = None
81
81
  if "data" in err:
82
82
  error_data = err["data"]
@@ -1,16 +1,15 @@
1
1
  from dataclasses import dataclass
2
- from typing import Optional
3
2
 
4
3
 
5
4
  @dataclass
6
5
  class AuthHeaders:
7
6
  jwt: str
8
- apiKey: str
7
+ api_key: str
9
8
 
10
9
 
11
10
  class ApiHeaders:
12
11
  __annotations__ = {
13
12
  "Content-Type": str,
14
- "Authorization": Optional[str],
15
- "X-API-KEY": Optional[str],
13
+ "Authorization": str | None,
14
+ "X-API-KEY": str | None,
16
15
  }
@@ -1,2 +1,3 @@
1
1
  # flake8: noqa
2
2
  from .client import *
3
+ from .websocket import WebSocketClient
@@ -1,10 +1,8 @@
1
1
  #
2
- from typing import List
3
2
 
4
3
  from sidan_gin import Asset, UTxO
5
4
 
6
5
  from deltadefi.api import API
7
- from deltadefi.lib.utils import check_required_parameter, check_required_parameters
8
6
  from deltadefi.models.models import OrderStatusType
9
7
  from deltadefi.responses import (
10
8
  BuildDepositTransactionResponse,
@@ -12,7 +10,6 @@ from deltadefi.responses import (
12
10
  CreateNewAPIKeyResponse,
13
11
  GetAccountBalanceResponse,
14
12
  GetDepositRecordsResponse,
15
- GetOrderRecordResponse,
16
13
  GetWithdrawalRecordsResponse,
17
14
  SubmitDepositTransactionResponse,
18
15
  SubmitWithdrawalTransactionResponse,
@@ -20,8 +17,11 @@ from deltadefi.responses import (
20
17
  from deltadefi.responses.accounts import (
21
18
  BuildTransferalTransactionResponse,
22
19
  GetOperationKeyResponse,
20
+ GetOrderRecordResponse,
21
+ GetOrderRecordsResponse,
23
22
  SubmitTransferalTransactionResponse,
24
23
  )
24
+ from deltadefi.utils import check_required_parameter, check_required_parameters
25
25
 
26
26
 
27
27
  class Accounts(API):
@@ -78,7 +78,7 @@ class Accounts(API):
78
78
 
79
79
  def get_order_records(
80
80
  self, status: OrderStatusType, **kwargs
81
- ) -> GetOrderRecordResponse:
81
+ ) -> GetOrderRecordsResponse:
82
82
  """
83
83
  Get order records.
84
84
 
@@ -89,7 +89,7 @@ class Accounts(API):
89
89
  page: Optional; The page number for pagination. Defaults to 1.
90
90
 
91
91
  Returns:
92
- A GetOrderRecordResponse object containing the order records.
92
+ A GetOrderRecordsResponse object containing the order records.
93
93
  """
94
94
  check_required_parameter(status, "status")
95
95
  payload = {"status": status, **kwargs}
@@ -97,6 +97,21 @@ class Accounts(API):
97
97
  url_path = "/order-records"
98
98
  return self.send_request("GET", self.group_url_path + url_path, payload)
99
99
 
100
+ def get_order_record(self, order_id: str, **kwargs) -> GetOrderRecordResponse:
101
+ """
102
+ Get a single order record by order ID.
103
+
104
+ Args:
105
+ order_id: The ID of the order to retrieve.
106
+
107
+ Returns:
108
+ A GetOrderRecordResponse object containing the order record.
109
+ """
110
+ check_required_parameter(order_id, "order_id")
111
+
112
+ url_path = f"/order/{order_id}"
113
+ return self.send_request("GET", self.group_url_path + url_path, kwargs)
114
+
100
115
  def get_account_balance(self, **kwargs) -> GetAccountBalanceResponse:
101
116
  """
102
117
  Get account balance.
@@ -108,7 +123,7 @@ class Accounts(API):
108
123
  return self.send_request("GET", self.group_url_path + url_path, kwargs)
109
124
 
110
125
  def build_deposit_transaction(
111
- self, deposit_amount: List[Asset], input_utxos: List[UTxO], **kwargs
126
+ self, deposit_amount: list[Asset], input_utxos: list[UTxO], **kwargs
112
127
  ) -> BuildDepositTransactionResponse:
113
128
  """
114
129
  Build a deposit transaction.
@@ -133,7 +148,7 @@ class Accounts(API):
133
148
  return self.send_request("POST", self.group_url_path + url_path, payload)
134
149
 
135
150
  def build_withdrawal_transaction(
136
- self, withdrawal_amount: List[Asset], **kwargs
151
+ self, withdrawal_amount: list[Asset], **kwargs
137
152
  ) -> BuildWithdrawalTransactionResponse:
138
153
  """
139
154
  Build a withdrawal transaction.
@@ -152,7 +167,7 @@ class Accounts(API):
152
167
  return self.send_request("POST", self.group_url_path + url_path, payload)
153
168
 
154
169
  def build_transferal_transaction(
155
- self, transferal_amount: List[Asset], to_address: str, **kwargs
170
+ self, transferal_amount: list[Asset], to_address: str, **kwargs
156
171
  ) -> BuildTransferalTransactionResponse:
157
172
  """
158
173
  Build a transferal transaction.
@@ -1,10 +1,9 @@
1
- # flake8: noqa: E501
2
1
  from sidan_gin import Wallet, decrypt_with_cipher
3
2
 
4
3
  from deltadefi.clients.accounts import Accounts
5
- from deltadefi.clients.app import App
6
4
  from deltadefi.clients.markets import Market
7
5
  from deltadefi.clients.orders import Order
6
+ from deltadefi.clients.websocket import WebSocketClient
8
7
  from deltadefi.models.models import OrderSide, OrderType
9
8
  from deltadefi.responses import PostOrderResponse
10
9
 
@@ -17,9 +16,9 @@ class ApiClient:
17
16
  def __init__(
18
17
  self,
19
18
  network: str = "preprod",
20
- api_key: str = None,
21
- base_url: str = None,
22
- master_wallet: Wallet = None,
19
+ api_key: str | None = None,
20
+ base_url: str | None = None,
21
+ master_wallet: Wallet | None = None,
23
22
  ):
24
23
  """
25
24
  Initialize the ApiClient.
@@ -43,10 +42,19 @@ class ApiClient:
43
42
  self.master_wallet = master_wallet
44
43
 
45
44
  self.accounts = Accounts(base_url=self.base_url, api_key=api_key)
46
- self.app = App(base_url=self.base_url, api_key=api_key)
47
45
  self.orders = Order(base_url=self.base_url, api_key=api_key)
48
46
  self.markets = Market(base_url=self.base_url, api_key=api_key)
49
47
 
48
+ # Initialize WebSocket client with correct stream URL
49
+ if network == "mainnet":
50
+ ws_base_url = (
51
+ "wss://stream.deltadefi.io" # TODO: Update when mainnet is available
52
+ )
53
+ else:
54
+ ws_base_url = "wss://stream-staging.deltadefi.io"
55
+
56
+ self.websocket = WebSocketClient(base_url=ws_base_url, api_key=api_key)
57
+
50
58
  def load_operation_key(self, password: str):
51
59
  """
52
60
  Load the operation key from the wallet using the provided password.
@@ -1,14 +1,8 @@
1
- # flake8: noqa: E501
2
-
3
1
  from typing import Literal
4
2
 
5
3
  from deltadefi.api import API
6
- from deltadefi.lib.utils import check_required_parameter, check_required_parameters
7
- from deltadefi.responses import (
8
- GetAggregatedPriceResponse,
9
- GetMarketDepthResponse,
10
- GetMarketPriceResponse,
11
- )
4
+ from deltadefi.responses import GetAggregatedPriceResponse, GetMarketPriceResponse
5
+ from deltadefi.utils import check_required_parameter, check_required_parameters
12
6
 
13
7
 
14
8
  class Market(API):
@@ -21,23 +15,6 @@ class Market(API):
21
15
  def __init__(self, api_key=None, base_url=None, **kwargs):
22
16
  super().__init__(api_key=api_key, base_url=base_url, **kwargs)
23
17
 
24
- def get_depth(self, symbol: str, **kwargs) -> GetMarketDepthResponse:
25
- """
26
- Get market depth.
27
-
28
- Args:
29
- data: A GetMarketDepthRequest object containing the market pair.
30
-
31
- Returns:
32
- A GetMarketDepthResponse object containing the market depth.
33
- """
34
-
35
- check_required_parameter(symbol, "symbol")
36
- payload = {"symbol": symbol, **kwargs}
37
- url_path = "/depth"
38
-
39
- return self.send_request("GET", self.group_url_path + url_path, payload)
40
-
41
18
  def get_market_price(self, symbol: str, **kwargs) -> GetMarketPriceResponse:
42
19
  """
43
20
  Get market price.
@@ -78,7 +55,7 @@ class Market(API):
78
55
  [end, "end"],
79
56
  ]
80
57
  )
81
- url_path = f"/aggregated-trade/{symbol}"
58
+ url_path = f"/graph/{symbol}"
82
59
  return self.send_request(
83
60
  "GET",
84
61
  self.group_url_path + url_path,
@@ -1,11 +1,11 @@
1
1
  from deltadefi.api import API
2
- from deltadefi.lib.utils import check_required_parameter, check_required_parameters
3
2
  from deltadefi.models.models import OrderSide, OrderType
4
3
  from deltadefi.responses import (
5
4
  BuildCancelOrderTransactionResponse,
6
5
  BuildPlaceOrderTransactionResponse,
7
6
  SubmitPlaceOrderTransactionResponse,
8
7
  )
8
+ from deltadefi.utils import check_required_parameter, check_required_parameters
9
9
 
10
10
 
11
11
  class Order(API):
@@ -0,0 +1,355 @@
1
+ import asyncio
2
+ from collections.abc import Callable
3
+ import json
4
+ import logging
5
+ from typing import Any
6
+
7
+ import websockets
8
+
9
+ from deltadefi.error import ClientError
10
+
11
+
12
+ class WebSocketClient:
13
+ """
14
+ WebSocket client for DeltaDeFi real-time data streams.
15
+
16
+ Supports:
17
+ - Recent trades
18
+ - Account streams
19
+ - Market price streams
20
+ - Market depth streams
21
+ """
22
+
23
+ def __init__(
24
+ self,
25
+ base_url: str = "wss://stream-staging.deltadefi.io",
26
+ api_key: str | None = None,
27
+ auto_reconnect: bool = True,
28
+ reconnect_interval: int = 5,
29
+ ping_interval: int = 20,
30
+ ping_timeout: int = 10,
31
+ ):
32
+ """
33
+ Initialize the WebSocket client.
34
+
35
+ Args:
36
+ base_url: WebSocket base URL
37
+ api_key: API key for authentication
38
+ auto_reconnect: Whether to automatically reconnect on disconnect
39
+ reconnect_interval: Seconds to wait before reconnection attempt
40
+ ping_interval: Seconds between ping frames
41
+ ping_timeout: Timeout for pong response
42
+ """
43
+ self.base_url = base_url.rstrip("/")
44
+ self.api_key = api_key
45
+ self.auto_reconnect = auto_reconnect
46
+ self.reconnect_interval = reconnect_interval
47
+ self.ping_interval = ping_interval
48
+ self.ping_timeout = ping_timeout
49
+
50
+ self.websocket: websockets.WebSocketServerProtocol | None = None
51
+ self.subscriptions: dict[str, dict[str, Any]] = {}
52
+ self.message_handlers: dict[str, Callable] = {}
53
+ self.is_connected = False
54
+ self.should_stop = False
55
+
56
+ self.logger = logging.getLogger(__name__)
57
+
58
+ async def connect(self, endpoint_path: str = "") -> None:
59
+ """
60
+ Establish WebSocket connection.
61
+
62
+ Args:
63
+ endpoint_path: Specific endpoint path for the connection
64
+ """
65
+ try:
66
+ # Build the full WebSocket URL
67
+ if endpoint_path:
68
+ url = f"{self.base_url}{endpoint_path}"
69
+ else:
70
+ url = f"{self.base_url}/ws"
71
+
72
+ # Add API key as query parameter if provided
73
+ if self.api_key:
74
+ separator = "&" if "?" in url else "?"
75
+ url = f"{url}{separator}api_key={self.api_key}"
76
+
77
+ self.websocket = await websockets.connect(
78
+ url,
79
+ ping_interval=self.ping_interval,
80
+ ping_timeout=self.ping_timeout,
81
+ )
82
+ self.is_connected = True
83
+ self.logger.info(f"WebSocket connected successfully to {url}")
84
+
85
+ # Start message listening loop
86
+ self._listen_task = asyncio.create_task(self._listen_messages())
87
+
88
+ except Exception as e:
89
+ self.logger.error(f"Failed to connect to WebSocket: {e}")
90
+ raise ClientError(0, "WS_CONNECTION_ERROR", str(e), {}, None) from e
91
+
92
+ async def disconnect(self) -> None:
93
+ """Close WebSocket connection."""
94
+ self.should_stop = True
95
+ if self.websocket:
96
+ await self.websocket.close()
97
+ self.is_connected = False
98
+ self.logger.info("WebSocket disconnected")
99
+
100
+ async def _listen_messages(self) -> None:
101
+ """Listen for incoming WebSocket messages."""
102
+ if not self.websocket:
103
+ return
104
+
105
+ try:
106
+ async for message in self.websocket:
107
+ if self.should_stop:
108
+ break
109
+
110
+ await self._handle_message(message)
111
+
112
+ except websockets.exceptions.ConnectionClosed:
113
+ self.is_connected = False
114
+ self.logger.warning("WebSocket connection closed")
115
+
116
+ if self.auto_reconnect and not self.should_stop:
117
+ await self._reconnect()
118
+
119
+ except Exception as e:
120
+ self.logger.error(f"Error in message listener: {e}")
121
+
122
+ async def _handle_message(self, message: str) -> None:
123
+ """Handle incoming WebSocket message."""
124
+ try:
125
+ data = json.loads(message)
126
+
127
+ # Determine message type based on structure
128
+ if isinstance(data, list) and len(data) > 0 and "timestamp" in data[0]:
129
+ # This is a trade stream message (array format)
130
+ if "trade" in self.message_handlers:
131
+ await self.message_handlers["trade"](data)
132
+ else:
133
+ self.logger.debug("No handler for trade stream")
134
+
135
+ elif isinstance(data, dict) and "type" in data:
136
+ # Handle typed messages (account, price, etc.)
137
+ msg_type = data.get("type", "unknown").lower()
138
+ sub_type = data.get("sub_type", "").lower()
139
+
140
+ if msg_type == "account":
141
+ # Account stream message
142
+ if "account" in self.message_handlers:
143
+ await self.message_handlers["account"](data)
144
+ else:
145
+ self.logger.debug("No handler for account stream")
146
+
147
+ elif msg_type == "market" and sub_type == "market_price":
148
+ # Price stream message
149
+ if "price" in self.message_handlers:
150
+ await self.message_handlers["price"](data)
151
+ else:
152
+ self.logger.debug("No handler for price stream")
153
+
154
+ else:
155
+ self.logger.debug(
156
+ f"Unknown message type: {msg_type}, sub_type: {sub_type}"
157
+ )
158
+
159
+ elif (
160
+ isinstance(data, dict)
161
+ and "timestamp" in data
162
+ and ("bids" in data or "asks" in data)
163
+ ):
164
+ # This is a depth stream message
165
+ if "depth" in self.message_handlers:
166
+ await self.message_handlers["depth"](data)
167
+ else:
168
+ self.logger.debug("No handler for depth stream")
169
+
170
+ else:
171
+ self.logger.debug(f"Unknown message format: {data}")
172
+
173
+ except json.JSONDecodeError:
174
+ self.logger.error(f"Failed to parse message: {message}")
175
+ except Exception as e:
176
+ self.logger.error(f"Error handling message: {e}")
177
+
178
+ async def _reconnect(self) -> None:
179
+ """Attempt to reconnect WebSocket."""
180
+ self.logger.info(
181
+ f"Attempting to reconnect in {self.reconnect_interval} seconds"
182
+ )
183
+ await asyncio.sleep(self.reconnect_interval)
184
+
185
+ try:
186
+ # For now, just reconnect to the first subscription if any exist
187
+ # In a more complex implementation, you'd want to handle multiple concurrent subscriptions
188
+ if self.subscriptions:
189
+ first_sub = next(iter(self.subscriptions.values()))
190
+ if first_sub.get("type") == "trade":
191
+ await self.connect(first_sub["endpoint"])
192
+ else:
193
+ await self.connect()
194
+ else:
195
+ await self.connect()
196
+
197
+ except Exception as e:
198
+ self.logger.error(f"Reconnection failed: {e}")
199
+ if self.auto_reconnect and not self.should_stop:
200
+ await self._reconnect()
201
+
202
+ async def _send_message(self, message: dict[str, Any]) -> None:
203
+ """Send message to WebSocket server."""
204
+ if not self.websocket or not self.is_connected:
205
+ raise ClientError(
206
+ 0, "WS_NOT_CONNECTED", "WebSocket not connected", {}, None
207
+ )
208
+
209
+ try:
210
+ await self.websocket.send(json.dumps(message))
211
+ except Exception as e:
212
+ self.logger.error(f"Failed to send message: {e}")
213
+ raise ClientError(0, "WS_SEND_ERROR", str(e), {}, None) from e
214
+
215
+ def register_handler(self, stream_type: str, handler: Callable) -> None:
216
+ """
217
+ Register a message handler for a specific stream type.
218
+
219
+ Args:
220
+ stream_type: Type of stream (e.g., 'trade', 'depth', 'price', 'account')
221
+ handler: Async function to handle messages
222
+ """
223
+ self.message_handlers[stream_type] = handler
224
+
225
+ async def subscribe_trades(self, symbol: str) -> None:
226
+ """
227
+ Subscribe to recent trades for a symbol using DeltaDeFi's specific endpoint.
228
+
229
+ Args:
230
+ symbol: Trading pair symbol (e.g., "ADAUSDM")
231
+ """
232
+ if not self.api_key:
233
+ raise ClientError(
234
+ 0, "API_KEY_REQUIRED", "API key required for trade streams", {}, None
235
+ )
236
+
237
+ # Close existing connection if any
238
+ if self.websocket:
239
+ await self.disconnect()
240
+
241
+ # Connect to the specific trades endpoint
242
+ endpoint_path = f"/market/recent-trades/{symbol}?limit=50"
243
+ await self.connect(endpoint_path)
244
+
245
+ # Store subscription info
246
+ self.subscriptions[f"trade_{symbol}"] = {
247
+ "type": "trade",
248
+ "symbol": symbol,
249
+ "endpoint": endpoint_path,
250
+ }
251
+ self.logger.info(f"Subscribed to trades for {symbol}")
252
+
253
+ async def subscribe_depth(self, symbol: str) -> None:
254
+ """
255
+ Subscribe to market depth for a symbol using DeltaDeFi's specific endpoint.
256
+
257
+ Args:
258
+ symbol: Trading pair symbol (e.g., "ADAUSDM")
259
+ """
260
+ if not self.api_key:
261
+ raise ClientError(
262
+ 0, "API_KEY_REQUIRED", "API key required for depth streams", {}, None
263
+ )
264
+
265
+ # Close existing connection if any
266
+ if self.websocket:
267
+ await self.disconnect()
268
+
269
+ # Connect to the specific depth endpoint
270
+ endpoint_path = f"/market/depth/{symbol}"
271
+ await self.connect(endpoint_path)
272
+
273
+ # Store subscription info
274
+ self.subscriptions[f"depth_{symbol}"] = {
275
+ "type": "depth",
276
+ "symbol": symbol,
277
+ "endpoint": endpoint_path,
278
+ }
279
+ self.logger.info(f"Subscribed to depth for {symbol}")
280
+
281
+ async def subscribe_price(self, symbol: str) -> None:
282
+ """
283
+ Subscribe to price streams for a symbol using DeltaDeFi's specific endpoint.
284
+
285
+ Args:
286
+ symbol: Trading pair symbol (e.g., "ADAUSDM")
287
+ """
288
+ if not self.api_key:
289
+ raise ClientError(
290
+ 0, "API_KEY_REQUIRED", "API key required for price streams", {}, None
291
+ )
292
+
293
+ # Close existing connection if any
294
+ if self.websocket:
295
+ await self.disconnect()
296
+
297
+ # Connect to the specific price endpoint
298
+ endpoint_path = f"/market/market-price/{symbol}"
299
+ await self.connect(endpoint_path)
300
+
301
+ # Store subscription info
302
+ self.subscriptions[f"price_{symbol}"] = {
303
+ "type": "price",
304
+ "symbol": symbol,
305
+ "endpoint": endpoint_path,
306
+ }
307
+ self.logger.info(f"Subscribed to price for {symbol}")
308
+
309
+ async def subscribe_account(self) -> None:
310
+ """
311
+ Subscribe to account streams using DeltaDeFi's specific endpoint.
312
+ Provides balance updates and order status updates.
313
+ """
314
+ if not self.api_key:
315
+ raise ClientError(
316
+ 0, "API_KEY_REQUIRED", "API key required for account streams", {}, None
317
+ )
318
+
319
+ # Close existing connection if any
320
+ if self.websocket:
321
+ await self.disconnect()
322
+
323
+ # Connect to the account stream endpoint
324
+ endpoint_path = "/accounts/stream"
325
+ await self.connect(endpoint_path)
326
+
327
+ # Store subscription info
328
+ self.subscriptions["account"] = {"type": "account", "endpoint": endpoint_path}
329
+ self.logger.info("Subscribed to account streams")
330
+
331
+ async def unsubscribe(self, subscription_key: str) -> None:
332
+ """
333
+ Unsubscribe from a stream.
334
+
335
+ Args:
336
+ subscription_key: Key of the subscription to cancel
337
+ """
338
+ if subscription_key not in self.subscriptions:
339
+ return
340
+
341
+ sub_data = self.subscriptions[subscription_key]
342
+ message = {
343
+ "method": "UNSUBSCRIBE",
344
+ "params": sub_data["params"],
345
+ "id": sub_data["id"],
346
+ }
347
+
348
+ await self._send_message(message)
349
+ del self.subscriptions[subscription_key]
350
+ self.logger.info(f"Unsubscribed from {subscription_key}")
351
+
352
+ async def unsubscribe_all(self) -> None:
353
+ """Unsubscribe from all streams."""
354
+ for sub_key in list(self.subscriptions.keys()):
355
+ await self.unsubscribe(sub_key)
deltadefi/error.py CHANGED
@@ -27,7 +27,7 @@ class ParameterRequiredError(Error):
27
27
  self.params = params
28
28
 
29
29
  def __str__(self):
30
- return "%s is mandatory, but received empty." % (", ".join(self.params))
30
+ return "{} is mandatory, but received empty.".format(", ".join(self.params))
31
31
 
32
32
 
33
33
  class ParameterValueError(Error):
@@ -35,7 +35,7 @@ class ParameterValueError(Error):
35
35
  self.params = params
36
36
 
37
37
  def __str__(self):
38
- return "the enum value %s is invalid." % (", ".join(self.params))
38
+ return "the enum value {} is invalid.".format(", ".join(self.params))
39
39
 
40
40
 
41
41
  class ParameterTypeError(Error):
@@ -1,5 +1,5 @@
1
1
  from dataclasses import dataclass
2
- from typing import List, Literal
2
+ from typing import Literal
3
3
 
4
4
  OrderStatusType = Literal["openOrder", "orderHistory", "tradingHistory"]
5
5
 
@@ -59,7 +59,7 @@ class OrderJSON:
59
59
  class DepositRecord:
60
60
  created_at: str
61
61
  status: TransactionStatus
62
- assets: List[AssetRecord]
62
+ assets: list[AssetRecord]
63
63
  tx_hash: str
64
64
 
65
65
 
@@ -67,7 +67,7 @@ class DepositRecord:
67
67
  class WithdrawalRecord:
68
68
  created_at: str
69
69
  status: TransactionStatus
70
- assets: List[AssetRecord]
70
+ assets: list[AssetRecord]
71
71
 
72
72
 
73
73
  @dataclass
@@ -1,5 +1,5 @@
1
1
  from dataclasses import dataclass
2
- from typing import List, TypedDict
2
+ from typing import TypedDict
3
3
 
4
4
  from deltadefi.models.models import (
5
5
  AssetBalance,
@@ -32,19 +32,31 @@ class SubmitDepositTransactionResponse(TypedDict):
32
32
 
33
33
 
34
34
  @dataclass
35
- class GetDepositRecordsResponse(List[DepositRecord]):
35
+ class GetDepositRecordsResponse(list[DepositRecord]):
36
36
  pass
37
37
 
38
38
 
39
39
  @dataclass
40
- class GetWithdrawalRecordsResponse(List[WithdrawalRecord]):
40
+ class GetWithdrawalRecordsResponse(list[WithdrawalRecord]):
41
41
  pass
42
42
 
43
43
 
44
+ @dataclass
45
+ class OrderRecordsData(TypedDict):
46
+ orders: list[OrderJSON]
47
+ order_filling_records: list[OrderFillingRecordJSON]
48
+
49
+
50
+ @dataclass
51
+ class GetOrderRecordsResponse(TypedDict):
52
+ data: list[OrderRecordsData]
53
+ total_count: int
54
+ total_page: int
55
+
56
+
44
57
  @dataclass
45
58
  class GetOrderRecordResponse(TypedDict):
46
- orders: List[OrderJSON]
47
- order_filling_records: List[OrderFillingRecordJSON]
59
+ order_json: OrderJSON
48
60
 
49
61
 
50
62
  @dataclass
@@ -76,5 +88,5 @@ class GetAccountInfoResponse(TypedDict):
76
88
 
77
89
 
78
90
  @dataclass
79
- class GetAccountBalanceResponse(List[AssetBalance]):
91
+ class GetAccountBalanceResponse(list[AssetBalance]):
80
92
  pass
@@ -1,5 +1,5 @@
1
1
  from dataclasses import dataclass
2
- from typing import List, TypedDict
2
+ from typing import TypedDict
3
3
 
4
4
  from deltadefi.models import OrderJSON
5
5
 
@@ -17,8 +17,8 @@ class MarketDepth(TypedDict):
17
17
 
18
18
  @dataclass
19
19
  class GetMarketDepthResponse(TypedDict):
20
- bids: List[MarketDepth]
21
- asks: List[MarketDepth]
20
+ bids: list[MarketDepth]
21
+ asks: list[MarketDepth]
22
22
 
23
23
 
24
24
  @dataclass
@@ -38,7 +38,7 @@ class Trade(TypedDict):
38
38
 
39
39
 
40
40
  @dataclass
41
- class GetAggregatedPriceResponse(List[Trade]):
41
+ class GetAggregatedPriceResponse(list[Trade]):
42
42
  pass
43
43
 
44
44
 
@@ -0,0 +1,2 @@
1
+ # flake8: noqa
2
+ from .helpers import *
@@ -9,7 +9,7 @@ from deltadefi.error import (
9
9
 
10
10
  def clean_none_value(d) -> dict:
11
11
  out = {}
12
- for k in d.keys():
12
+ for k in d:
13
13
  if d[k] is not None:
14
14
  out[k] = d[k]
15
15
  return out
@@ -33,7 +33,7 @@ def check_required_parameters(params):
33
33
 
34
34
 
35
35
  def check_enum_parameter(value, enum_class):
36
- if value not in set(item.value for item in enum_class):
36
+ if value not in {item.value for item in enum_class}:
37
37
  raise ParameterValueError([value])
38
38
 
39
39
 
@@ -1,29 +1,30 @@
1
- Metadata-Version: 2.3
1
+ Metadata-Version: 2.4
2
2
  Name: deltadefi
3
- Version: 0.0.11
3
+ Version: 0.1.1
4
4
  Summary: Python SDK for DeltaDeFi protocol.
5
- License: Apache-2.0
6
- Keywords: cardano
7
- Author: HinsonSIDAN
8
- Author-email: wongkahinhinson@gmail.com
9
- Requires-Python: >3.11,<4.0.0
5
+ Author-email: HinsonSIDAN <wongkahinhinson@gmail.com>
6
+ License-Expression: Apache-2.0
7
+ Keywords: cardano,defi,sdk,trading
8
+ Classifier: Development Status :: 3 - Alpha
10
9
  Classifier: Intended Audience :: Developers
11
10
  Classifier: License :: OSI Approved :: Apache Software License
12
11
  Classifier: Natural Language :: English
13
12
  Classifier: Programming Language :: Python :: 3
13
+ Classifier: Programming Language :: Python :: 3.11
14
14
  Classifier: Programming Language :: Python :: 3.12
15
15
  Classifier: Programming Language :: Python :: 3.13
16
- Classifier: Programming Language :: Python :: 3.11
17
- Requires-Dist: certifi (==2024.8.30)
18
- Requires-Dist: charset-normalizer (==3.4.0)
19
- Requires-Dist: dotenv (>=0.9.9,<0.10.0)
20
- Requires-Dist: idna (==3.10)
21
- Requires-Dist: pycardano (>=0.12.3,<0.13.0)
22
- Requires-Dist: requests (>=2.25,<3.0)
23
- Requires-Dist: sidan-gin (==0.1.6)
24
- Requires-Dist: urllib3 (==2.2.3)
25
- Project-URL: Documentation, https://github.com/deltadefi-protocol/python-sdk
26
- Project-URL: Homepage, https://github.com/deltadefi-protocol/python-sdk
16
+ Classifier: Topic :: Office/Business :: Financial :: Investment
17
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
18
+ Requires-Python: <4.0.0,>3.11
19
+ Requires-Dist: certifi>=2024.8.30
20
+ Requires-Dist: charset-normalizer>=3.4.0
21
+ Requires-Dist: idna>=3.10
22
+ Requires-Dist: pycardano>=0.12.3
23
+ Requires-Dist: python-dotenv>=0.9.9
24
+ Requires-Dist: requests>=2.25.0
25
+ Requires-Dist: sidan-gin>=0.1.6
26
+ Requires-Dist: urllib3>=2.2.3
27
+ Requires-Dist: websockets>=12.0
27
28
  Description-Content-Type: text/markdown
28
29
 
29
30
  # DeltaDeFi Python SDK
@@ -119,4 +120,3 @@ DELTADEFI_API_KEY=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx make test
119
120
  ## License
120
121
 
121
122
  Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at <http://www.apache.org/licenses/LICENSE-2.0>
122
-
@@ -0,0 +1,24 @@
1
+ deltadefi/__init__.py,sha256=pKZHfRdXT3f3kncxAKamtk5V3EDQB8Ocy8xBmjhsJ4A,63
2
+ deltadefi/api.py,sha256=jnTK7g1WHIDPbrYQWYdMfT0sgWcUgGKRn_uHVNBI-CY,2720
3
+ deltadefi/error.py,sha256=zDMx5ukb5zs0AOeGAHjXiIMDZ0LbEcaGyVi45WFJfmI,1658
4
+ deltadefi/api_resources/__init__.py,sha256=_SGHTpaQTIBvh9Rm868IT5pXpvvGBPqz3bxkY6YapZ4,61
5
+ deltadefi/api_resources/auth.py,sha256=4QCEI4P4UlQPQYctqY9Oat4hn7lsI95QihHTD_0PZKg,245
6
+ deltadefi/api_resources/validation.py,sha256=vz-hovpLy9SMOIFGcBHC8vWZH8CJRlQP8rcbbTSM-PM,1375
7
+ deltadefi/clients/__init__.py,sha256=4hyPuk6_bcJGXUElOvkgZ7ARlQ6QwKLp-nFgCXTbFVI,76
8
+ deltadefi/clients/accounts.py,sha256=sfdPh8CWsein1UAn8h-Y0JB_zMvr95FZx2QuaL6Tico,8407
9
+ deltadefi/clients/client.py,sha256=2hLOsxqBc8eu_6ovuYLRoK2popdI1_t3pGcEP8Keu9A,4619
10
+ deltadefi/clients/markets.py,sha256=--wMUFYkZryZjj8wO-rxxJhHEbM3UmcPpubrHU92Bdk,1985
11
+ deltadefi/clients/orders.py,sha256=AX6RZfLZFUonjKDPYc1T4wbxVomQeES1mzfJHSjhI-M,3886
12
+ deltadefi/clients/websocket.py,sha256=0454RunoE9eHqmQ0wrywEwxqrie1qEXq2ObxyKXopck,12424
13
+ deltadefi/constants/__init__.py,sha256=7LkrzfLTJsCCUl5IgZYrl-AbY_cf1fftcLklgnBYDTs,40
14
+ deltadefi/constants/constants.py,sha256=4bkY4kfNcsgoCe1xU8n2We7w-vxZXyzVw5rQvAsx4j8,168
15
+ deltadefi/models/__init__.py,sha256=oDJj6Y4gXN6C7Oz_t2fq8hej-D0G9OqfXjL4Jaeq8z8,37
16
+ deltadefi/models/models.py,sha256=kiRpCdzUh3WmyuFOaxlZ1rjsQ2cxLWjVFBCqsHXMtBc,1633
17
+ deltadefi/responses/__init__.py,sha256=JKSIUQu6qI_XhbAR2mVMCKNvR6x_vFZdyLGOuQTVrVY,64
18
+ deltadefi/responses/accounts.py,sha256=o-It4vyNsiDeCmHa-XQl77KuCVtJi7qlPdn059fgwcI,1590
19
+ deltadefi/responses/responses.py,sha256=Kz5PtDnx_AgKrV7NhZqrSMnS1wPlLbu13J2BKNzN0ME,1012
20
+ deltadefi/utils/__init__.py,sha256=krFwciyC3ArJ1j96b5IOVMqKfiFjnKtgQvYPsw3A-MU,38
21
+ deltadefi/utils/helpers.py,sha256=S90RpdkKJS-khuwk8B0vhOdTQXuUkutZ0RZLybeF550,1025
22
+ deltadefi-0.1.1.dist-info/METADATA,sha256=_Y9ZNj9oM_W99lWEj6HzoBb2uJo3Q6DDWh_sjN0jYGw,3075
23
+ deltadefi-0.1.1.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
24
+ deltadefi-0.1.1.dist-info/RECORD,,
@@ -1,4 +1,4 @@
1
1
  Wheel-Version: 1.0
2
- Generator: poetry-core 2.1.3
2
+ Generator: hatchling 1.27.0
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
deltadefi/clients/app.py DELETED
@@ -1,23 +0,0 @@
1
- from deltadefi.api import API
2
- from deltadefi.responses import GetTermsAndConditionResponse
3
-
4
-
5
- class App(API):
6
- """
7
- App client for interacting with the DeltaDeFi API.
8
- """
9
-
10
- group_url_path = "/app"
11
-
12
- def __init__(self, api_key=None, base_url=None, **kwargs):
13
- super().__init__(api_key=api_key, base_url=base_url, **kwargs)
14
-
15
- def get_terms_and_condition(self, **kwargs) -> GetTermsAndConditionResponse:
16
- """
17
- Get terms and conditions.
18
-
19
- Returns:
20
- A GetTermsAndConditionResponse object containing the terms and conditions.
21
- """
22
- url_path = "/terms-and-conditions"
23
- return self.send_request("GET", self.group_url_path + url_path, kwargs)
deltadefi/lib/__init__.py DELETED
File without changes
@@ -1,24 +0,0 @@
1
- deltadefi/__init__.py,sha256=_dbB-toNXZvwZxj5DnEY0nW5noDnDpF4QsJNEwGO_IA,46
2
- deltadefi/api.py,sha256=XSdOFwq9s2HFxKxiv7ljaCgUhwXVAkkq19dPSRhwlek,2720
3
- deltadefi/api_resources/__init__.py,sha256=_SGHTpaQTIBvh9Rm868IT5pXpvvGBPqz3bxkY6YapZ4,61
4
- deltadefi/api_resources/auth.py,sha256=Mpl4Dbh_d_gGhwLo2CtBSKxZ21DC74x-qjVhlczZCDE,278
5
- deltadefi/api_resources/validation.py,sha256=vz-hovpLy9SMOIFGcBHC8vWZH8CJRlQP8rcbbTSM-PM,1375
6
- deltadefi/clients/__init__.py,sha256=GEEsW2Sl-fPq0ilDsNyztoCDO7JSed14uMN2gOurIOI,37
7
- deltadefi/clients/accounts.py,sha256=L1170nEd67YXadKDi0uGybuqgx9Xx6X3caO7CXL_t3U,7912
8
- deltadefi/clients/app.py,sha256=TOgRlP83p91r7oS4ez8Gfm8soQzFHrJAmOHZJoGZ4SM,712
9
- deltadefi/clients/client.py,sha256=khtgJYE4m6VFPLylVUe5a52SWu6kzdtHdse7XXy0LoE,4284
10
- deltadefi/clients/markets.py,sha256=v8hK06oXC73qS3IjvWDempHq_-9T6OW2pckIcDR7P2M,2580
11
- deltadefi/clients/orders.py,sha256=gnh8AcXWI1QQK9riJtsu_1BqzuOml5OGf4bFP6yfy9g,3890
12
- deltadefi/constants/__init__.py,sha256=7LkrzfLTJsCCUl5IgZYrl-AbY_cf1fftcLklgnBYDTs,40
13
- deltadefi/constants/constants.py,sha256=4bkY4kfNcsgoCe1xU8n2We7w-vxZXyzVw5rQvAsx4j8,168
14
- deltadefi/error.py,sha256=Pq55p7FQbVn1GTih7NQBI7ZcVUUrlkaFKn-SwZUxBA8,1650
15
- deltadefi/lib/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
16
- deltadefi/lib/utils.py,sha256=zuQFAKQphbGxDdPzBURw4A2n3AkRSbzmjMLHPLm9Ed4,1035
17
- deltadefi/models/__init__.py,sha256=oDJj6Y4gXN6C7Oz_t2fq8hej-D0G9OqfXjL4Jaeq8z8,37
18
- deltadefi/models/models.py,sha256=Fgk3W6Ps1tibnE3cJTaBt5OPfVKl70nIDxDFsu1m5bk,1639
19
- deltadefi/responses/__init__.py,sha256=JKSIUQu6qI_XhbAR2mVMCKNvR6x_vFZdyLGOuQTVrVY,64
20
- deltadefi/responses/accounts.py,sha256=pUs3_M-kMprN_kCn0wda1Ox3hvoF1irE2zdCRKeP6ZU,1393
21
- deltadefi/responses/responses.py,sha256=JZrnBWZZGM_yyulrcgYNdJyw-8bOhlsmMTK3xZbuBKM,1018
22
- deltadefi-0.0.11.dist-info/METADATA,sha256=TdzbY7KZ2C2r3jiFfmEi9SvfPfbfCbWg3JCbJ9LPQmU,3027
23
- deltadefi-0.0.11.dist-info/WHEEL,sha256=b4K_helf-jlQoXBBETfwnf4B04YC67LOev0jo4fX5m8,88
24
- deltadefi-0.0.11.dist-info/RECORD,,