├── .gitignore
├── .idea
├── inspectionProfiles
│ └── Project_Default.xml
├── misc.xml
├── modules.xml
├── rqalpha-data.iml
└── vcs.xml
├── LICENSE
├── MANIFEST.in
├── README.md
├── requirements.txt
├── rqalpha_data
├── VERSION.txt
├── __init__.py
├── datasource.py
├── datetime_utils.py
├── demo.py
└── quant_utils.py
├── setup.cfg
└── setup.py
/.gitignore:
--------------------------------------------------------------------------------
1 | # Byte-compiled / optimized / DLL files
2 | __pycache__/
3 | *.py[cod]
4 | *$py.class
5 |
6 | # C extensions
7 | *.so
8 |
9 | # Distribution / packaging
10 | .Python
11 | env/
12 | build/
13 | develop-eggs/
14 | dist/
15 | downloads/
16 | eggs/
17 | .eggs/
18 | lib/
19 | lib64/
20 | parts/
21 | sdist/
22 | var/
23 | wheels/
24 | *.egg-info/
25 | .installed.cfg
26 | *.egg
27 |
28 | # PyInstaller
29 | # Usually these files are written by a python script from a template
30 | # before PyInstaller builds the exe, so as to inject date/other infos into it.
31 | *.manifest
32 | *.spec
33 |
34 | # Installer logs
35 | pip-log.txt
36 | pip-delete-this-directory.txt
37 |
38 | # Unit test / coverage reports
39 | htmlcov/
40 | .tox/
41 | .coverage
42 | .coverage.*
43 | .cache
44 | nosetests.xml
45 | coverage.xml
46 | *.cover
47 | .hypothesis/
48 |
49 | # Translations
50 | *.mo
51 | *.pot
52 |
53 | # Django stuff:
54 | *.log
55 | local_settings.py
56 |
57 | # Flask stuff:
58 | instance/
59 | .webassets-cache
60 |
61 | # Scrapy stuff:
62 | .scrapy
63 |
64 | # Sphinx documentation
65 | docs/_build/
66 |
67 | # PyBuilder
68 | target/
69 |
70 | # Jupyter Notebook
71 | .ipynb_checkpoints
72 |
73 | # pyenv
74 | .python-version
75 |
76 | # celery beat schedule file
77 | celerybeat-schedule
78 |
79 | # SageMath parsed files
80 | *.sage.py
81 |
82 | # dotenv
83 | .env
84 |
85 | # virtualenv
86 | .venv
87 | venv/
88 | ENV/
89 |
90 | # Spyder project settings
91 | .spyderproject
92 | .spyproject
93 |
94 | # Rope project settings
95 | .ropeproject
96 |
97 | # mkdocs documentation
98 | /site
99 |
100 | # mypy
101 | .mypy_cache/
102 |
--------------------------------------------------------------------------------
/.idea/inspectionProfiles/Project_Default.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
13 |
14 |
15 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/.idea/misc.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | ApexVCS
5 |
6 |
7 |
--------------------------------------------------------------------------------
/.idea/modules.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/.idea/rqalpha-data.iml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/.idea/vcs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 SixQuant
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/MANIFEST.in:
--------------------------------------------------------------------------------
1 | include requirements.txt
2 | include rqalpha_data/VERSION.txt
3 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # RQAlpha-Data
2 |
3 | [](https://pypi.python.org/pypi/rqalpha-data)
4 |
5 | ## Overview
6 | A utility for RQAlpha to directly use data.
7 |
8 | 不需要在回测里而是直接调用 RQAlpha 的数据。
9 |
10 |
11 |
12 | 对 history_bars 函数进行一定包装后变成 get_bars 函数,以便直接在 Jupyter 中直接使用!
13 |
14 | 匆忙写就,欢迎各位提问题以便改进它,当然更欢迎给我加个 Star。
15 |
16 | 最终效果:
17 |
18 | 
19 |
20 | ### 常用的函数:
21 |
22 | * is_trading_date 判断是否是交易日
23 |
24 | * get_trading_dates - 交易日列表
25 |
26 | * get_previous_trading_date - 上一交易日
27 |
28 | * get_next_trading_date - 下一交易日
29 |
30 | * is_suspended - 全天停牌判断
31 |
32 | * is_st_stock - ST股判断
33 |
34 | * get_prev_close
35 |
36 | * get_bar 和RQAlpha兼容
37 |
38 | * history 和RQAlpha兼容
39 |
40 | * history_bars 和RQAlpha兼容
41 |
42 | * get_bars 推荐使用
43 |
44 | (注意:如果中间有停牌日期,则自动跳过,保证最后数据行数为 bar_count = 5 个)
45 |
46 | | field | 字段名 |
47 | | -------------- | ---- |
48 | | open | 开盘价 |
49 | | high | 最高价 |
50 | | low | 最低价 |
51 | | close | 收盘价 |
52 | | volume | 成交量 |
53 | | total_turnover | 成交额 |
54 | | datetime | 时间 |
55 |
56 |
57 |
58 | ```
59 | get_bars(order_book_id,
60 | dt,
61 | bar_count=1,
62 | frequency='1d',
63 | fields=None,
64 | skip_suspended=True,
65 | include_now=False,
66 | adjust_type='pre',
67 | adjust_orig=None,
68 | convert_to_dataframe=False)
69 | ```
70 |
71 | ## Install
72 |
73 | #### Install rqalpha
74 | ```bash
75 | $ pip install rqalpha
76 | ```
77 |
78 | #### Install rqalpha-data
79 | ```bash
80 | $ pip install rqalpha-data
81 | ```
82 |
83 | ## Quick Start
84 |
85 | ### 数据更新
86 |
87 | 如果第一次使用或想要更新数据,请调用 update 方法
88 |
89 | ```python
90 | from rqalpha_data import datasource
91 | datasource.update()
92 | ```
93 |
94 | ### get_bars
95 |
96 | 1. 获取单支股票,返回格式为数组
97 |
98 | ```python
99 | from rqalpha_data import *
100 |
101 | df = get_bars('600469.XSHG', '2017-11-01', 5, fields=['datetime', 'open', 'close'])
102 | print(df)
103 | ```
104 |
105 | 输出(注意:如果中间有停牌日期,则自动跳过,保证最后数据行数为 bar_count = 5 个)
106 |
107 | ```python
108 | [(20171025000000L, 8.09, 8.16) (20171026000000L, 8.16, 8.18)
109 | (20171027000000L, 8.17, 8.11) (20171030000000L, 8.11, 7.98)
110 | (20171101000000L, 7.88, 7.44)]
111 | ```
112 |
113 |
114 |
115 | 2. 获取单支股票,返回格式为DataFrame
116 |
117 | ```python
118 | from rqalpha_data import *
119 |
120 | df = get_bars('600469.XSHG', '2017-11-01', 5, fields=['datetime', 'open', 'close'], convert_to_dataframe=True)
121 | print(df)
122 | ```
123 |
124 | 输出(注意:如果中间有停牌日期,则自动跳过,保证最后数据行数为 bar_count = 5 个)
125 |
126 | ```python
127 | open close
128 |
129 | 2017-10-25 8.09 8.16
130 | 2017-10-26 8.16 8.18
131 | 2017-10-27 8.17 8.11
132 | 2017-10-30 8.11 7.98
133 | 2017-11-01 7.88 7.44
134 | ```
135 |
136 |
137 |
138 | ### 如何在 Jupyter 中使用 rqalpha 进行回测
139 | 有的朋友可能不知道如何在 Jupyter 中使用 rqalpha 进行回测
140 |
141 | 1. 用 %reload_ext rqalpha 命令加载 %%rqalpha命令
142 |
143 | 2. 用 %%rqalpha 命令运行回测
144 |
145 | 
146 |
147 | ## License
148 |
149 | [MIT](https://tldrlegal.com/license/mit-license)
150 |
151 |
--------------------------------------------------------------------------------
/requirements.txt:
--------------------------------------------------------------------------------
1 | numpy
2 | pandas
3 | rqalpha
4 |
--------------------------------------------------------------------------------
/rqalpha_data/VERSION.txt:
--------------------------------------------------------------------------------
1 | 0.0.7
2 |
--------------------------------------------------------------------------------
/rqalpha_data/__init__.py:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python
2 | # -*- coding: utf-8 -*-
3 | #
4 |
5 | # =================================================
6 | # disable rqalpha better_exceptions: WARNING: better_exceptions will only inspect code from the command line
7 | import sys
8 | if hasattr(sys, 'ps1'):
9 | orig_sys_ps1 = sys.ps1
10 | del sys.ps1
11 | import better_exceptions
12 | sys.ps1 = orig_sys_ps1
13 | # =================================================
14 |
15 | from .datasource import *
16 | from .datetime_utils import *
17 | from .quant_utils import *
18 |
--------------------------------------------------------------------------------
/rqalpha_data/datasource.py:
--------------------------------------------------------------------------------
1 | # -*- coding: UTF-8 -*-
2 |
3 | import os
4 | import datetime
5 | import pandas as pd
6 | from rqalpha.data.data_proxy import DataProxy
7 | from rqalpha.utils.datetime_func import convert_int_to_datetime
8 |
9 | from rqalpha_data.datetime_utils import to_date_object
10 | from rqalpha_data.quant_utils import to_order_book_id
11 |
12 |
13 | class DataSource(DataProxy):
14 | """
15 | 直接使用RQAlpha的全部数据
16 | """
17 |
18 | def __init__(self, data_bundle_path=None):
19 | default_bundle_path = os.path.abspath(os.path.expanduser('~/.rqalpha'))
20 | if data_bundle_path is None:
21 | data_bundle_path = default_bundle_path
22 | else:
23 | data_bundle_path = os.path.abspath(os.path.join(data_bundle_path, '.'))
24 |
25 | data_bundle_path = data_bundle_path + '/bundle'
26 |
27 | self._data_bundle_path = data_bundle_path
28 |
29 | # basic_system_log.debug('rqalpha data bundle path: ' + data_bundle_path)
30 | if not os.path.exists(data_bundle_path):
31 | self.update(skip_last_date_check=True)
32 |
33 | from rqalpha.data.base_data_source import BaseDataSource
34 | data_source = BaseDataSource(data_bundle_path)
35 | super(DataSource, self).__init__(data_source)
36 |
37 | self._last_date_date = None
38 | self.get_data_last_date()
39 | # basic_system_log.debug('rqalpha data bundle date: ' + self._last_date_date.strftime('%Y-%m-%d'))
40 |
41 | def get_data_last_date(self):
42 | """返回最新数据日期"""
43 | if self._last_date_date is not None:
44 | return self._last_date_date
45 |
46 | d = self._data_source
47 |
48 | instrument = self.instruments('000001.XSHG')
49 | raw = d._all_day_bars_of(instrument)
50 | df = pd.DataFrame.from_dict(raw)
51 | df['datetime'] = df['datetime'].map(lambda x: pd.to_datetime(str(x)[:8]))
52 |
53 | self._last_date_date = df['datetime'].max().date()
54 |
55 | del df, raw, instrument, d
56 |
57 | return self._last_date_date
58 |
59 | def get_last_trading_day(self):
60 | """返回最后交易日期"""
61 | date = datetime.date.today()
62 | while not self.is_trading_date(date):
63 | date = date + datetime.timedelta(days=-1)
64 | return date
65 |
66 | def update(self, skip_last_date_check=False):
67 | """
68 | 更新最新的远程数据到本地
69 | """
70 | if not skip_last_date_check:
71 | last_trading_day = self.get_last_trading_day()
72 |
73 | data_bundle_path = self._data_bundle_path
74 | if os.path.exists(data_bundle_path):
75 | date = self.get_data_last_date()
76 | if date == last_trading_day:
77 | return date # 数据已经是最新无需下载
78 | # basic_system_log.debug('need update data bundle to ' + date.strftime('%Y-%m-%d'))
79 |
80 | data_bundle_path = self._data_bundle_path
81 | data_bundle_path = data_bundle_path[:len(data_bundle_path) - len('/bundle')]
82 | from rqalpha import main
83 | main.update_bundle(data_bundle_path=data_bundle_path)
84 |
85 | if not skip_last_date_check:
86 | date = self.get_data_last_date()
87 | return date
88 |
89 | def get_bar(self, order_book_id, dt, frequency='1d'):
90 | order_book_id = to_order_book_id(order_book_id)
91 | dt = to_date_object(dt)
92 | return super(DataSource, self).get_bar(order_book_id=order_book_id, dt=dt, frequency=frequency)
93 |
94 | def history_bars(self,
95 | order_book_id,
96 | bar_count,
97 | frequency,
98 | field,
99 | dt,
100 | skip_suspended=True, include_now=False,
101 | adjust_type='pre', adjust_orig=None):
102 | order_book_id = to_order_book_id(order_book_id)
103 | dt = to_date_object(dt)
104 | bars = super(DataSource, self).history_bars(order_book_id=order_book_id,
105 | bar_count=bar_count,
106 | frequency=frequency,
107 | field=field,
108 | dt=dt,
109 | skip_suspended=skip_suspended,
110 | include_now=include_now,
111 | adjust_type=adjust_type,
112 | adjust_orig=adjust_orig)
113 | return bars
114 |
115 | def get_bars(self,
116 | order_book_id,
117 | dt,
118 | bar_count=1,
119 | frequency='1d',
120 | fields=None,
121 | skip_suspended=True,
122 | include_now=False,
123 | adjust_type='pre',
124 | adjust_orig=None,
125 | convert_to_dataframe=False):
126 | order_book_id = to_order_book_id(order_book_id)
127 | dt = to_date_object(dt)
128 |
129 | if fields is None:
130 | fields = ['datetime', 'open', 'high', 'low', 'close', 'volume', 'total_turnover']
131 |
132 | bars = super(DataSource, self).history_bars(order_book_id=order_book_id,
133 | bar_count=bar_count,
134 | frequency=frequency,
135 | field=fields,
136 | dt=dt,
137 | skip_suspended=skip_suspended,
138 | include_now=include_now,
139 | adjust_type=adjust_type,
140 | adjust_orig=adjust_orig)
141 | if convert_to_dataframe:
142 | df = pd.DataFrame.from_dict(bars)
143 | if 'datetime' in df.columns:
144 | df['datetime'] = df['datetime'].map(lambda x: convert_int_to_datetime(x))
145 | df.set_index('datetime', inplace=True)
146 | df.index.name = ''
147 | return df
148 |
149 | return bars
150 |
151 |
152 | datasource = DataSource()
153 |
154 |
155 | def is_trading_date(date):
156 | datasource.is_trading_date(date)
157 |
158 |
159 | def get_bar(order_book_id, dt, frequency='1d'):
160 | return datasource.get_bar(order_book_id=order_book_id, dt=dt, frequency=frequency)
161 |
162 |
163 | def history_bars(
164 | order_book_id,
165 | bar_count,
166 | frequency,
167 | field,
168 | dt,
169 | skip_suspended=True,
170 | include_now=False,
171 | adjust_type='pre',
172 | adjust_orig=None):
173 | return datasource.history_bars(order_book_id=order_book_id,
174 | bar_count=bar_count,
175 | frequency=frequency,
176 | field=field,
177 | dt=dt,
178 | skip_suspended=skip_suspended,
179 | include_now=include_now,
180 | adjust_type=adjust_type,
181 | adjust_orig=adjust_orig)
182 |
183 |
184 | def get_bars(order_book_id,
185 | dt,
186 | bar_count=1,
187 | frequency='1d',
188 | fields=None,
189 | skip_suspended=True,
190 | include_now=False,
191 | adjust_type='pre',
192 | adjust_orig=None,
193 | convert_to_dataframe=False):
194 | return datasource.get_bars(order_book_id=order_book_id,
195 | bar_count=bar_count,
196 | dt=dt,
197 | frequency=frequency,
198 | fields=fields,
199 | skip_suspended=skip_suspended,
200 | include_now=include_now,
201 | adjust_type=adjust_type,
202 | adjust_orig=adjust_orig,
203 | convert_to_dataframe=convert_to_dataframe)
204 |
--------------------------------------------------------------------------------
/rqalpha_data/datetime_utils.py:
--------------------------------------------------------------------------------
1 | # -*- coding: UTF-8 -*-
2 |
3 | import datetime
4 | import numpy as np
5 |
6 |
7 | def to_date_object(date):
8 | """
9 | 转换字符串或日期时间对象为日期对象(直接忽略时分秒部分)
10 | :param date:
11 | :return:
12 | """
13 | if date is None:
14 | return None
15 |
16 | if isinstance(date, datetime.datetime):
17 | return date.date()
18 |
19 | if isinstance(date, datetime.date):
20 | return date
21 |
22 | date = to_time_object(date)
23 | date = date.date()
24 |
25 | return date
26 |
27 |
28 | def to_time_object(dt):
29 | """
30 | 转换字符串或日期时间对象为时间对象
31 | :param dt:
32 | :return:
33 | """
34 | if dt is None:
35 | return None
36 |
37 | adjust_time_zone = False
38 |
39 | if isinstance(dt, str):
40 | n = len(dt)
41 | if 8 == n:
42 | fmt = '%Y%m%d'
43 | elif 10 == n:
44 | pos = dt.find('/')
45 | if -1 == pos:
46 | fmt = '%Y-%m-%d' if 4 == dt.find('-') else '%m-%d-%Y'
47 | elif 4 == pos:
48 | fmt = '%Y/%m/%d'
49 | else:
50 | fmt = '%m/%d/%Y'
51 | elif n > 4 and dt[n - 4:] == ' GMT':
52 | fmt = '%a, %d %b %Y %H:%M:%S GMT'
53 | adjust_time_zone = True # 需要调整时区,一般 HTTP 请求头里用 GMT 时间表示
54 | else:
55 | fmt = '%Y-%m-%d %H:%M:%S'
56 | dt = datetime.datetime.strptime(dt, fmt)
57 |
58 | # 需要调整时区
59 | if adjust_time_zone:
60 | dt = dt + datetime.timedelta(seconds=-datetime.time.timezone)
61 | elif isinstance(dt, np.datetime64):
62 | dt = datetime.datetime.fromtimestamp(dt.astype('O') / 1e9)
63 | elif isinstance(dt, datetime.datetime):
64 | pass
65 | elif isinstance(dt, datetime.date):
66 | dt = datetime.datetime(dt.year, dt.month, dt.day)
67 | else:
68 | raise TypeError('date type error! ' + str(type(dt)))
69 |
70 | return dt
71 |
72 |
73 | def to_date_str_fmt(date, fmt):
74 | """
75 | 转换为日期字符串
76 | :param date:
77 | :param fmt:
78 | :return:
79 | """
80 | if date is None:
81 | return ""
82 |
83 | date = to_date_object(date)
84 | return date.strftime(fmt)
85 |
86 |
87 | def to_date_str(date):
88 | """转换为日期字符串 %Y-%m-%d
89 | :param date:
90 | :return:
91 | """
92 | return to_date_str_fmt(date, '%Y-%m-%d')
93 |
94 |
95 | def to_date_str_short(date):
96 | """转换为日期字符串 %Y%m%d
97 | :param date:
98 | :return:
99 | """
100 | return to_date_str_fmt(date, '%Y%m%d')
101 |
102 |
103 | def to_datetime_str_fmt(dt, fmt):
104 | """
105 | 转换为日期时间字符串
106 | :param dt:
107 | :param fmt:
108 | :return:
109 | """
110 | if dt is None:
111 | return ""
112 |
113 | dt = to_time_object(dt)
114 | return dt.strftime(fmt)
115 |
116 |
117 | def to_datetime_str(dt):
118 | """转换为日期字符串 %Y-%m-%d %H:%M:%S
119 | :param dt:
120 | :return:
121 | """
122 | return to_datetime_str_fmt(dt, '%Y-%m-%d %H:%M:%S')
123 |
--------------------------------------------------------------------------------
/rqalpha_data/demo.py:
--------------------------------------------------------------------------------
1 | # -*- coding: UTF-8 -*-
2 |
3 | if __name__ == '__main__':
4 | from rqalpha_data import *
5 |
6 | # df = get_bar('000001.XSHG', '2017-11-24')
7 | df = get_bars('600469.XSHG', '2017-11-01', 5, fields=['datetime', 'open', 'close'])
8 | df = get_bars('600469.XSHG', '2017-11-01', 5, convert_to_dataframe=True)
9 | # df = get_bars('600469.XSHG', '2017-11-01', 5, fields=['open', 'close'], convert_to_dataframe=True)
10 | print(df)
11 |
12 | # df = get_bars('000001.XSHG', 2, '2017-11-24')
13 | # print(df)
14 |
15 |
16 |
--------------------------------------------------------------------------------
/rqalpha_data/quant_utils.py:
--------------------------------------------------------------------------------
1 | # -*- coding: UTF-8 -*-
2 |
3 |
4 | def to_order_book_id(stocks):
5 | """增加股票代码后缀, 对应 to_pure_code()
6 | 兼容米宽的代码
7 | order_book_id 证券代码
8 | 证券的独特的标识符。应以'.XSHG'或'.XSHE'结尾,前者代表上证,后者代表深证
9 | """
10 | if not isinstance(stocks, str):
11 | rs = []
12 | for stock in stocks:
13 | rs.append(to_order_book_id(stock))
14 | return rs
15 |
16 | stock = stocks
17 | if len(stock) == 11:
18 | return stock
19 |
20 | c = stock[:1]
21 | if c == '0' or c == '3':
22 | return stock + '.XSHE'
23 | elif c == '6':
24 | return stock + '.XSHG'
25 | else:
26 | raise NameError(stock)
27 |
28 |
29 | def to_pure_code(order_book_id):
30 | """返回去除后缀后的股票代码, 对应 to_order_book_id()
31 | 兼容米宽的代码
32 | order_book_id 证券代码
33 | 证券的独特的标识符。应以'.XSHG'或'.XSHE'结尾,前者代表上证,后者代表深证
34 | """
35 | if not isinstance(order_book_id, str):
36 | rs = []
37 | for stock in order_book_id:
38 | rs.append(to_pure_code(stock))
39 | return rs
40 |
41 | stock = order_book_id
42 | if len(stock) == 6:
43 | return stock
44 |
45 | return stock[:6]
46 |
--------------------------------------------------------------------------------
/setup.cfg:
--------------------------------------------------------------------------------
1 | [egg_info]
2 | tag_build =
3 | tag_date = 0
4 |
5 |
--------------------------------------------------------------------------------
/setup.py:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python
2 | # -*- coding: utf-8 -*-
3 | #
4 |
5 | import sys
6 | from os.path import dirname, join
7 | from pip.req import parse_requirements
8 |
9 | from setuptools import (
10 | find_packages,
11 | setup,
12 | )
13 |
14 | with open(join(dirname(__file__), 'rqalpha_data/VERSION.txt'), 'rb') as f:
15 | version = f.read().decode('ascii').strip()
16 |
17 | requirements = [str(ir.req) for ir in parse_requirements(join(dirname(__file__), "requirements.txt"), session=False)]
18 |
19 | setup(
20 | name='rqalpha-data',
21 | version=version,
22 | description='A utility for RQAlpha to directly use data',
23 | packages=find_packages(exclude=[]),
24 | author='sixquant',
25 | author_email='public@sixquant.com',
26 | license='MIT',
27 | url='https://github.com/sixquant/rqalpha-data',
28 | keywords='RiceQuant RQAlpha finance data',
29 | install_requires=requirements,
30 | classifiers=['Development Status :: 3 - Alpha',
31 | 'Programming Language :: Python',
32 | 'Operating System :: Microsoft :: Windows',
33 | 'Operating System :: Unix',
34 | 'Programming Language :: Python :: 2.7',
35 | 'Programming Language :: Python :: 3.4',
36 | 'Programming Language :: Python :: 3.5',
37 | 'Programming Language :: Python :: 3.6',
38 | 'License :: OSI Approved :: MIT License',
39 | ],
40 | )
41 |
--------------------------------------------------------------------------------