tushare 1.4.5__py3-none-any.whl → 1.4.6__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.
Files changed (46) hide show
  1. baks/__init__.py +0 -0
  2. baks/demo.py +184 -0
  3. baks/rtqc.py +612 -0
  4. baks/setup.py +15 -0
  5. baks/sss.py +56 -0
  6. test/__init__.py +0 -0
  7. test/bar_test.py +23 -0
  8. test/billboard_test.py +35 -0
  9. test/build_pyd/__init__.py +8 -0
  10. test/build_pyd/rtqc.py +612 -0
  11. test/build_pyd/setup.py +15 -0
  12. test/build_pyd//321/206/320/231/320/243/321/205/320/234/320/225pyd/321/205/320/241/342/225/234/321/204/342/225/227/320/264.txt +1 -0
  13. test/classifying_test.py +50 -0
  14. test/dateu_test.py +19 -0
  15. test/fund_test.py +43 -0
  16. test/indictor_test.py +23 -0
  17. test/macro_test.py +50 -0
  18. test/nav_test.py +104 -0
  19. test/news_test.py +38 -0
  20. test/pro_test.py +11 -0
  21. test/ref_test.py +57 -0
  22. test/shibor_test.py +33 -0
  23. test/storing_test.py +61 -0
  24. test/test_query.py +16 -0
  25. test/test_realtime.py +24 -0
  26. test/test_realtime_quote.py +13 -0
  27. test/test_sdk_event.py +21 -0
  28. test/test_stk_mins.py +16 -0
  29. test/test_stock_basic.py +16 -0
  30. test/test_tgw_subscribe.py +28 -0
  31. test/test_ts_subscribe.py +22 -0
  32. test/test_websocket.py +52 -0
  33. test/trading_test.py +43 -0
  34. tushare/__init__.py +1 -1
  35. tushare/stock/rtq.py +6 -4
  36. tushare/stock/rtqc.pyd +0 -0
  37. tushare/subs/ht_subs/service/__init__.py +0 -0
  38. tushare/subs/ht_subs/service/covert.py +189 -0
  39. tushare/subs/model/tick.py +128 -128
  40. tushare/subs/tgw_subs/convert.py +20 -20
  41. tushare/subs/ts_subs.py +192 -0
  42. {tushare-1.4.5.dist-info → tushare-1.4.6.dist-info}/METADATA +101 -101
  43. {tushare-1.4.5.dist-info → tushare-1.4.6.dist-info}/RECORD +46 -9
  44. {tushare-1.4.5.dist-info → tushare-1.4.6.dist-info}/WHEEL +1 -1
  45. {tushare-1.4.5.dist-info → tushare-1.4.6.dist-info}/top_level.txt +1 -0
  46. {tushare-1.4.5.dist-info → tushare-1.4.6.dist-info}/LICENSE +0 -0
@@ -1,128 +1,128 @@
1
- from datetime import datetime
2
- from typing import Optional
3
-
4
- from pydantic import BaseModel
5
-
6
-
7
- class TsTick(BaseModel):
8
- ts_code: str
9
- name: Optional[str]
10
- trade_time: Optional[datetime]
11
- pre_close_price: Optional[float]
12
- last_price: Optional[float]
13
- open_price: Optional[float]
14
- high_price: Optional[float]
15
- low_price: Optional[float]
16
- close_price: Optional[float]
17
- volume: Optional[int] # 成交量
18
- amount: Optional[int] # 成交金额
19
- count: Optional[int] # 交易数量
20
- ask_price1: Optional[float] # 申卖价, 委托档位卖1档价格
21
- ask_volume1: Optional[int] # 申卖量
22
- bid_price1: Optional[float] # 申买价, 委托档位买1档价格
23
- bid_volume1: Optional[int] # 申买量
24
- ask_price2: Optional[float]
25
- ask_volume2: Optional[int]
26
- bid_price2: Optional[float]
27
- bid_volume2: Optional[int]
28
- ask_price3: Optional[float]
29
- ask_volume3: Optional[int]
30
- bid_price3: Optional[float]
31
- bid_volume3: Optional[int]
32
- ask_price4: Optional[float]
33
- ask_volume4: Optional[int]
34
- bid_price4: Optional[float]
35
- bid_volume4: Optional[int]
36
- ask_price5: Optional[float]
37
- ask_volume5: Optional[int]
38
- bid_price5: Optional[float]
39
- bid_volume5: Optional[int]
40
- ask_price6: Optional[float]
41
- ask_volume6: Optional[int]
42
- bid_price6: Optional[float]
43
- bid_volume6: Optional[int]
44
- ask_price7: Optional[float]
45
- ask_volume7: Optional[int]
46
- bid_price7: Optional[float]
47
- bid_volume7: Optional[int]
48
- ask_price8: Optional[float]
49
- ask_volume8: Optional[int]
50
- bid_price8: Optional[float]
51
- bid_volume8: Optional[int]
52
- ask_price9: Optional[float]
53
- ask_volume9: Optional[int]
54
- bid_price9: Optional[float]
55
- bid_volume9: Optional[int]
56
- ask_price10: Optional[float]
57
- ask_volume10: Optional[int]
58
- bid_price10: Optional[float]
59
- bid_volume10: Optional[int]
60
-
61
-
62
- class TsTickIdx(BaseModel):
63
- ts_code: str
64
- name: Optional[str]
65
- trade_time: Optional[datetime]
66
- last_price: Optional[float] # last_price 单位元
67
- pre_close_price: Optional[float] # pre_close_price
68
- high_price: Optional[float] # high_price
69
- open_price: Optional[float] # open_price
70
- low_price: Optional[float] # low_price
71
- close_price: Optional[float] # close_price
72
- volume: Optional[int] # volume, 成交总量
73
- amount: Optional[float] # amount, 成交总金额
74
-
75
-
76
- class TsTickOpt(BaseModel):
77
- ts_code: str
78
- instrument_id: str
79
- trade_time: Optional[datetime]
80
- pre_price: Optional[float] # 单位元
81
- price: Optional[float]
82
- open: Optional[float]
83
- high: Optional[float]
84
- low: Optional[float]
85
- close: Optional[float]
86
- open_int: Optional[int]
87
- vol: Optional[float]
88
- amount: Optional[float]
89
- num: Optional[int]
90
- ask_price1: Optional[float]
91
- ask_volume1: Optional[int]
92
- bid_price1: Optional[float]
93
- bid_volume1: Optional[int]
94
- pre_delta: Optional[float] # 昨虚实度,暂未提供
95
- dif_price1: Optional[float]
96
- dif_price2: Optional[float]
97
- high_limit_price: Optional[float]
98
- low_limit_price: Optional[float]
99
- refer_price: Optional[float] # 参考价,港股使用
100
-
101
-
102
- class TsTickFuture(BaseModel):
103
- ts_code: str
104
- instrument_id: Optional[str]
105
- trade_time: Optional[datetime]
106
- pre_price: Optional[float]
107
- price: Optional[float]
108
- open: Optional[float]
109
- high: Optional[float]
110
- low: Optional[float]
111
- close: Optional[float]
112
- open_int: Optional[int]
113
- vol: Optional[int]
114
- amount: Optional[int] # 单数量
115
- num: Optional[int]
116
- ask_price1: Optional[float]
117
- ask_volume1: Optional[int]
118
- bid_price1: Optional[float]
119
- bid_volume1: Optional[int]
120
- pre_delta: Optional[float]
121
- curr_delta: Optional[float]
122
- dif_price1: Optional[float]
123
- dif_price2: Optional[float]
124
- high_limit_price: Optional[float]
125
- low_limit_price: Optional[float]
126
- refer_price: Optional[float]
127
- pre_settle_price: Optional[float]
128
- settle_price: Optional[float]
1
+ from datetime import datetime
2
+ from typing import Optional
3
+
4
+ from pydantic import BaseModel
5
+
6
+
7
+ class TsTick(BaseModel):
8
+ ts_code: str
9
+ name: Optional[str]
10
+ trade_time: Optional[datetime]
11
+ pre_close_price: Optional[float]
12
+ last_price: Optional[float]
13
+ open_price: Optional[float]
14
+ high_price: Optional[float]
15
+ low_price: Optional[float]
16
+ close_price: Optional[float]
17
+ volume: Optional[int] # 成交量
18
+ amount: Optional[int] # 成交金额
19
+ count: Optional[int] # 交易数量
20
+ ask_price1: Optional[float] # 申卖价, 委托档位卖1档价格
21
+ ask_volume1: Optional[int] # 申卖量
22
+ bid_price1: Optional[float] # 申买价, 委托档位买1档价格
23
+ bid_volume1: Optional[int] # 申买量
24
+ ask_price2: Optional[float]
25
+ ask_volume2: Optional[int]
26
+ bid_price2: Optional[float]
27
+ bid_volume2: Optional[int]
28
+ ask_price3: Optional[float]
29
+ ask_volume3: Optional[int]
30
+ bid_price3: Optional[float]
31
+ bid_volume3: Optional[int]
32
+ ask_price4: Optional[float]
33
+ ask_volume4: Optional[int]
34
+ bid_price4: Optional[float]
35
+ bid_volume4: Optional[int]
36
+ ask_price5: Optional[float]
37
+ ask_volume5: Optional[int]
38
+ bid_price5: Optional[float]
39
+ bid_volume5: Optional[int]
40
+ ask_price6: Optional[float]
41
+ ask_volume6: Optional[int]
42
+ bid_price6: Optional[float]
43
+ bid_volume6: Optional[int]
44
+ ask_price7: Optional[float]
45
+ ask_volume7: Optional[int]
46
+ bid_price7: Optional[float]
47
+ bid_volume7: Optional[int]
48
+ ask_price8: Optional[float]
49
+ ask_volume8: Optional[int]
50
+ bid_price8: Optional[float]
51
+ bid_volume8: Optional[int]
52
+ ask_price9: Optional[float]
53
+ ask_volume9: Optional[int]
54
+ bid_price9: Optional[float]
55
+ bid_volume9: Optional[int]
56
+ ask_price10: Optional[float]
57
+ ask_volume10: Optional[int]
58
+ bid_price10: Optional[float]
59
+ bid_volume10: Optional[int]
60
+
61
+
62
+ class TsTickIdx(BaseModel):
63
+ ts_code: str
64
+ name: Optional[str]
65
+ trade_time: Optional[datetime]
66
+ last_price: Optional[float] # last_price
67
+ pre_close_price: Optional[float] # pre_close_price
68
+ high_price: Optional[float] # high_price
69
+ open_price: Optional[float] # open_price
70
+ low_price: Optional[float] # low_price
71
+ close_price: Optional[float] # close_price
72
+ volume: Optional[int] # volume, 成交总量
73
+ amount: Optional[float] # amount, 成交总金额
74
+
75
+
76
+ class TsTickOpt(BaseModel):
77
+ ts_code: str
78
+ instrument_id: str
79
+ trade_time: Optional[datetime]
80
+ pre_price: Optional[float]
81
+ price: Optional[float]
82
+ open: Optional[float]
83
+ high: Optional[float]
84
+ low: Optional[float]
85
+ close: Optional[float]
86
+ open_int: Optional[int]
87
+ vol: Optional[float]
88
+ amount: Optional[float]
89
+ num: Optional[int]
90
+ ask_price1: Optional[float]
91
+ ask_volume1: Optional[int]
92
+ bid_price1: Optional[float]
93
+ bid_volume1: Optional[int]
94
+ pre_delta: Optional[float] # 昨虚实度,暂未提供
95
+ dif_price1: Optional[float]
96
+ dif_price2: Optional[float]
97
+ high_limit_price: Optional[float]
98
+ low_limit_price: Optional[float]
99
+ refer_price: Optional[float] # 参考价,港股使用
100
+
101
+
102
+ class TsTickFuture(BaseModel):
103
+ ts_code: str
104
+ instrument_id: Optional[str]
105
+ trade_time: Optional[datetime]
106
+ pre_price: Optional[float]
107
+ price: Optional[float]
108
+ open: Optional[float]
109
+ high: Optional[float]
110
+ low: Optional[float]
111
+ close: Optional[float]
112
+ open_int: Optional[int]
113
+ vol: Optional[int]
114
+ amount: Optional[int] # 单数量
115
+ num: Optional[int]
116
+ ask_price1: Optional[float]
117
+ ask_volume1: Optional[int]
118
+ bid_price1: Optional[float]
119
+ bid_volume1: Optional[int]
120
+ pre_delta: Optional[float]
121
+ curr_delta: Optional[float]
122
+ dif_price1: Optional[float]
123
+ dif_price2: Optional[float]
124
+ high_limit_price: Optional[float]
125
+ low_limit_price: Optional[float]
126
+ refer_price: Optional[float]
127
+ pre_settle_price: Optional[float]
128
+ settle_price: Optional[float]
@@ -62,14 +62,14 @@ def convert_tick_index(tgw_data: dict) -> TsTickIdx:
62
62
  ts_code=get_ts_code(tgw_data.get("market_type"), tgw_data.get("security_code")),
63
63
  name=None,
64
64
  trade_time=datetime.strptime(str(tgw_data.get('orig_time'))[:-3], '%Y%m%d%H%M%S'),
65
- last_price=tgw_data.get('last_index')/1000000,
66
- pre_close_price=tgw_data.get('pre_close_index')/1000000,
67
- open_price=tgw_data.get('open_index')/1000000,
68
- high_price=tgw_data.get('high_index')/1000000,
69
- low_price=tgw_data.get('low_index')/1000000,
70
- close_price=tgw_data.get('close_index')/1000000,
71
- volume=tgw_data.get('total_volume_trade')/100,
72
- amount=tgw_data.get('total_value_trade')/100000,
65
+ last_price=tgw_data.get('last_index'),
66
+ pre_close_price=tgw_data.get('pre_close_index'),
67
+ open_price=tgw_data.get('open_index'),
68
+ high_price=tgw_data.get('high_index'),
69
+ low_price=tgw_data.get('low_index'),
70
+ close_price=tgw_data.get('close_index'),
71
+ volume=tgw_data.get('total_volume_trade'),
72
+ amount=tgw_data.get('total_value_trade'),
73
73
  )
74
74
  return item
75
75
 
@@ -138,22 +138,22 @@ def convert_tick_stock(tgw_data: dict) -> TsTick:
138
138
  """
139
139
  extra = {}
140
140
  for i in range(1, 11):
141
- extra[f'ask_price{i}'] = tgw_data.get(f'offer_price{i}')/1000000
142
- extra[f'ask_volume{i}'] = tgw_data.get(f'offer_volume{i}')/100
143
- extra[f'bid_price{i}'] = tgw_data.get(f'bid_price{i}')/1000000
144
- extra[f'bid_volume{i}'] = tgw_data.get(f'bid_volume{i}')/100
141
+ extra[f'ask_price{i}'] = tgw_data.get(f'offer_price{i}')
142
+ extra[f'ask_volume{i}'] = tgw_data.get(f'offer_volume{i}')
143
+ extra[f'bid_price{i}'] = tgw_data.get(f'bid_price{i}')
144
+ extra[f'bid_volume{i}'] = tgw_data.get(f'bid_volume{i}')
145
145
  item = TsTick(
146
146
  ts_code=get_ts_code(tgw_data.get("market_type"), tgw_data.get("security_code")),
147
147
  name=None,
148
148
  trade_time=datetime.strptime(str(tgw_data.get('orig_time'))[:-3], '%Y%m%d%H%M%S'),
149
- pre_close_price=tgw_data.get("pre_close_price")/1000000,
150
- last_price=tgw_data.get("last_price")/1000000,
151
- open_price=tgw_data.get("open_price")/1000000,
152
- high_price=tgw_data.get("high_price")/1000000,
153
- low_price=tgw_data.get("low_price")/1000000,
154
- close_price=tgw_data.get("close_price")/1000000,
155
- volume=tgw_data.get("total_volume_trade")/100,
156
- amount=tgw_data.get("total_value_trade")/1000000,
149
+ pre_close_price=tgw_data.get("pre_close_price"),
150
+ last_price=tgw_data.get("last_price"),
151
+ open_price=tgw_data.get("open_price"),
152
+ high_price=tgw_data.get("high_price"),
153
+ low_price=tgw_data.get("low_price"),
154
+ close_price=tgw_data.get("close_price"),
155
+ volume=tgw_data.get("total_volume_trade"),
156
+ amount=tgw_data.get("total_value_trade"),
157
157
  count=tgw_data.get("num_trades"),
158
158
  **extra
159
159
  )
@@ -0,0 +1,192 @@
1
+ # -*- coding:utf-8 -*-
2
+ '''
3
+ @group:waditu
4
+ @author: DY
5
+ '''
6
+ import _thread as thread
7
+ import fnmatch
8
+ import json
9
+
10
+ import logging, sys
11
+ import re
12
+ import ssl
13
+ import threading
14
+ import time
15
+ from collections import defaultdict
16
+ from functools import wraps
17
+ from multiprocessing.context import Process
18
+
19
+ import websocket
20
+ from websocket import WebSocketConnectionClosedException
21
+
22
+ logging.basicConfig(stream=sys.stdout, level=logging.ERROR, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s')
23
+ import logging
24
+
25
+ logger = logging.getLogger(__name__)
26
+
27
+
28
+ class Subs(object):
29
+
30
+ def __init__(self, token='', callback_mode='multi-thread', debug=False):
31
+ self.url = 'wss://ws.tushare.pro/listening'
32
+ self.token = token
33
+ self.debug = debug
34
+
35
+ self.callback_mode = callback_mode
36
+ self.topics = defaultdict(lambda: list())
37
+ self.callback_funcs = defaultdict(lambda: list())
38
+
39
+ self.websocket = None
40
+
41
+ def threading_keepalive_ping(self):
42
+ def ping():
43
+ time.sleep(30)
44
+ req_data = {
45
+ "action": "ping"
46
+ }
47
+ self.websocket.send(json.dumps(req_data))
48
+ logger.debug('send ping message')
49
+ threading.Thread(target=ping).start()
50
+
51
+ def on_open(self, *args, **kwargs):
52
+ req_data = {
53
+ "action": "listening",
54
+ "token": self.token,
55
+ "data": self.topics
56
+ }
57
+ self.websocket.send(json.dumps(req_data))
58
+ logger.info('application starting...')
59
+ self.threading_keepalive_ping()
60
+
61
+ def on_message(self, message, *args, **kwargs):
62
+ logger.debug(message)
63
+ if isinstance(message, (str, bytes, bytearray)):
64
+ resp_data = json.loads(message)
65
+ if not resp_data.get('status'):
66
+ logger.error(resp_data.get('message'))
67
+ return
68
+ else:
69
+ logger.info(message)
70
+ return
71
+ data = resp_data.get('data', {})
72
+ if not data or not isinstance(data, dict):
73
+ return
74
+
75
+ topic = data.get('topic')
76
+ code = data.get('code')
77
+ record = data.get('record')
78
+ if not topic or not code or not record:
79
+ logger.warning('get invalid response-data(%s)' % resp_data)
80
+ return
81
+
82
+ self._do_callback_function(topic, code, record)
83
+
84
+ def on_error(self, error, *args, **kwargs):
85
+ if self.debug:
86
+ logging.error(str(error), exc_info=True)
87
+
88
+ def on_close(self, *args, **kwargs):
89
+ logger.error('close')
90
+ _type, _value, _traceback = sys.exc_info()
91
+ if _type in [WebSocketConnectionClosedException, ConnectionRefusedError]:
92
+ time.sleep(1)
93
+ self.run()
94
+
95
+ def run(self):
96
+ if not self.topics:
97
+ logger.error('no data.')
98
+ return
99
+
100
+ self.websocket = websocket.WebSocketApp(
101
+ self.url,
102
+ on_message=self.on_message,
103
+ on_error=self.on_error,
104
+ on_close=self.on_close,
105
+ on_open=self.on_open
106
+ )
107
+ if self.url.startswith('wss:'):
108
+ self.websocket.run_forever(sslopt={"cert_reqs": ssl.CERT_NONE})
109
+ else:
110
+ self.websocket.run_forever()
111
+
112
+ def register(self, topic, codes):
113
+ codes = set(codes)
114
+
115
+ def decorator(func):
116
+ func.codes = set()
117
+ func.pcodes = set()
118
+ for code in codes:
119
+ if not re.match(r'[\d\w\.\*]+', code):
120
+ logger.error('error code')
121
+ exit(1)
122
+
123
+ if '*' in code:
124
+ for code1 in func.pcodes:
125
+ if fnmatch.fnmatch(code1, code) or fnmatch.fnmatch(code, code1):
126
+ logger.error('duplicate code')
127
+ exit(1)
128
+ for code1 in func.codes:
129
+ if fnmatch.fnmatch(code1, code):
130
+ logger.error('duplicate code')
131
+ exit(1)
132
+ func.pcodes.add(code)
133
+ else:
134
+ for code1 in func.pcodes:
135
+ if fnmatch.fnmatch(code, code1):
136
+ logger.error('duplicate code')
137
+ exit(1)
138
+ func.codes.add(code)
139
+
140
+ self.topics[topic] += codes
141
+ self.callback_funcs[topic].append(func)
142
+
143
+ @wraps(func)
144
+ def inner(*args, **kwargs):
145
+ """ should receive a message-value parameter """
146
+ return func(*args, **kwargs)
147
+
148
+ return inner
149
+
150
+ return decorator
151
+
152
+ def _do_callback_function(self, topic, code, value):
153
+ for func in self.callback_funcs[topic]:
154
+ checked = False
155
+ if code in func.codes:
156
+ checked = True
157
+ else:
158
+ for pcode in func.pcodes:
159
+ if fnmatch.fnmatch(code, pcode):
160
+ checked = True
161
+ break
162
+
163
+ if not checked:
164
+ continue
165
+
166
+ if self.callback_mode == 'single-thread':
167
+ func(value)
168
+ elif self.callback_mode == 'multi-thread':
169
+ thread.start_new_thread(func, (value,))
170
+ elif self.callback_mode == 'multi-process':
171
+ p = Process(target=func, args=(value,))
172
+ p.start()
173
+
174
+
175
+ def test():
176
+ app = Subs(token='')
177
+
178
+ # code 可以包含 * (通配符)
179
+ @app.register(topic='HQ_STK_TICK', codes=["000001.SZ"])
180
+ def print_message(record):
181
+ """
182
+ 订阅主题topic,并指定codes列表,在接收到topic的推送消息时,符合code条件,就会执行回调
183
+ :param record:
184
+ :return:
185
+ """
186
+ print('用户定义业务代码输出 print_message(%s)' % str(record))
187
+
188
+ app.run()
189
+
190
+
191
+ if __name__ == '__main__':
192
+ test()