kaq-quant-common 0.2.17__py3-none-any.whl → 0.2.18__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.
- kaq_quant_common/api/common/__init__.py +1 -1
- kaq_quant_common/api/common/api_interface.py +38 -38
- kaq_quant_common/api/rest/api_client_base.py +187 -187
- kaq_quant_common/api/rest/instruction/helper/commission_helper.py +141 -141
- kaq_quant_common/api/rest/instruction/helper/mock_order_helper.py +346 -346
- kaq_quant_common/api/rest/instruction/helper/order_helper.py +362 -362
- kaq_quant_common/api/rest/instruction/instruction_client.py +40 -2
- kaq_quant_common/api/rest/instruction/instruction_server_base.py +62 -53
- kaq_quant_common/api/rest/instruction/models/__init__.py +17 -17
- kaq_quant_common/api/rest/instruction/models/kline.py +60 -0
- kaq_quant_common/api/rest/instruction/models/transfer.py +32 -32
- kaq_quant_common/api/ws/exchange/models.py +23 -23
- kaq_quant_common/api/ws/exchange/ws_exchange_server.py +440 -440
- kaq_quant_common/common/ddb_table_monitor.py +106 -106
- kaq_quant_common/common/http_monitor.py +69 -69
- kaq_quant_common/common/monitor_base.py +84 -84
- kaq_quant_common/common/monitor_group.py +97 -97
- kaq_quant_common/common/ws_wrapper.py +21 -21
- kaq_quant_common/utils/logger_utils.py +4 -4
- kaq_quant_common/utils/signal_utils.py +23 -23
- kaq_quant_common/utils/uuid_utils.py +5 -5
- {kaq_quant_common-0.2.17.dist-info → kaq_quant_common-0.2.18.dist-info}/METADATA +1 -1
- {kaq_quant_common-0.2.17.dist-info → kaq_quant_common-0.2.18.dist-info}/RECORD +24 -23
- {kaq_quant_common-0.2.17.dist-info → kaq_quant_common-0.2.18.dist-info}/WHEEL +1 -1
|
@@ -1,141 +1,141 @@
|
|
|
1
|
-
import json
|
|
2
|
-
import pandas as pd
|
|
3
|
-
from typing import Optional
|
|
4
|
-
|
|
5
|
-
from kaq_quant_common.utils import logger_utils
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
class CommissionHelper:
|
|
9
|
-
"""手续费助手,用于从Redis加载和获取交易对的手续费率"""
|
|
10
|
-
|
|
11
|
-
def __init__(self, ins_server):
|
|
12
|
-
# 必须放在这里 延迟引入,否则会有循环引用问题
|
|
13
|
-
from kaq_quant_common.api.rest.instruction.instruction_server_base import (
|
|
14
|
-
InstructionServerBase,
|
|
15
|
-
)
|
|
16
|
-
|
|
17
|
-
self._server: InstructionServerBase = ins_server
|
|
18
|
-
self._logger = logger_utils.get_logger(self)
|
|
19
|
-
|
|
20
|
-
# 手续费数据缓存
|
|
21
|
-
self._commission_data: Optional[pd.DataFrame] = None
|
|
22
|
-
# 是否已加载
|
|
23
|
-
self._loaded = False
|
|
24
|
-
|
|
25
|
-
def _load_commission_rates(self):
|
|
26
|
-
"""从Redis加载手续费率数据"""
|
|
27
|
-
if self._loaded:
|
|
28
|
-
return
|
|
29
|
-
|
|
30
|
-
redis = self._server._redis
|
|
31
|
-
if redis is None:
|
|
32
|
-
self._logger.warning("Redis未配置,无法加载手续费率")
|
|
33
|
-
return
|
|
34
|
-
|
|
35
|
-
exchange = self._server._exchange
|
|
36
|
-
# 组装Redis key,格式: kaq_{exchange}_futures_commission_rate
|
|
37
|
-
redis_key = f"kaq_{exchange}_futures_commission_rate"
|
|
38
|
-
|
|
39
|
-
try:
|
|
40
|
-
self._logger.info(f"Loading commission rates from Redis key: {redis_key}")
|
|
41
|
-
# 从Redis读取list数据
|
|
42
|
-
data_list = redis.lrange(redis_key)
|
|
43
|
-
|
|
44
|
-
if data_list is not None and not data_list.empty:
|
|
45
|
-
self._commission_data = data_list
|
|
46
|
-
self._loaded = True
|
|
47
|
-
self._logger.info(
|
|
48
|
-
f"Successfully loaded {len(self._commission_data)} commission rates"
|
|
49
|
-
)
|
|
50
|
-
else:
|
|
51
|
-
self._logger.warning(f"No commission rate data found in Redis key: {redis_key}")
|
|
52
|
-
except Exception as e:
|
|
53
|
-
self._logger.error(f"Failed to load commission rates from Redis: {e}")
|
|
54
|
-
|
|
55
|
-
def get_taker_commission_rate(self, symbol: str, default_rate: float = 0.0005) -> float:
|
|
56
|
-
"""
|
|
57
|
-
获取指定交易对的taker手续费率
|
|
58
|
-
|
|
59
|
-
Args:
|
|
60
|
-
symbol: 交易对,如 BTCUSDT
|
|
61
|
-
default_rate: 默认手续费率,如果获取失败则使用该值
|
|
62
|
-
|
|
63
|
-
Returns:
|
|
64
|
-
float: taker手续费率
|
|
65
|
-
"""
|
|
66
|
-
# 如果还没加载,先加载
|
|
67
|
-
if not self._loaded:
|
|
68
|
-
self._load_commission_rates()
|
|
69
|
-
|
|
70
|
-
# 如果还是没有数据,返回默认值
|
|
71
|
-
if self._commission_data is None or self._commission_data.empty:
|
|
72
|
-
self._logger.warning(
|
|
73
|
-
f"Commission data not available, using default rate: {default_rate}"
|
|
74
|
-
)
|
|
75
|
-
return default_rate
|
|
76
|
-
|
|
77
|
-
try:
|
|
78
|
-
# 从DataFrame中查找对应的symbol
|
|
79
|
-
matched = self._commission_data[self._commission_data["symbol"] == symbol]
|
|
80
|
-
|
|
81
|
-
if not matched.empty:
|
|
82
|
-
rate = float(matched.iloc[0]["takerCommissionRate"])
|
|
83
|
-
self._logger.debug(f"Found taker commission rate for {symbol}: {rate}")
|
|
84
|
-
return rate
|
|
85
|
-
else:
|
|
86
|
-
self._logger.warning(
|
|
87
|
-
f"Symbol {symbol} not found in commission data, using default rate: {default_rate}"
|
|
88
|
-
)
|
|
89
|
-
return default_rate
|
|
90
|
-
except Exception as e:
|
|
91
|
-
self._logger.error(
|
|
92
|
-
f"Error getting commission rate for {symbol}: {e}, using default rate: {default_rate}"
|
|
93
|
-
)
|
|
94
|
-
return default_rate
|
|
95
|
-
|
|
96
|
-
def get_maker_commission_rate(self, symbol: str, default_rate: float = 0.0002) -> float:
|
|
97
|
-
"""
|
|
98
|
-
获取指定交易对的maker手续费率
|
|
99
|
-
|
|
100
|
-
Args:
|
|
101
|
-
symbol: 交易对,如 BTCUSDT
|
|
102
|
-
default_rate: 默认手续费率,如果获取失败则使用该值
|
|
103
|
-
|
|
104
|
-
Returns:
|
|
105
|
-
float: maker手续费率
|
|
106
|
-
"""
|
|
107
|
-
# 如果还没加载,先加载
|
|
108
|
-
if not self._loaded:
|
|
109
|
-
self._load_commission_rates()
|
|
110
|
-
|
|
111
|
-
# 如果还是没有数据,返回默认值
|
|
112
|
-
if self._commission_data is None or self._commission_data.empty:
|
|
113
|
-
self._logger.warning(
|
|
114
|
-
f"Commission data not available, using default rate: {default_rate}"
|
|
115
|
-
)
|
|
116
|
-
return default_rate
|
|
117
|
-
|
|
118
|
-
try:
|
|
119
|
-
# 从DataFrame中查找对应的symbol
|
|
120
|
-
matched = self._commission_data[self._commission_data["symbol"] == symbol]
|
|
121
|
-
|
|
122
|
-
if not matched.empty:
|
|
123
|
-
rate = float(matched.iloc[0]["makerCommissionRate"])
|
|
124
|
-
self._logger.debug(f"Found maker commission rate for {symbol}: {rate}")
|
|
125
|
-
return rate
|
|
126
|
-
else:
|
|
127
|
-
self._logger.warning(
|
|
128
|
-
f"Symbol {symbol} not found in commission data, using default rate: {default_rate}"
|
|
129
|
-
)
|
|
130
|
-
return default_rate
|
|
131
|
-
except Exception as e:
|
|
132
|
-
self._logger.error(
|
|
133
|
-
f"Error getting commission rate for {symbol}: {e}, using default rate: {default_rate}"
|
|
134
|
-
)
|
|
135
|
-
return default_rate
|
|
136
|
-
|
|
137
|
-
def reload(self):
|
|
138
|
-
"""重新加载手续费率数据"""
|
|
139
|
-
self._loaded = False
|
|
140
|
-
self._commission_data = None
|
|
141
|
-
self._load_commission_rates()
|
|
1
|
+
import json
|
|
2
|
+
import pandas as pd
|
|
3
|
+
from typing import Optional
|
|
4
|
+
|
|
5
|
+
from kaq_quant_common.utils import logger_utils
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class CommissionHelper:
|
|
9
|
+
"""手续费助手,用于从Redis加载和获取交易对的手续费率"""
|
|
10
|
+
|
|
11
|
+
def __init__(self, ins_server):
|
|
12
|
+
# 必须放在这里 延迟引入,否则会有循环引用问题
|
|
13
|
+
from kaq_quant_common.api.rest.instruction.instruction_server_base import (
|
|
14
|
+
InstructionServerBase,
|
|
15
|
+
)
|
|
16
|
+
|
|
17
|
+
self._server: InstructionServerBase = ins_server
|
|
18
|
+
self._logger = logger_utils.get_logger(self)
|
|
19
|
+
|
|
20
|
+
# 手续费数据缓存
|
|
21
|
+
self._commission_data: Optional[pd.DataFrame] = None
|
|
22
|
+
# 是否已加载
|
|
23
|
+
self._loaded = False
|
|
24
|
+
|
|
25
|
+
def _load_commission_rates(self):
|
|
26
|
+
"""从Redis加载手续费率数据"""
|
|
27
|
+
if self._loaded:
|
|
28
|
+
return
|
|
29
|
+
|
|
30
|
+
redis = self._server._redis
|
|
31
|
+
if redis is None:
|
|
32
|
+
self._logger.warning("Redis未配置,无法加载手续费率")
|
|
33
|
+
return
|
|
34
|
+
|
|
35
|
+
exchange = self._server._exchange
|
|
36
|
+
# 组装Redis key,格式: kaq_{exchange}_futures_commission_rate
|
|
37
|
+
redis_key = f"kaq_{exchange}_futures_commission_rate"
|
|
38
|
+
|
|
39
|
+
try:
|
|
40
|
+
self._logger.info(f"Loading commission rates from Redis key: {redis_key}")
|
|
41
|
+
# 从Redis读取list数据
|
|
42
|
+
data_list = redis.lrange(redis_key)
|
|
43
|
+
|
|
44
|
+
if data_list is not None and not data_list.empty:
|
|
45
|
+
self._commission_data = data_list
|
|
46
|
+
self._loaded = True
|
|
47
|
+
self._logger.info(
|
|
48
|
+
f"Successfully loaded {len(self._commission_data)} commission rates"
|
|
49
|
+
)
|
|
50
|
+
else:
|
|
51
|
+
self._logger.warning(f"No commission rate data found in Redis key: {redis_key}")
|
|
52
|
+
except Exception as e:
|
|
53
|
+
self._logger.error(f"Failed to load commission rates from Redis: {e}")
|
|
54
|
+
|
|
55
|
+
def get_taker_commission_rate(self, symbol: str, default_rate: float = 0.0005) -> float:
|
|
56
|
+
"""
|
|
57
|
+
获取指定交易对的taker手续费率
|
|
58
|
+
|
|
59
|
+
Args:
|
|
60
|
+
symbol: 交易对,如 BTCUSDT
|
|
61
|
+
default_rate: 默认手续费率,如果获取失败则使用该值
|
|
62
|
+
|
|
63
|
+
Returns:
|
|
64
|
+
float: taker手续费率
|
|
65
|
+
"""
|
|
66
|
+
# 如果还没加载,先加载
|
|
67
|
+
if not self._loaded:
|
|
68
|
+
self._load_commission_rates()
|
|
69
|
+
|
|
70
|
+
# 如果还是没有数据,返回默认值
|
|
71
|
+
if self._commission_data is None or self._commission_data.empty:
|
|
72
|
+
self._logger.warning(
|
|
73
|
+
f"Commission data not available, using default rate: {default_rate}"
|
|
74
|
+
)
|
|
75
|
+
return default_rate
|
|
76
|
+
|
|
77
|
+
try:
|
|
78
|
+
# 从DataFrame中查找对应的symbol
|
|
79
|
+
matched = self._commission_data[self._commission_data["symbol"] == symbol]
|
|
80
|
+
|
|
81
|
+
if not matched.empty:
|
|
82
|
+
rate = float(matched.iloc[0]["takerCommissionRate"])
|
|
83
|
+
self._logger.debug(f"Found taker commission rate for {symbol}: {rate}")
|
|
84
|
+
return rate
|
|
85
|
+
else:
|
|
86
|
+
self._logger.warning(
|
|
87
|
+
f"Symbol {symbol} not found in commission data, using default rate: {default_rate}"
|
|
88
|
+
)
|
|
89
|
+
return default_rate
|
|
90
|
+
except Exception as e:
|
|
91
|
+
self._logger.error(
|
|
92
|
+
f"Error getting commission rate for {symbol}: {e}, using default rate: {default_rate}"
|
|
93
|
+
)
|
|
94
|
+
return default_rate
|
|
95
|
+
|
|
96
|
+
def get_maker_commission_rate(self, symbol: str, default_rate: float = 0.0002) -> float:
|
|
97
|
+
"""
|
|
98
|
+
获取指定交易对的maker手续费率
|
|
99
|
+
|
|
100
|
+
Args:
|
|
101
|
+
symbol: 交易对,如 BTCUSDT
|
|
102
|
+
default_rate: 默认手续费率,如果获取失败则使用该值
|
|
103
|
+
|
|
104
|
+
Returns:
|
|
105
|
+
float: maker手续费率
|
|
106
|
+
"""
|
|
107
|
+
# 如果还没加载,先加载
|
|
108
|
+
if not self._loaded:
|
|
109
|
+
self._load_commission_rates()
|
|
110
|
+
|
|
111
|
+
# 如果还是没有数据,返回默认值
|
|
112
|
+
if self._commission_data is None or self._commission_data.empty:
|
|
113
|
+
self._logger.warning(
|
|
114
|
+
f"Commission data not available, using default rate: {default_rate}"
|
|
115
|
+
)
|
|
116
|
+
return default_rate
|
|
117
|
+
|
|
118
|
+
try:
|
|
119
|
+
# 从DataFrame中查找对应的symbol
|
|
120
|
+
matched = self._commission_data[self._commission_data["symbol"] == symbol]
|
|
121
|
+
|
|
122
|
+
if not matched.empty:
|
|
123
|
+
rate = float(matched.iloc[0]["makerCommissionRate"])
|
|
124
|
+
self._logger.debug(f"Found maker commission rate for {symbol}: {rate}")
|
|
125
|
+
return rate
|
|
126
|
+
else:
|
|
127
|
+
self._logger.warning(
|
|
128
|
+
f"Symbol {symbol} not found in commission data, using default rate: {default_rate}"
|
|
129
|
+
)
|
|
130
|
+
return default_rate
|
|
131
|
+
except Exception as e:
|
|
132
|
+
self._logger.error(
|
|
133
|
+
f"Error getting commission rate for {symbol}: {e}, using default rate: {default_rate}"
|
|
134
|
+
)
|
|
135
|
+
return default_rate
|
|
136
|
+
|
|
137
|
+
def reload(self):
|
|
138
|
+
"""重新加载手续费率数据"""
|
|
139
|
+
self._loaded = False
|
|
140
|
+
self._commission_data = None
|
|
141
|
+
self._load_commission_rates()
|