def get_style_factor_exposure(order_book_ids, start_date, end_date, factors=None, market="cn"): """获取个股风格因子暴露度 :param order_book_ids: 证券代码(例如:‘600705.XSHG’) :param start_date: 开始日期(例如:‘2017-03-03’) :param end_date: 结束日期(例如:‘2017-03-20’) :param factors: 风格因子。默认调用全部因子的暴露度('all')。 具体因子名称见说明文档 (Default value = None) :param market: (Default value = "cn") """ order_book_ids = ensure_order_book_ids(order_book_ids) start_date, end_date = ensure_date_range(start_date, end_date) if factors is not None: factors = ensure_list_of_string(factors) check_items_in_container(factors, _STYLE_FACTORS, "factors") df = get_client().execute("get_style_factor_exposure", order_book_ids, start_date, end_date, factors, market=market) if not df: return return pd.DataFrame(df).set_index(["order_book_id", "date"]).sort_index(level=1)
def performance_forecast(order_book_id, info_date=None, end_date=None, fields=None, market="cn"): """获取业绩预报 :param order_book_id: 股票代码,如'000001.XSHE' :param info_date: 信息发布日期,如'20180501',默认为最近的交易日 (Default value = None) :param end_date: 业绩预计报告期,如'20180501',默认为最近的交易日 (Default value = None) :param fields: str或list类型. 默认为None,返回所有字段 (Default value = None) :param market: (Default value = "cn") :returns: pd.DataFrame """ order_book_id = ensure_order_book_id(order_book_id) if info_date: info_date = ensure_date_int(info_date) elif end_date: end_date = ensure_date_int(end_date) else: info_date = ensure_date_int(datetime.datetime.today()) if fields: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, PERFORMANCE_FORECAST_FIELDS, "fields") else: fields = PERFORMANCE_FORECAST_FIELDS data = get_client().execute( "performance_forecast", order_book_id, info_date, end_date, fields, market=market ) if not data: return df = pd.DataFrame(data)[["info_date", "end_date"] + fields] return df
def _ensure_fields(fields, fields_dict, stocks, funds, futures, spots, options, convertibles, indexes, repos): has_dominant_id = True all_fields = set(fields_dict["common"]) if futures: all_fields.update(fields_dict["future"]) if stocks: all_fields.update(fields_dict["stock"]) if funds: all_fields.update(fields_dict["fund"]) if spots: all_fields.update(fields_dict["spot"]) if options: all_fields.update(fields_dict["option"]) if convertibles: all_fields.update(fields_dict["convertible"]) if indexes: all_fields.update(fields_dict["index"]) if repos: all_fields.update(fields_dict["repo"]) if fields: fields = ensure_list_of_string(fields, "fields") fields_set = set(fields) if len(fields_set) < len(fields): warnings.warn("duplicated fields: %s" % [f for f in fields if fields.count(f) > 1]) fields = list(fields_set) if 'dominant_id' in fields: if len(fields) == 1: raise ValueError("can't get dominant_id separately, please use futures.get_dominant") fields.remove('dominant_id') else: has_dominant_id = False check_items_in_container(fields, all_fields, "fields") return fields, has_dominant_id else: return list(all_fields), has_dominant_id
def get_instrument_industry(order_book_ids, source='sws', level=1, date=None, market="cn"): """获取股票对应的行业 :param order_book_ids: 股票列表,如['000001.XSHE', '000002.XSHE'] :param source: 分类来源。sws: 申万, citics: 中信, gildata: 聚源 :param date: 如 '2015-01-07' (Default value = None) :param level: (Default value = 1) :param market: (Default value = "cn") :returns: code, name 返回输入日期最近交易日的股票对应行业 """ order_book_ids = ensure_order_book_ids(order_book_ids) source = ensure_string_in(source, ["sws", "citics", "gildata"], "source") check_items_in_container(level, [0, 1, 2, 3], 'level') date = ensure_date_or_today_int(date) r = get_client().execute("get_instrument_industry", order_book_ids, source, level, date, market=market) if not r: return return pd.DataFrame(r).set_index("order_book_id")
def get_manager_info(manager_id, fields=None, market="cn"): """获取基金经理个人信息 :param manager: 可以使用人员编码(如'101000002')或姓名(如'江辉'),str 或 list of str :param fields: str or list of str,例如:"gender", "region", (Default value = None) :param market: (Default value = "cn") :returns: DataFrame """ manager_id = ensure_list_of_string(manager_id) # 检查manager中是否同时有人员编码或姓名 if len(set(map(lambda x: x.isdigit(), manager_id))) > 1: raise ValueError("couldn't get manager_id and name at the same time") manager_fields = ["gender", "region", "birthdate", "education", "practice_date", "experience_time", "background"] if fields is not None: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, manager_fields, "fields") else: fields = manager_fields result = get_client().execute("fund.get_manager_info", manager_id, fields, market=market) if not result: warnings.warn("manager_id/manager_name does not exist") return df = pd.DataFrame(result).set_index("id") fields.insert(0, "chinesename") df.sort_index(inplace=True) return df[fields]
def top_stocks(field, date, frequency="1d", count=5, market="cn"): """获取雪球舆情数据 :param field: 如 'new_comments', 'total_comments', 'new_followers', 'total_followers', 'sell_actions', 'buy_actions' :param date: 如 '2015-05-21', 必须在2015年4月23日之后 :param frequency: 如 '1d', '1w', '1M' (Default value = "1d") :param count: 如 5, 10, 100 (Default value = 5) :param market: 地区代码, 如 'cn' (Default value = "cn") :returns: 如果有数据,返回一个DataFrame,否则返回None """ field = ensure_string(field, "field") frequency = ensure_string(frequency, "frequency") check_items_in_container([field], FIELDS, "field") check_items_in_container([frequency], {"1d", "1w", "1M"}, "frequency") d = {"1d": "d", "1M": "m", "1w": "w"} frequency = d[frequency] date = ensure_date_int(date) if date < 20150423 or date > ensure_date_int(datetime.datetime.today()): raise ValueError("date out of range, start_date " "cannot be earlier than 2015-04-23") data = get_client().execute("xueqiu.top_stocks", field, date, frequency, count, market) if not data: return df = pd.DataFrame(data) df = df[["order_book_id", field]] return df
def get_commission_margin(order_book_ids=None, fields=None, hedge_flag="speculation"): """获取期货保证金和手续费数据 :param order_book_ids: 期货合约, 支持 order_book_id 或 order_book_id list, 若不指定则默认获取所有合约 (Default value = None) :param fields: str 或 list, 可选字段有: 'margin_type', 'long_margin_ratio', 'short_margin_ratio', 'commission_type', 'open_commission_ratio', 'close_commission_ratio', 'close_commission_today_ratio', 若不指定则默认获取所有字段 (Default value = None) :param hedge_flag: str, 账户对冲类型, 可选字段为: 'speculation', 'hedge', 'arbitrage', 默认为'speculation', 目前仅支持'speculation' (Default value = "speculation") :returns: pandas.DataFrame """ if order_book_ids: order_book_ids = ensure_list_of_string(order_book_ids) if fields is None: fields = _FIELDS else: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, _FIELDS, "fields") hedge_flag = ensure_string(hedge_flag, "hedge_flag") if hedge_flag not in ["speculation", "hedge", "arbitrage"]: raise ValueError("invalid hedge_flag: {}".format(hedge_flag)) ret = get_client().execute("futures.get_commission_margin", order_book_ids, fields, hedge_flag) return pd.DataFrame(ret)
def get_reserve_ratio(reserve_type="all", start_date=None, end_date=None, market="cn"): """获取存款准备金率 :param reserve_type: 存款准备金详细类别,默认为'all',目前仅支持'all'、'major'、'other'类别的查询 :param start_date: 开始查找时间,如'20180501',默认为上一年的当天 :param end_date: 截止查找时间,如'20180501',默认为当天 :param market: (Default value = "cn") :return: pd.DataFrame """ check_items_in_container(reserve_type, ["all", "major", "other"], "reserve_type") start_date, end_date = ensure_date_range(start_date, end_date, delta=relativedelta(years=1)) ret = get_client().execute("econ.get_reserve_ratio", reserve_type, start_date, end_date, market) if not ret: return columns = [ "info_date", "effective_date", "reserve_type", "ratio_floor", "ratio_ceiling" ] df = pd.DataFrame( ret, columns=columns).set_index("info_date").sort_index(ascending=True) return df
def get_money_supply(start_date=None, end_date=None, market="cn"): """获取货币供应量信息 :param start_date: 开始日期,默认为一年前 :param end_date: 结束日期,默认为今天 :param market: (Default value = "cn") """ check_items_in_container("info_date", ["info_date", "effective_date"], "date_type") start_date, end_date = ensure_date_range(start_date, end_date, delta=relativedelta(years=1)) data = get_client().execute("econ.get_money_supply", start_date, end_date, market=market) if not data: return columns = [ "info_date", "effective_date", "m2", "m1", "m0", "m2_growth_yoy", "m1_growth_yoy", "m0_growth_yoy", ] df = pd.DataFrame( data, columns=columns).set_index("info_date").sort_index(ascending=True) return df
def current_stock_connect_quota( connect=None, fields=None ): """ 获取沪港通、深港通资金流向数据 :param connect: 字符串,目前可从sh_to_hk, hk_to_sh, sz_to_hk, hk_to_sz多选, 默认为查询所有资金流向数据 :param fields: 字符串列表,需要的字段,目前可从buy_turnover, sell_turnover, quota_balance, quota_balance_ratio多选, 默认取所有 """ DEFAULT_CONNECT = ["sh_to_hk", "hk_to_sh", "sz_to_hk", "hk_to_sz"] if connect is None: connect = DEFAULT_CONNECT else: connect = ensure_list_of_string(connect) check_items_in_container(connect, DEFAULT_CONNECT, 'connect') DEFAULT_FIELDS = ['buy_turnover', 'sell_turnover', 'quota_balance', 'quota_balance_ratio'] if fields is None: fields = DEFAULT_FIELDS else: fields = ensure_list_of_string(fields) check_items_in_container(fields, DEFAULT_FIELDS, 'fields') data = get_client().execute("current_stock_connect_quota", connect=connect) res = pd.DataFrame(data) if res.empty: return None res["datetime"] = pd.to_datetime(res["datetime"], format='%Y%m%d%H%M') res.set_index(['datetime', 'connect'], inplace=True) res = res[fields] return res
def get_descriptor_exposure(order_book_ids, start_date, end_date, descriptors=None, market="cn"): """获取个股细分因子暴露度 :param order_book_ids: 证券代码(例如:‘600705.XSHG’) :param start_date: 开始日期(例如:‘2017-03-03’) :param end_date: 结束日期(例如:‘2017-03-20’) :param descriptors: 细分风格因子。默认调用全部因子的暴露度('all')。 具体细分因子名称见说明文档 (Default value = None) :param market: (Default value = "cn") :returns: MultiIndex DataFrame. index 第一个 level 为 order_book_id,第 二个 level 为 date,column 为细分风格因子字段名称。 """ order_book_ids = ensure_order_book_ids(order_book_ids) start_date, end_date = ensure_date_range(start_date, end_date) if descriptors is not None: if descriptors == "all": descriptors = None else: descriptors = ensure_list_of_string(descriptors) check_items_in_container(descriptors, _DESCRIPTORS, "descriptors") df = get_client().execute("get_descriptor_exposure", order_book_ids, start_date, end_date, descriptors, market=market) if not df: return return pd.DataFrame(df).set_index(["order_book_id", "date"]).sort_index(level=1)
def data(order_book_id, start_date=None, end_date=None, frequency="1d", fields=None): """获取天猫电商销售额数据 :param order_book_id: 股票名 :param start_date: 开始日期,默认为结束日期前一个月, 必须在2016年6月30日之后 (Default value = None) :param end_date: 结束日期 (Default value = None) :param frequency: 如'1d', '1M' (Default value = "1d") :param fields: 如'sales' (Default value = None) :returns: 返回DataFrame """ order_book_id = ensure_order_book_id(order_book_id) if not end_date: end_date = datetime.date.today() if not start_date: start_date = end_date - datetime.timedelta(days=30) end_date = to_datetime(end_date) start_date = to_datetime(start_date) if start_date < datetime.datetime(2016, 6, 30): raise ValueError("start_date cannot be earlier than 2016-06-30") if start_date > end_date: raise ValueError() ensure_string(frequency, "frequency") check_items_in_container([frequency], {"1d", "1M"}, "frequency") if fields is None: fields = "sales" else: fields = ensure_string(fields, "fields") check_items_in_container(fields, ["sales"], "fields") data = get_client().execute("tmall.data", order_book_id, start_date, end_date, frequency) if not data: return df = pd.DataFrame(data) df = df.set_index("date") df.sort_index(inplace=True) df.columns = ["sales"] return df
def get_yield_curve(start_date=None, end_date=None, tenor=None, market="cn"): """获取国债收益率曲线 :param market: 地区代码, 如'cn', 'us' (Default value = "cn") :param start_date: 开始日期 (Default value = "2013-01-04") :param end_date: 结束日期 (Default value = "2014-01-04") :param tenor: 类别, 如 OS, 1M, 3M, 1Y (Default value = None) """ start_date, end_date = ensure_date_range(start_date, end_date) all_tenor = ( "0S", "1M", "2M", "3M", "6M", "9M", "1Y", "2Y", "3Y", "4Y", "5Y", "6Y", "7Y", "8Y", "9Y", "10Y", "15Y", "20Y", "30Y", "40Y", "50Y", ) if tenor: tenor = ensure_list_of_string(tenor, "tenor") check_items_in_container(tenor, all_tenor, "tenor") tenor = ensure_order(tenor, all_tenor) df = get_client().execute("get_yield_curve", start_date, end_date, tenor, market=market) if not df: return columns = ["trading_date"] columns.extend(tenor or all_tenor) df = pd.DataFrame(df, columns=columns) df.set_index("trading_date", inplace=True) return df.sort_index()
def get_current_news(n=None, start_time=None, end_time=None, channels=None): """获取新闻 :param n: 新闻条数, n 和 start_time/end_time 只能指定其一 :param start_time: 开始日期,默认为None,格式为%Y-%m-%d %H:%M:%S,如"2018-10-20 09:10:20" :param end_time: 结束日期,默认为None,格式为%Y-%m-%d %H:%M:%S,如"2018-10-20 19:10:20" :param channels: 新闻大类, 默认为None,返回每个大类n条新闻, 如 "global","forex", "commodity", "a-stock" """ if start_time is not None or end_time is not None: try: start_time = datetime.datetime.strptime(start_time, "%Y-%m-%d %H:%M:%S") except Exception: raise ValueError( 'start_time should be str format like "%Y-%m-%d %H:%M:%S"') try: end_time = datetime.datetime.strptime(end_time, "%Y-%m-%d %H:%M:%S") except Exception: raise ValueError( 'end_time should be str format like "%Y-%m-%d %H:%M:%S"') start_time = datetime_to_int14(start_time) end_time = datetime_to_int14(end_time) if n is not None: raise ValueError( "please either specify parameter n, or specify both start_time and end_time" ) n = 1200 elif n is None: n = 1 else: n = ensure_int(n, "n") if n < 1 or n > 1200: raise ValueError("n should be in [0, 1200]") if channels is not None: channels = ensure_list_of_string(channels) check_items_in_container(channels, ["global", "forex", "a-stock", "commodity"], "channels") else: channels = ["global", "forex", "a-stock", "commodity"] data = get_client().execute("get_current_news", n, start_time, end_time, channels) if not data: return df = pd.DataFrame(data, columns=["channel", "datetime", "content"]) return df.set_index("channel")
def get_greeks(order_book_ids, start_date=None, end_date=None, fields=None, model='implied_forward', market="cn"): """获取指定股票期权的隐含波动率iv, 以及5个希腊字母数值(delta, gamma, bega, theta, rho) :param order_book_ids: 股票 order_book_id or order_book_id list :param start_date: 开始日期, 必要参数 :param end_date: 结束日期;默认为今天 :param fields: str或list类型. 默认为None, 返回所有fields. :param model: str类型, last: 代表用每日close价格, implied_forward 代表用隐含风险收益率计算 :param market: 默认值为"cn" """ order_book_ids = ensure_order_book_ids(order_book_ids, market=market) check_items_in_container(model, ['implied_forward', 'last'], 'model') if start_date is not None: start_date = ensure_date_int(start_date) else: raise ValueError('start_date is expected') if end_date is not None: end_date = ensure_date_int(end_date) else: end_date = ensure_date_int(datetime.datetime.now().date()) if end_date < start_date: raise ValueError("invalid date range: [{!r}, {!r}]".format( start_date, end_date)) if fields is None: fields = VALID_GREEKS_FIELDS else: check_items_in_container(fields, VALID_GREEKS_FIELDS, 'Greeks') data = get_client().execute("options.get_greeks", order_book_ids, start_date, end_date, fields, model, market=market) if not data: return None df = pd.DataFrame(data) df.set_index(["order_book_id", "trading_date"], inplace=True) df.sort_index(inplace=True) return df[fields]
def get_instrument_industry(order_book_ids, source='citics', level=1, date=None, market="cn"): """获取股票对应的行业 :param order_book_ids: 股票列表,如['000001.XSHE', '000002.XSHE'] :param source: 分类来源。citics 以及 citics_2019: 中信, gildata: 聚源 :param date: 如 '2015-01-07' (Default value = None) :param level: (Default value = 1) :param market: (Default value = "cn") :returns: code, name 返回输入日期最近交易日的股票对应行业 """ order_book_ids = ensure_order_book_ids(order_book_ids) source = ensure_string_in(source, ["sws", "citics", "gildata", "citics_2019"], "source") if source == "citics_2019": check_items_in_container(level, [0, 1, 2, 3, "citics_sector"], 'level') else: check_items_in_container(level, [0, 1, 2, 3], 'level') date = ensure_date_or_today_int(date) r = get_client().execute("get_instrument_industry", order_book_ids, source, level, date, market=market) if not r: return res = [i['order_book_id'] for i in r] if source == "citics_2019" and level == "citics_sector": # is_special industry是否传入的是风格版块,产业板块和上下游产业版块 from rqdatac.services import basic res_list = basic.instruments(res) date = to_date_str(date) for index, order_book in enumerate(res_list): if order_book.de_listed_date == "0000-00-00" or order_book.de_listed_date is None: order_book.de_listed_date = "2099-12-31" if not order_book.listed_date <= date <= order_book.de_listed_date: r.pop(index) return pd.DataFrame(r).set_index("order_book_id")
def get_dominant(underlying_symbol, start_date=None, end_date=None, rule=0, market="cn"): """获取指定期货品种当日对应的主力合约 :param underlying_symbol: 如'IF' 'IC' :param start_date: 如 '2015-01-07' (Default value = None) :param end_date: 如 '2015-01-08' (Default value = None) :param market: (Default value = "cn") :param rule: 主力合约规则 (Default value = 0) 0:在rule=1的规则上,增加约束(曾做过主力合约的合约,一旦被换下来后,不会再被选上) 1:合约首次上市时,以当日收盘同品种持仓量最大者作为从第二个交易日开始的主力合约,当同品种其他合约持仓量在收盘后 超过当前主力合约1.1倍时,从第二个交易日开始进行主力合约的切换。日内不会进行主力合约的切换 :returns: pandas.Series 返回参数指定的具体主力合约名称 """ if not isinstance(underlying_symbol, six.string_types): raise ValueError( "invalid underlying_symbol: {}".format(underlying_symbol)) check_items_in_container(rule, [0, 1], 'rule') underlying_symbol = underlying_symbol.upper() if start_date: start_date = ensure_date_int(start_date) if end_date: end_date = ensure_date_int(end_date) elif start_date: end_date = start_date result = get_client().execute("futures.get_dominant", underlying_symbol, start_date, end_date, rule, market=market) if not result: return df = pd.DataFrame(result) df["date"] = df["date"].apply(int8_to_datetime) return df.set_index("date").sort_index()["dominant"]
def history( order_book_ids, start_date="2015-05-21", end_date="2016-05-21", frequency="1d", fields=None, market="cn", ): """获取雪球历史舆情数据 :param order_book_ids: 股票代码或代码列表 :param start_date: 如 '2015-05-21', 必须在2015年4月23日之后 (Default value = "2015-05-21") :param end_date: 如 '2016-05-21' (Default value = "2016-05-21") :param frequency: 如 '1d' (Default value = "1d") :param fields: 如 'new_comments', 'total_comments', 'new_followers', 'total_followers', 'sell_actions', 'buy_actions' (Default value = None) :param market: 地区代码, 如 'cn' (Default value = "cn") :returns: 返回pd.Panel或pd.DataFrame或pd.Series """ order_book_ids = ensure_order_book_ids(order_book_ids, market=market) if fields: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, FIELDS, "fields") else: fields = FIELDS frequency = ensure_string(frequency, "frequency") check_items_in_container([frequency], {"1d"}, "frequency") start_date, end_date = ensure_date_range(start_date, end_date) if start_date < 20150423: raise ValueError("date out of range, start_date " "cannot be earlier than 2015-04-23") data = get_client().execute("xueqiu.history", order_book_ids, start_date, end_date, fields, market) if not data: return df = pd.DataFrame(data) df = df.set_index(["date", "order_book_id"]) df.sort_index(inplace=True) pl = df.to_panel() if len(pl.minor_axis) == 1: pl = pl.minor_xs(pl.minor_axis[0]) if len(fields) == 1: pl = pl[fields[0]] return pl
def _ensure_fields(fields, fields_dict, stocks, funds, futures, futures888, spots, options, convertibles, indexes, repos): has_dominant_id = False future_only = futures and not any([stocks, funds, spots, options, convertibles, indexes, repos]) all_fields = set(fields_dict["common"]) if futures: all_fields.update(fields_dict["future"]) if stocks: all_fields.update(fields_dict["stock"]) if funds: all_fields.update(fields_dict["fund"]) if spots: all_fields.update(fields_dict["spot"]) if options: all_fields.update(fields_dict["option"]) if convertibles: all_fields.update(fields_dict["convertible"]) if indexes: all_fields.update(fields_dict["index"]) if repos: all_fields.update(fields_dict["repo"]) if future_only and futures888 and len(futures) == len(futures888) and not fields: has_dominant_id = True if fields: fields = ensure_list_of_string(fields, "fields") fields_set = set(fields) if len(fields_set) < len(fields): warnings.warn("duplicated fields: %s" % [f for f in fields if fields.count(f) > 1]) fields = list(fields_set) # 只有期货类型 if 'dominant_id' in fields: fields.remove("dominant_id") if not fields: raise ValueError("can't get dominant_id separately, please use futures.get_dominant") if futures888: has_dominant_id = True else: warnings.warn( "only if one of the order_book_id is future and contains 88/888/99/889 can the dominant_id be selected in fields") check_items_in_container(fields, all_fields, "fields") return fields, has_dominant_id else: return list(all_fields), has_dominant_id
def get_update_status(categories): """ 获取数据最新日期 :param categories: str or list or str, 数据类型,支持类型有: stock_1d: 股票日线 stock_1m: 股票分钟线 future_1d: 期货日线 future_1m: 期货分钟线 index_1d:指数日线 index_1m:指数分钟线 :return datetime.datetime or dict(category=datetime.datetime) """ categories = ensure_list_of_string(categories, "categories") check_items_in_container(categories, _CHECK_CATEGORIES, "categories") ret = get_client().execute("get_update_status", categories) if len(categories) == 1: return ret[0]["date"] return {r["category"]: r["date"] for r in ret}
def get_margin_stocks(date=None, exchange=None, margin_type='stock', market="cn"): """获取融资融券信息 :param date: 查询日期,默认返回今天上一交易日,支持 str, timestamp, datetime 类型 :param exchange: 交易所信息,默认不填写则返回全部。 str类型,默认为 None,返回所有字段。可选字段包括: 'XSHE', 'sz' 代表深交所;'XSHG', 'sh' 代表上交所,不区分大小写 (Default value = None) :param margin_type: 'stock' 代表融券卖出,'cash',代表融资买入,默认为'stock' """ if date: date = ensure_date_int(date) else: date = get_previous_trading_date(datetime.date.today()) date = date.year * 10000 + date.month * 100 + date.day if exchange is None: exchange = EXCHANGE_CONTENT else: exchange = ensure_string(exchange, "exchange") if exchange in EXCHANGE_TYPE: exchange = EXCHANGE_TYPE[exchange] check_items_in_container(exchange, EXCHANGE_CONTENT, "exchange") exchange = [exchange] margin_type = ensure_string(margin_type, "margin_type") check_items_in_container(margin_type, MARGIN_TYPE, "margin_type") data = get_client().execute("get_margin_stocks", date, exchange, margin_type, market=market) if not data: return [] else: return sorted(data)
def get_stock_connect_quota(connect=None, start_date=None, end_date=None, fields=None): """获取历史沪深港通额度日频数据 :param connect: 默认返回全部content ["sh_to_hk", "hk_to_sh", "sz_to_hk", "hk_to_sz"] :param start_date: 默认为全部历史数据 :param end_date: 默认为最新日期 :param fields: 默认为所有字段 ['buy_turnover', 'sell_turnover', 'quota_balance', 'quota_balance_ratio'] :return: """ DEFAULT_CONNECT = ["sh_to_hk", "hk_to_sh", "sz_to_hk", "hk_to_sz"] if connect is None: connect = DEFAULT_CONNECT else: connect = ensure_list_of_string(connect) check_items_in_container(connect, DEFAULT_CONNECT, 'connect') DEFAULT_FIELDS = ['buy_turnover', 'sell_turnover', 'quota_balance', 'quota_balance_ratio'] if fields is None: fields = DEFAULT_FIELDS else: fields = ensure_list_of_string(fields) check_items_in_container(fields, DEFAULT_FIELDS, 'fields') start_date = ensure_date_int(start_date) if start_date else start_date end_date = ensure_date_int(end_date) if end_date else end_date if start_date and end_date and start_date > end_date: raise ValueError("invalid date range: [{!r}, {!r}]".format(start_date, end_date)) data = get_client().execute( "get_stock_connect_quota", connect=connect, start_date=start_date, end_date=end_date, fields=fields ) if not data: return None res = pd.DataFrame(data) res.set_index(['datetime', 'connect'], inplace=True) res.sort_index(ascending=True, inplace=True) return res
def get_allotment(order_book_ids, start_date=None, end_date=None, fields=None, market="cn"): """获取配股信息 :param order_book_ids: 股票名称 :param start_date: 开始日期, 如'1991-01-01' (Default value = 1991-01-01) :param end_date: 结束日期,如'2014-01-04' (Default value = None) :param market: 地区代码,如'cn' (Default value = "cn") :returns: 返回一个DataFrame 'order_book_id': 股票合约代码 'declaration_announcement_date': 首次信息发布日期 'proportion': 配股比例(每一股对应的配股比例) 'allotted_proportion': 实际配股比例(每一股对应的配股比例) 'allotted_shares': 实际配股数量 'allotment_price': 每股配股价格 'book_closure_date': 股权登记日 'ex_right_date': 除权除息日 """ order_book_ids = ensure_order_book_ids(order_book_ids, market=market) if start_date: start_date = ensure_date_int(start_date) if end_date: end_date = ensure_date_int(end_date) if fields: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, allotment_fields, "fields") else: fields = allotment_fields all_allotment = get_client().execute("get_allotment", order_book_ids, fields, start_date, end_date, market=market) if not all_allotment: return df = pd.DataFrame(all_allotment) df.set_index(["order_book_id", "declaration_announcement_date"], inplace=True) df.sort_index(inplace=True) df = df[fields] return df
def get_main_shareholder(order_book_id, start_date=None, end_date=None, is_total=False, market="cn"): """获取十大股东信息 :param order_book_id: 股票代码 :param start_date: 开始日期,默认为一年前 :param end_date: 结束日期,默认为今天 :param is_total: 是否十大股东, True 和 False,默认为False :param market: (Default value = "cn") """ check_items_in_container(is_total, [True, False], "is_total") start_date, end_date = ensure_date_range(start_date, end_date, delta=relativedelta(years=1)) ret = get_client().execute("get_main_shareholder", order_book_id, start_date, end_date, is_total, market=market) if not ret: return columns = [ 'info_date', 'end_date', 'rank', 'shareholder_name', 'shareholder_attr', 'shareholder_kind', 'shareholder_type', 'hold_percent_total', 'hold_percent_float', 'share_pledge', 'share_freeze' ] df = pd.DataFrame(ret, columns=columns).sort_values( by=['info_date', 'rank']).set_index('info_date') return df
def get_exchange_rate(start_date=None, end_date=None, fields=None): """获取汇率信息 :param start_date: 开始日期, 如 '2013-01-04' (Default value = None) :param end_date: 结束日期, 如 '2014-01-04' (Default value = None) :param fields: str or list 返回 字段名称:currency_pair、bid_referrence_rate、ask_referrence_rate、middle_referrence_rate bid_settlement_rate_sh、ask_settlement_rate_sh、bid_settlement_rate_sz、ask_settlement_rate_sz """ start_date, end_date = ensure_date_range(start_date, end_date) if fields: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, EXCHANGE_DATE_FIELDS, "fields") else: fields = EXCHANGE_DATE_FIELDS data = get_client().execute("get_exchange_rate", start_date, end_date, fields) if not data: return None df = pd.DataFrame(data) df.set_index("date", inplace=True) df = df[fields] return df
def get_amc(amc_ids=None, fields=None, market="cn"): """获取基金公司详情信息 :param amc_ids: 基金公司id或简称,默认为 None :param fields: 可选参数。默认为所有字段。 (Default value = None) :param market: (Default value = "cn") :returns: DataFrame """ if fields is None: fields = AMC_FIELDS else: fields = ensure_list_of_string(fields) check_items_in_container(fields, AMC_FIELDS, "fields") result = get_client().execute("fund.get_amc", market=market) if amc_ids: amc_ids = ensure_list_of_string(amc_ids) amcs = tuple(amc_ids) result = [i for i in result if i["amc_id"] in amc_ids or i["amc"].startswith(amcs)] if not result: return return pd.DataFrame(result)[fields]
def get_index_factor_exposure(order_book_ids, start_date=None, end_date=None, factors=None, market="cn"): """获取因子暴露度 :param order_book_ids: 股票代码或代码列表 :param start_date: 如'2013-01-04' (Default value = None) :param end_date: 如'2014-01-04' (Default value = None) :param factors: 如'yield', 'beta', 'volatility' (Default value = None) :param market: 地区代码, 如'cn' (Default value = "cn") """ try: order_book_ids = ensure_order_book_ids(order_book_ids, type="INDX") except ValueError: return start_date, end_date = ensure_date_range(start_date, end_date) if factors is not None: factors = ensure_list_of_string(factors) check_items_in_container(factors, exposure_factors, "factors") results = get_client().execute("get_index_factor_exposure", order_book_ids, start_date, end_date, factors, market=market) if not results: return None df = pd.DataFrame.from_records(results, index=['date', 'order_book_id']) df.sort_index(inplace=True) return df
def get_stock_beta(order_book_ids, start_date, end_date, benchmark="000300.XSHG", market="cn"): """获取个股相对于基准的贝塔 :param order_book_ids: 证券代码(例如:‘600705.XSHG’) :param start_date: 开始日期(例如:‘2017-03-03’) :param end_date: 结束日期(例如:‘2017-03-20’) :param benchmark: 基准指数。默认为沪深300(‘000300.XSHG’) 可选上证50('000016.XSHG')、中证500('000905.XSHG')、 中证800('000906.XSHG')以及中证全指('000985.XSHG') (Default value = "000300.XSHG") :param market: (Default value = "cn") :returns: pandas.DataFrame,index 为日期,column 为个股的 order_book_id """ order_book_ids = ensure_order_book_ids(order_book_ids) start_date, end_date = ensure_date_range(start_date, end_date) all_benchmark = ("000300.XSHG", "000016.XSHG", "000905.XSHG", "000906.XSHG", "000985.XSHG") benchmark = ensure_string(benchmark, "benchmark") check_items_in_container(benchmark, all_benchmark, "benchmark") benchmark = benchmark.replace(".", "_") df = get_client().execute("get_stock_beta", order_book_ids, start_date, end_date, benchmark, market=market) if not df: return df = pd.DataFrame(df) df = df.pivot(index="date", columns="order_book_id", values=benchmark).sort_index() return df
def current_performance( order_book_id, info_date=None, quarter=None, interval="1q", fields=None, market="cn" ): """获取A股快报 :param order_book_id: 股票代码, 如'000001.XSHE' :param info_date: 发布日期, 如'20180501', 默认为最近的交易日 (Default value = None) :param quarter: 发布季度, 如'2018q1' (Default value = None) :param interval: 数据区间, 发布日期, 如'2y', '4q' (Default value = "1q") :param fields: str 或 list 类型. 默认为 None, 返回所有字段 (Default value = None) :param market: 地区代码, 如'cn' (Default value = "cn") :returns: pd.DataFrame """ order_book_id = ensure_order_book_id(order_book_id, market=market) end_date = None if info_date: info_date = ensure_date_int(info_date) elif quarter: splited = quarter.lower().split("q") if len(quarter) != 6 or len(splited) != 2: raise ValueError( "invalid argument {}: {}, valid parameter: {}".format( "quarter", quarter, "string format like '2016q1'" ) ) year, quarter = int(splited[0]), int(splited[1]) if not 1 <= quarter <= 4: raise ValueError( "invalid argument {}: {}, valid parameter: {}".format( "quarter", quarter, "quarter should be in [1, 4]" ) ) month, day = QUARTER_DATE_MAP[quarter] end_date = ensure_date_int(datetime.datetime(year, month, day)) else: info_date = ensure_date_int(datetime.date.today()) ensure_string(interval, "interval") if interval[-1] not in ("y", "q", "Y", "Q"): raise ValueError( "invalid argument {}: {}, valid parameter: {}".format( "interval", interval, "interval unit should be q(quarter) or y(year)" ) ) try: int(interval[:-1]) except ValueError: raise ValueError( "invalid argument {}: {}, valid parameter: {}".format( "interval", interval, "string like 4q, 2y" ) ) interval = interval.lower() if fields is not None: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, PERFORMANCE_FIELDS, "fields") else: fields = PERFORMANCE_FIELDS data = get_client().execute( "current_performance", order_book_id, info_date, end_date, fields, market=market ) if not data: return df = pd.DataFrame(data) sort_field = "info_date" if info_date else "end_date" df.sort_values(by=[sort_field, "mark"], ascending=[False, True], inplace=True) df.drop_duplicates(subset="end_date", keep="first", inplace=True) num = int(interval[:-1]) unit = interval[-1] if unit == "y": latest_month = df.loc[0, "end_date"].month df["month"] = df.end_date.apply(lambda x: x.month) df = df[df.month == latest_month] df.reset_index(drop=True, inplace=True) return df.loc[: num - 1, ["end_date", "info_date"] + fields]
def get_tick_price_multi_df(order_book_ids, start_date, end_date, fields, market): ins_list = ensure_instruments(order_book_ids) order_book_ids = [ins.order_book_id for ins in ins_list] types = {ins.type for ins in ins_list} start_date, end_date = ensure_date_range(start_date, end_date, datetime.timedelta(days=3)) if "Future" in types or "Option" in types: base_fields = FUTURE_TICK_FIELDS base_columns = FUTURE_TICK_COLUMNS else: base_fields = EQUITIES_TICK_FIELDS base_columns = EQUITIES_TICK_COLUMNS if fields: fields = ensure_list_of_string(fields, "fields") check_items_in_container(fields, base_fields, "fields") columns = [f for f in base_columns if f in fields] else: fields = base_fields columns = base_columns gtw_fields = set(fields) | {"date", "time"} if set(fields) & RELATED_DABAR_FIELDS: gtw_fields.update({"volume", "last"}) history_df = get_history_tick(order_book_ids, start_date, end_date, list(gtw_fields), columns, market) history_latest_date = 0 if history_df is None else date_to_int8(get_current_trading_date( history_df.index.get_level_values(1).max())) today = today_int() next_trading_date = date_to_int8(get_next_trading_date(today, market=market)) if history_latest_date >= end_date or start_date > next_trading_date or end_date < today: return history_df if end_date >= next_trading_date and (start_date > today or history_latest_date >= today): live_date = next_trading_date else: live_date = today if history_latest_date >= live_date: return history_df live_dfs = [] for ins in ins_list: try: live_df = get_ticks(ins.order_book_id, start_date=live_date, end_date=live_date, expect_df=True, market=market) except (PermissionDenied, MarketNotSupportError): pass else: if live_df is None: continue if "trading_date" not in live_df.columns: live_df["trading_date"] = int8_to_datetime(live_date) else: live_df["trading_date"] = live_df["trading_date"].apply(to_datetime) if ins.type in ("Future", "Option"): live_df["change_rate"] = live_df["last"] / live_df["prev_settlement"] - 1 else: live_df["change_rate"] = live_df["last"] / live_df["prev_close"] - 1 live_df = live_df.reindex(columns=columns) live_dfs.append(live_df) if not live_dfs: return history_df if history_df is None: return pd.concat(live_dfs) return pd.concat([history_df] + live_dfs)