stock-tracker

This commit is contained in:
C菌
2026-07-04 00:17:11 +08:00
commit 6087341a48
6463 changed files with 1929869 additions and 0 deletions
File diff suppressed because it is too large Load Diff
@@ -0,0 +1 @@
__version__ = "1.18.64"
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/9/30 13:58
Desc:
"""
@@ -0,0 +1,107 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/25 17:20
Desc: 河北省空气质量预报信息发布系统
https://110.249.223.67/publish
每日 17 时发布
等级划分
1. 空气污染指数为0-50,空气质量级别为一级,空气质量状况属于优。此时,空气质量令人满意,基本无空气污染,各类人群可正常活动。
2. 空气污染指数为51-100,空气质量级别为二级,空气质量状况属于良。此时空气质量可接受,但某些污染物可能对极少数异常敏感人群健康有较弱影响,建议极少数异常敏感人群应减少户外活动。
3. 空气污染指数为101-150,空气质量级别为三级,空气质量状况属于轻度污染。此时,易感人群症状有轻度加剧,健康人群出现刺激症状。建议儿童、老年人及心脏病、呼吸系统疾病患者应减少长时间、高强度的户外锻炼。
4. 空气污染指数为151-200,空气质量级别为四级,空气质量状况属于中度污染。此时,进一步加剧易感人群症状,可能对健康人群心脏、呼吸系统有影响,建议疾病患者避免长时间、高强度的户外锻练,一般人群适量减少户外运动。
5. 空气污染指数为201-300,空气质量级别为五级,空气质量状况属于重度污染。此时,心脏病和肺病患者症状显著加剧,运动耐受力降低,健康人群普遍出现症状,建议儿童、老年人和心脏病、肺病患者应停留在室内,停止户外运动,一般人群减少户外运动。
6. 空气污染指数大于300,空气质量级别为六级,空气质量状况属于严重污染。此时,健康人群运动耐受力降低,有明显强烈症状,提前出现某些疾病,建议儿童、老年人和病人应当留在室内,避免体力消耗,一般人群应避免户外活动。
发布单位:河北省环境应急与重污染天气预警中心 技术支持:中国科学院大气物理研究所 中科三清科技有限公司
"""
import pandas as pd
import requests
from bs4 import BeautifulSoup
def air_quality_hebei() -> pd.DataFrame:
"""
河北省空气质量预报信息发布系统-空气质量预报, 未来 6 天
http://218.11.10.130:8080/#/application/home
:return: city = "", 返回所有地区的数据; city="唐山市", 返回唐山市的数据
:rtype: pandas.DataFrame
"""
url = "http://218.11.10.130:8080/api/hour/130000.xml"
r = requests.get(url)
soup = BeautifulSoup(r.content, features="xml")
data = []
cities = soup.find_all("City")
for city in cities:
pointers = city.find_all("Pointer")
for pointer in pointers:
row = {
"City": city.Name.text if city.Name else None,
"Region": pointer.Region.text if pointer.Region else None,
"Station": pointer.Name.text if pointer.Name else None,
"DateTime": pointer.DataTime.text if pointer.DataTime else None,
"AQI": pointer.AQI.text if pointer.AQI else None,
"Level": pointer.Level.text if pointer.Level else None,
"MaxPoll": pointer.MaxPoll.text if pointer.MaxPoll else None,
"Longitude": pointer.CLng.text if pointer.CLng else None,
"Latitude": pointer.CLat.text if pointer.CLat else None,
}
polls = pointer.find_all("Poll")
for poll in polls:
poll_name = poll.Name.text if poll.Name else None
poll_value = poll.Value.text if poll.Value else None
row[f"{poll_name}_Value"] = poll_value
row[f"{poll_name}_IAQI"] = poll.IAQI.text if poll.IAQI else None
data.append(row)
df = pd.DataFrame(data)
numeric_columns = ["AQI", "Longitude", "Latitude"] + [
col for col in df.columns if col.endswith("_Value") or col.endswith("_IAQI")
]
for col in numeric_columns:
df[col] = pd.to_numeric(df[col], errors="coerce")
column_names = {
"City": "城市",
"Region": "区域",
"Station": "监测点",
"DateTime": "时间",
"Level": "空气质量等级",
"MaxPoll": "首要污染物",
"Longitude": "经度",
"Latitude": "纬度",
"SO2_Value": "二氧化硫_浓度",
"SO2_IAQI": "二氧化硫_IAQI",
"CO_Value": "一氧化碳_浓度",
"CO_IAQI": "一氧化碳_IAQI",
"NO2_Value": "二氧化氮_浓度",
"NO2_IAQI": "二氧化氮_IAQI",
"O3-1H_Value": "臭氧1小时_浓度",
"O3-1H_IAQI": "臭氧1小时_IAQI",
"O3-8H_Value": "臭氧8小时_浓度",
"O3-8H_IAQI": "臭氧8小时_IAQI",
"PM2.5_Value": "PM2.5_浓度",
"PM2.5_IAQI": "PM2.5_IAQI",
"PM10_Value": "PM10_浓度",
"PM10_IAQI": "PM10_IAQI",
}
df = df.rename(columns=column_names)
basic_columns = [
"城市",
"区域",
"监测点",
"时间",
"AQI",
"空气质量等级",
"首要污染物",
"经度",
"纬度",
]
pollutant_columns = [col for col in df.columns if col not in basic_columns]
df = df[basic_columns + sorted(pollutant_columns)]
return df
if __name__ == "__main__":
air_quality_hebei_df = air_quality_hebei()
print(air_quality_hebei_df)
@@ -0,0 +1,294 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/2 22:40
Desc: 真气网-空气质量
https://www.zq12369.com/environment.php
空气质量在线监测分析平台的空气质量数据
https://www.aqistudy.cn/
"""
import json
import os
import re
from io import StringIO
import pandas as pd
import requests
from py_mini_racer import MiniRacer
from akshare.utils import demjson
def _get_js_path(name: str = None, module_file: str = None) -> str:
"""
获取 JS 文件的路径(从模块所在目录查找)
:param name: 文件名
:type name: str
:param module_file: 模块路径
:type module_file: str
:return: 路径
:rtype: str
"""
module_folder = os.path.abspath(os.path.dirname(os.path.dirname(module_file)))
module_json_path = os.path.join(module_folder, "air", name)
return module_json_path
def _get_file_content(file_name: str = "crypto.js") -> str:
"""
获取 JS 文件的内容
:param file_name: JS 文件名
:type file_name: str
:return: 文件内容
:rtype: str
"""
setting_file_name = file_name
setting_file_path = _get_js_path(setting_file_name, __file__)
with open(setting_file_path) as f:
file_data = f.read()
return file_data
def has_month_data(href):
"""
Deal with href node
:param href: href
:type href: str
:return: href result
:rtype: str
"""
return href and re.compile("monthdata.php").search(href)
def air_city_table() -> pd.DataFrame:
"""
真气网-空气质量历史数据查询-全部城市列表
https://www.zq12369.com/environment.php?date=2019-06-05&tab=rank&order=DESC&type=DAY#rank
:return: 城市映射
:rtype: pandas.DataFrame
"""
url = "https://www.zq12369.com/environment.php"
date = "2020-05-01"
temp_df = None
if len(date.split("-")) == 3:
params = {
"date": date,
"tab": "rank",
"order": "DESC",
"type": "DAY",
}
r = requests.get(url, params=params)
temp_df = pd.read_html(StringIO(r.text))[1].iloc[1:, :]
del temp_df["降序"]
temp_df.reset_index(inplace=True)
temp_df["index"] = temp_df.index + 1
temp_df.columns = [
"序号",
"省份",
"城市",
"AQI",
"空气质量",
"PM2.5浓度",
"首要污染物",
]
temp_df["AQI"] = pd.to_numeric(temp_df["AQI"])
return temp_df
def air_quality_watch_point(
city: str = "杭州", start_date: str = "20220408", end_date: str = "20220409"
) -> pd.DataFrame:
"""
真气网-监测点空气质量-细化到具体城市的每个监测点
指定之间段之间的空气质量数据
https://www.zq12369.com/
:param city: 调用 ak.air_city_table() 接口获取
:type city: str
:param start_date: e.g., "20190327"
:type start_date: str
:param end_date: e.g., ""20200327""
:type end_date: str
:return: 指定城市指定日期区间的观测点空气质量
:rtype: pandas.DataFrame
"""
start_date = "-".join([start_date[:4], start_date[4:6], start_date[6:]])
end_date = "-".join([end_date[:4], end_date[4:6], end_date[6:]])
url = "https://www.zq12369.com/api/zhenqiapi.php"
file_data = _get_file_content(file_name="crypto.js")
ctx = MiniRacer()
ctx.eval(file_data)
method = "GETCITYPOINTAVG"
city_param = ctx.call("encode_param", city)
payload = {
"appId": "a01901d3caba1f362d69474674ce477f",
"method": ctx.call("encode_param", method),
"city": city_param,
"startTime": ctx.call("encode_param", start_date),
"endTime": ctx.call("encode_param", end_date),
"secret": ctx.call("encode_secret", method, city_param, start_date, end_date),
}
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/81.0.4044.122 Safari/537.36"
}
r = requests.post(url, data=payload, headers=headers)
data_text = r.text
data_json = demjson.decode(ctx.call("decode_result", data_text))
temp_df = pd.DataFrame(data_json["rows"])
return temp_df
def air_quality_hist(
city: str = "杭州",
period: str = "day",
start_date: str = "20190327",
end_date: str = "20200427",
) -> pd.DataFrame:
"""
真气网-空气历史数据
https://www.zq12369.com/
:param city: 调用 ak.air_city_table() 接口获取所有城市列表
:type city: str
:param period: "hour": 每小时一个数据, 由于数据量比较大, 下载较慢; "day": 每天一个数据; "month": 每个月一个数据
:type period: str
:param start_date: e.g., "20190327"
:type start_date: str
:param end_date: e.g., "20200327"
:type end_date: str
:return: 指定城市和数据频率下在指定时间段内的空气质量数据
:rtype: pandas.DataFrame
"""
start_date = "-".join([start_date[:4], start_date[4:6], start_date[6:]])
end_date = "-".join([end_date[:4], end_date[4:6], end_date[6:]])
url = "https://www.zq12369.com/api/newzhenqiapi.php"
file_data = _get_file_content(file_name="outcrypto.js")
ctx = MiniRacer()
ctx.eval(file_data)
app_id = "4f0e3a273d547ce6b7147bfa7ceb4b6e"
method = "CETCITYPERIOD"
timestamp = ctx.eval("timestamp = new Date().getTime()")
p_text = json.dumps(
{
"city": city,
"endTime": f"{end_date} 23:45:39",
"startTime": f"{start_date} 00:00:00",
"type": period.upper(),
},
ensure_ascii=False,
indent=None,
).replace(' "', '"')
secret = ctx.call("hex_md5", app_id + method + str(timestamp) + "WEB" + p_text)
payload = {
"appId": "4f0e3a273d547ce6b7147bfa7ceb4b6e",
"method": "CETCITYPERIOD",
"timestamp": int(timestamp),
"clienttype": "WEB",
"object": {
"city": city,
"type": period.upper(),
"startTime": f"{start_date} 00:00:00",
"endTime": f"{end_date} 23:45:39",
},
"secret": secret,
}
need = (
json.dumps(payload, ensure_ascii=False, indent=None, sort_keys=False)
.replace(' "', '"')
.replace("\\", "")
.replace('p": ', 'p":')
.replace('t": ', 't":')
)
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko)"
"Chrome/100.0.4896.75 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {"param": ctx.call("encode_param", need)}
r = requests.post(url, data=params, headers=headers)
temp_text = ctx.call("decryptData", r.text)
data_json = demjson.decode(ctx.call("b.decode", temp_text))
temp_df = pd.DataFrame(data_json["result"]["data"]["rows"])
temp_df.index = temp_df["time"]
del temp_df["time"]
temp_df = temp_df.astype(float, errors="ignore")
return temp_df
def air_quality_rank(date: str = "") -> pd.DataFrame:
"""
真气网-168 城市 AQI 排行榜
https://www.zq12369.com/environment.php?date=2020-03-12&tab=rank&order=DESC&type=DAY#rank
:param date: "": 当前时刻空气质量排名; "20200312": 当日空气质量排名; "202003": 当月空气质量排名; "2019": 当年空气质量排名;
:type date: str
:return: 指定 date 类型的空气质量排名数据
:rtype: pandas.DataFrame
"""
if len(date) == 4:
date = date
elif len(date) == 6:
date = "-".join([date[:4], date[4:6]])
elif date == "":
date = "实时"
else:
date = "-".join([date[:4], date[4:6], date[6:]])
url = "https://www.zq12369.com/environment.php"
if len(date.split("-")) == 3:
params = {
"date": date,
"tab": "rank",
"order": "DESC",
"type": "DAY",
}
r = requests.get(url, params=params)
return pd.read_html(StringIO(r.text))[1].iloc[1:, :]
elif len(date.split("-")) == 2:
params = {
"month": date,
"tab": "rank",
"order": "DESC",
"type": "MONTH",
}
r = requests.get(url, params=params)
return pd.read_html(StringIO(r.text))[2].iloc[1:, :]
elif len(date.split("-")) == 1 and date != "实时":
params = {
"year": date,
"tab": "rank",
"order": "DESC",
"type": "YEAR",
}
r = requests.get(url, params=params)
return pd.read_html(StringIO(r.text))[3].iloc[1:, :]
if date == "实时":
params = {
"tab": "rank",
"order": "DESC",
"type": "MONTH",
}
r = requests.get(url, params=params)
return pd.read_html(StringIO(r.text))[0].iloc[1:, :]
if __name__ == "__main__":
air_city_table_df = air_city_table()
print(air_city_table_df)
air_quality_watch_point_df = air_quality_watch_point(
city="杭州", start_date="20220408", end_date="20220409"
)
print(air_quality_watch_point_df)
air_quality_hist_df = air_quality_hist(
city="北京",
period="day",
start_date="20220801",
end_date="20240402",
)
print(air_quality_hist_df)
air_quality_rank_df = air_quality_rank()
print(air_quality_rank_df)
@@ -0,0 +1,413 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/11/25 20:45
Desc: 空气质量接口配置文件
"""
city_chinese_list = [
"北京",
"重庆",
"福州",
"广州",
"杭州",
"昆明",
"南昌",
"南京",
"南宁",
"南通",
"宁波",
"上海",
"深圳",
"苏州",
"徐州",
"银川",
]
city_english_list = [
"beijing",
"chongqing",
"foochow",
"guangzhou",
"hangzhou",
"kunming",
"nanchang",
"nanjing",
"nanning",
"nantong",
"ningbo",
"shanghai",
"shenzhen",
"suzhou",
"xuzhou",
"yinchuan",
]
city_code_dict = {
"北京": "110000",
"天津": "120000",
"石家庄": "130100",
"唐山": "130200",
"秦皇岛": "130300",
"邯郸": "130400",
"邢台": "130500",
"保定": "130600",
"承德": "130800",
"沧州": "130900",
"廊坊": "131000",
"衡水": "131100",
"张家口": "131200",
"太原": "140100",
"大同": "140200",
"阳泉": "140300",
"长治": "140400",
"晋城": "140500",
"朔州": "140600",
"晋中": "140700",
"运城": "140800",
"忻州": "140900",
"临汾": "141000",
"吕梁": "141100",
"呼和浩特": "150100",
"包头": "150200",
"乌海": "150300",
"赤峰": "150400",
"通辽": "150500",
"鄂尔多斯": "150600",
"呼伦贝尔": "150700",
"巴彦淖尔": "150800",
"乌兰察布": "150900",
"兴安盟": "152200",
"锡林郭勒盟": "152500",
"阿拉善盟": "152900",
"沈阳": "210100",
"大连": "210200",
"瓦房店": "210281",
"鞍山": "210300",
"抚顺": "210400",
"本溪": "210500",
"丹东": "210600",
"锦州": "210700",
"营口": "210800",
"阜新": "210900",
"辽阳": "211000",
"盘锦": "211100",
"铁岭": "211200",
"朝阳": "211300",
"葫芦岛": "211400",
"长春": "220100",
"吉林": "220200",
"四平": "220300",
"辽源": "220400",
"通化": "220500",
"白山": "220600",
"松原": "220700",
"白城": "220800",
"延边州": "222400",
"哈尔滨": "230100",
"齐齐哈尔": "230200",
"鸡西": "230300",
"鹤岗": "230400",
"双鸭山": "230500",
"大庆": "230600",
"伊春": "230700",
"佳木斯": "230800",
"七台河": "230900",
"牡丹江": "231000",
"黑河": "231100",
"绥化": "231200",
"大兴安岭地区": "232700",
"上海": "310000",
"南京": "320100",
"无锡": "320200",
"江阴": "320281",
"宜兴": "320282",
"徐州": "320300",
"常州": "320400",
"溧阳": "320481",
"金坛": "320482",
"苏州": "320500",
"常熟": "320581",
"张家港": "320582",
"昆山": "320583",
"吴江": "320584",
"太仓": "320585",
"南通": "320600",
"海门": "320684",
"连云港": "320700",
"淮安": "320800",
"盐城": "320900",
"扬州": "321000",
"镇江": "321100",
"句容": "321183",
"泰州": "321200",
"宿迁": "321300",
"杭州": "330100",
"富阳": "330183",
"临安": "330185",
"宁波": "330200",
"温州": "330300",
"嘉兴": "330400",
"湖州": "330500",
"诸暨": "330681",
"金华": "330700",
"义乌": "330782",
"衢州": "330800",
"舟山": "330900",
"台州": "331000",
"丽水": "331100",
"绍兴": "331300",
"合肥": "340100",
"芜湖": "340200",
"蚌埠": "340300",
"淮南": "340400",
"马鞍山": "340500",
"淮北": "340600",
"铜陵": "340700",
"安庆": "340800",
"黄山": "341000",
"滁州": "341100",
"阜阳": "341200",
"宿州": "341300",
"六安": "341500",
"亳州": "341600",
"池州": "341700",
"宣城": "341800",
"福州": "350100",
"厦门": "350200",
"莆田": "350300",
"三明": "350400",
"泉州": "350500",
"漳州": "350600",
"南平": "350700",
"龙岩": "350800",
"宁德": "350900",
"南昌": "360100",
"景德镇": "360200",
"萍乡": "360300",
"九江": "360400",
"新余": "360500",
"鹰潭": "360600",
"赣州": "360700",
"吉安": "360800",
"宜春": "360900",
"抚州": "361000",
"上饶": "361100",
"济南": "370100",
"章丘": "370181",
"青岛": "370200",
"胶州": "370281",
"即墨": "370282",
"平度": "370283",
"胶南": "370284",
"莱西": "370285",
"淄博": "370300",
"枣庄": "370400",
"东营": "370500",
"烟台": "370600",
"莱州": "370683",
"蓬莱": "370684",
"招远": "370685",
"潍坊": "370700",
"寿光": "370783",
"济宁": "370800",
"泰安": "370900",
"威海": "371000",
"文登": "371081",
"荣成": "371082",
"乳山": "371083",
"日照": "371100",
"莱芜": "371200",
"临沂": "371300",
"德州": "371400",
"聊城": "371500",
"滨州": "371600",
"菏泽": "371700",
"郑州": "410100",
"开封": "410200",
"洛阳": "410300",
"平顶山": "410400",
"安阳": "410500",
"鹤壁": "410600",
"新乡": "410700",
"焦作": "410800",
"濮阳": "410900",
"许昌": "411000",
"漯河": "411100",
"三门峡": "411200",
"南阳": "411300",
"商丘": "411400",
"信阳": "411500",
"周口": "411600",
"驻马店": "411700",
"武汉": "420100",
"黄石": "420200",
"十堰": "420300",
"宜昌": "420500",
"襄阳": "420600",
"鄂州": "420700",
"荆门": "420800",
"孝感": "420900",
"荆州": "421000",
"黄冈": "421100",
"咸宁": "421200",
"随州": "421300",
"恩施州": "422800",
"长沙": "430100",
"株洲": "430200",
"湘潭": "430300",
"衡阳": "430400",
"邵阳": "430500",
"岳阳": "430600",
"常德": "430700",
"张家界": "430800",
"益阳": "430900",
"郴州": "431000",
"永州": "431100",
"怀化": "431200",
"娄底": "431300",
"湘西州": "433100",
"广州": "440100",
"韶关": "440200",
"深圳": "440300",
"珠海": "440400",
"汕头": "440500",
"佛山": "440600",
"江门": "440700",
"湛江": "440800",
"茂名": "440900",
"肇庆": "441200",
"惠州": "441300",
"梅州": "441400",
"汕尾": "441500",
"河源": "441600",
"阳江": "441700",
"清远": "441800",
"东莞": "441900",
"中山": "442000",
"潮州": "445100",
"揭阳": "445200",
"云浮": "445300",
"南宁": "450100",
"柳州": "450200",
"桂林": "450300",
"梧州": "450400",
"北海": "450500",
"防城港": "450600",
"钦州": "450700",
"贵港": "450800",
"玉林": "450900",
"百色": "451000",
"贺州": "451100",
"河池": "451200",
"来宾": "451300",
"崇左": "451400",
"海口": "460100",
"三亚": "460200",
"重庆": "500000",
"成都": "510100",
"自贡": "510300",
"攀枝花": "510400",
"泸州": "510500",
"德阳": "510600",
"绵阳": "510700",
"广元": "510800",
"遂宁": "510900",
"内江": "511000",
"乐山": "511100",
"南充": "511300",
"眉山": "511400",
"宜宾": "511500",
"广安": "511600",
"达州": "511700",
"雅安": "511800",
"巴中": "511900",
"资阳": "512000",
"阿坝州": "513200",
"甘孜州": "513300",
"凉山州": "513400",
"贵阳": "520100",
"六盘水": "520200",
"遵义": "520300",
"安顺": "520400",
"铜仁地区": "522200",
"黔西南州": "522300",
"毕节": "522400",
"黔东南州": "522600",
"黔南州": "522700",
"昆明": "530100",
"曲靖": "530300",
"玉溪": "530400",
"保山": "530500",
"昭通": "530600",
"丽江": "530700",
"普洱": "530800",
"临沧": "530900",
"红河州": "532522",
"文山州": "532621",
"西双版纳州": "532801",
"大理州": "532901",
"德宏州": "533103",
"怒江州": "533300",
"迪庆州": "533421",
"拉萨": "540100",
"昌都": "542100",
"山南": "542200",
"日喀则": "542300",
"那曲地区": "542400",
"阿里地区": "542500",
"林芝": "542600",
"西安": "610100",
"铜川": "610200",
"宝鸡": "610300",
"咸阳": "610400",
"渭南": "610500",
"延安": "610600",
"汉中": "610700",
"榆林": "610800",
"安康": "610900",
"商洛": "611000",
"兰州": "620100",
"嘉峪关": "620200",
"金昌": "620300",
"白银": "620400",
"天水": "620500",
"武威": "620600",
"张掖": "620700",
"平凉": "620800",
"酒泉": "620900",
"庆阳": "621000",
"定西": "621100",
"陇南": "621200",
"临夏州": "622900",
"甘南州": "623000",
"西宁": "630100",
"海东地区": "632100",
"海北州": "632200",
"黄南州": "632300",
"海南州": "632500",
"果洛州": "632600",
"玉树州": "632700",
"海西州": "632800",
"银川": "640100",
"石嘴山": "640200",
"吴忠": "640300",
"固原": "640400",
"中卫": "640500",
"乌鲁木齐": "650100",
"克拉玛依": "650200",
"吐鲁番地区": "652100",
"哈密地区": "652200",
"昌吉州": "652300",
"博州": "652700",
"库尔勒": "652800",
"阿克苏地区": "652900",
"克州": "653000",
"喀什地区": "653100",
"和田地区": "653200",
"伊犁哈萨克州": "654000",
"塔城地区": "654200",
"阿勒泰地区": "654300",
"石河子": "659001",
"五家渠": "659004",
}
@@ -0,0 +1,139 @@
function Base64() {
_keyStr = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=", this.encode = function(a) {
var c, d, e, f, g, h, i, b = "",
j = 0;
for (a = _utf8_encode(a); j < a.length;) c = a.charCodeAt(j++), d = a.charCodeAt(j++), e = a.charCodeAt(j++), f = c >> 2, g = (3 & c) << 4 | d >> 4, h = (15 & d) << 2 | e >> 6, i = 63 & e, isNaN(d) ? h = i = 64 : isNaN(e) && (i = 64), b = b + _keyStr.charAt(f) + _keyStr.charAt(g) + _keyStr.charAt(h) + _keyStr.charAt(i);
return b
}, this.decode = function(a) {
var c, d, e, f, g, h, i, b = "",
j = 0;
for (a = a.replace(/[^A-Za-z0-9\+\/\=]/g, ""); j < a.length;) f = _keyStr.indexOf(a.charAt(j++)), g = _keyStr.indexOf(a.charAt(j++)), h = _keyStr.indexOf(a.charAt(j++)), i = _keyStr.indexOf(a.charAt(j++)), c = f << 2 | g >> 4, d = (15 & g) << 4 | h >> 2, e = (3 & h) << 6 | i, b += String.fromCharCode(c), 64 != h && (b += String.fromCharCode(d)), 64 != i && (b += String.fromCharCode(e));
return b = _utf8_decode(b)
}, _utf8_encode = function(a) {
var b, c, d;
for (a = a.replace(/\r\n/g, "\n"), b = "", c = 0; c < a.length; c++) d = a.charCodeAt(c), 128 > d ? b += String.fromCharCode(d) : d > 127 && 2048 > d ? (b += String.fromCharCode(192 | d >> 6), b += String.fromCharCode(128 | 63 & d)) : (b += String.fromCharCode(224 | d >> 12), b += String.fromCharCode(128 | 63 & d >> 6), b += String.fromCharCode(128 | 63 & d));
return b
}, _utf8_decode = function(a) {
for (var b = "", c = 0, d = c1 = c2 = 0; c < a.length;) d = a.charCodeAt(c), 128 > d ? (b += String.fromCharCode(d), c++) : d > 191 && 224 > d ? (c2 = a.charCodeAt(c + 1), b += String.fromCharCode((31 & d) << 6 | 63 & c2), c += 2) : (c2 = a.charCodeAt(c + 1), c3 = a.charCodeAt(c + 2), b += String.fromCharCode((15 & d) << 12 | (63 & c2) << 6 | 63 & c3), c += 3);
return b
}
}
function hex_md5(a) {
return binl2hex(core_md5(str2binl(a), a.length * chrsz))
}
function b64_md5(a) {
return binl2b64(core_md5(str2binl(a), a.length * chrsz))
}
function str_md5(a) {
return binl2str(core_md5(str2binl(a), a.length * chrsz))
}
function hex_hmac_md5(a, b) {
return binl2hex(core_hmac_md5(a, b))
}
function b64_hmac_md5(a, b) {
return binl2b64(core_hmac_md5(a, b))
}
function str_hmac_md5(a, b) {
return binl2str(core_hmac_md5(a, b))
}
function md5_vm_test() {
return "900150983cd24fb0d6963f7d28e17f72" == hex_md5("abc")
}
function core_md5(a, b) {
var c, d, e, f, g, h, i, j, k;
for (a[b >> 5] |= 128 << b % 32, a[(b + 64 >>> 9 << 4) + 14] = b, c = 1732584193, d = -271733879, e = -1732584194, f = 271733878, g = 0; g < a.length; g += 16) h = c, i = d, j = e, k = f, c = md5_ff(c, d, e, f, a[g + 0], 7, -680876936), f = md5_ff(f, c, d, e, a[g + 1], 12, -389564586), e = md5_ff(e, f, c, d, a[g + 2], 17, 606105819), d = md5_ff(d, e, f, c, a[g + 3], 22, -1044525330), c = md5_ff(c, d, e, f, a[g + 4], 7, -176418897), f = md5_ff(f, c, d, e, a[g + 5], 12, 1200080426), e = md5_ff(e, f, c, d, a[g + 6], 17, -1473231341), d = md5_ff(d, e, f, c, a[g + 7], 22, -45705983), c = md5_ff(c, d, e, f, a[g + 8], 7, 1770035416), f = md5_ff(f, c, d, e, a[g + 9], 12, -1958414417), e = md5_ff(e, f, c, d, a[g + 10], 17, -42063), d = md5_ff(d, e, f, c, a[g + 11], 22, -1990404162), c = md5_ff(c, d, e, f, a[g + 12], 7, 1804603682), f = md5_ff(f, c, d, e, a[g + 13], 12, -40341101), e = md5_ff(e, f, c, d, a[g + 14], 17, -1502002290), d = md5_ff(d, e, f, c, a[g + 15], 22, 1236535329), c = md5_gg(c, d, e, f, a[g + 1], 5, -165796510), f = md5_gg(f, c, d, e, a[g + 6], 9, -1069501632), e = md5_gg(e, f, c, d, a[g + 11], 14, 643717713), d = md5_gg(d, e, f, c, a[g + 0], 20, -373897302), c = md5_gg(c, d, e, f, a[g + 5], 5, -701558691), f = md5_gg(f, c, d, e, a[g + 10], 9, 38016083), e = md5_gg(e, f, c, d, a[g + 15], 14, -660478335), d = md5_gg(d, e, f, c, a[g + 4], 20, -405537848), c = md5_gg(c, d, e, f, a[g + 9], 5, 568446438), f = md5_gg(f, c, d, e, a[g + 14], 9, -1019803690), e = md5_gg(e, f, c, d, a[g + 3], 14, -187363961), d = md5_gg(d, e, f, c, a[g + 8], 20, 1163531501), c = md5_gg(c, d, e, f, a[g + 13], 5, -1444681467), f = md5_gg(f, c, d, e, a[g + 2], 9, -51403784), e = md5_gg(e, f, c, d, a[g + 7], 14, 1735328473), d = md5_gg(d, e, f, c, a[g + 12], 20, -1926607734), c = md5_hh(c, d, e, f, a[g + 5], 4, -378558), f = md5_hh(f, c, d, e, a[g + 8], 11, -2022574463), e = md5_hh(e, f, c, d, a[g + 11], 16, 1839030562), d = md5_hh(d, e, f, c, a[g + 14], 23, -35309556), c = md5_hh(c, d, e, f, a[g + 1], 4, -1530992060), f = md5_hh(f, c, d, e, a[g + 4], 11, 1272893353), e = md5_hh(e, f, c, d, a[g + 7], 16, -155497632), d = md5_hh(d, e, f, c, a[g + 10], 23, -1094730640), c = md5_hh(c, d, e, f, a[g + 13], 4, 681279174), f = md5_hh(f, c, d, e, a[g + 0], 11, -358537222), e = md5_hh(e, f, c, d, a[g + 3], 16, -722521979), d = md5_hh(d, e, f, c, a[g + 6], 23, 76029189), c = md5_hh(c, d, e, f, a[g + 9], 4, -640364487), f = md5_hh(f, c, d, e, a[g + 12], 11, -421815835), e = md5_hh(e, f, c, d, a[g + 15], 16, 530742520), d = md5_hh(d, e, f, c, a[g + 2], 23, -995338651), c = md5_ii(c, d, e, f, a[g + 0], 6, -198630844), f = md5_ii(f, c, d, e, a[g + 7], 10, 1126891415), e = md5_ii(e, f, c, d, a[g + 14], 15, -1416354905), d = md5_ii(d, e, f, c, a[g + 5], 21, -57434055), c = md5_ii(c, d, e, f, a[g + 12], 6, 1700485571), f = md5_ii(f, c, d, e, a[g + 3], 10, -1894986606), e = md5_ii(e, f, c, d, a[g + 10], 15, -1051523), d = md5_ii(d, e, f, c, a[g + 1], 21, -2054922799), c = md5_ii(c, d, e, f, a[g + 8], 6, 1873313359), f = md5_ii(f, c, d, e, a[g + 15], 10, -30611744), e = md5_ii(e, f, c, d, a[g + 6], 15, -1560198380), d = md5_ii(d, e, f, c, a[g + 13], 21, 1309151649), c = md5_ii(c, d, e, f, a[g + 4], 6, -145523070), f = md5_ii(f, c, d, e, a[g + 11], 10, -1120210379), e = md5_ii(e, f, c, d, a[g + 2], 15, 718787259), d = md5_ii(d, e, f, c, a[g + 9], 21, -343485551), c = safe_add(c, h), d = safe_add(d, i), e = safe_add(e, j), f = safe_add(f, k);
return Array(c, d, e, f)
}
function md5_cmn(a, b, c, d, e, f) {
return safe_add(bit_rol(safe_add(safe_add(b, a), safe_add(d, f)), e), c)
}
function md5_ff(a, b, c, d, e, f, g) {
return md5_cmn(b & c | ~b & d, a, b, e, f, g)
}
function md5_gg(a, b, c, d, e, f, g) {
return md5_cmn(b & d | c & ~d, a, b, e, f, g)
}
function md5_hh(a, b, c, d, e, f, g) {
return md5_cmn(b ^ c ^ d, a, b, e, f, g)
}
function md5_ii(a, b, c, d, e, f, g) {
return md5_cmn(c ^ (b | ~d), a, b, e, f, g)
}
function core_hmac_md5(a, b) {
var d, e, f, g, c = str2binl(a);
for (c.length > 16 && (c = core_md5(c, a.length * chrsz)), d = Array(16), e = Array(16), f = 0; 16 > f; f++) d[f] = 909522486 ^ c[f], e[f] = 1549556828 ^ c[f];
return g = core_md5(d.concat(str2binl(b)), 512 + b.length * chrsz), core_md5(e.concat(g), 640)
}
function safe_add(a, b) {
var c = (65535 & a) + (65535 & b),
d = (a >> 16) + (b >> 16) + (c >> 16);
return d << 16 | 65535 & c
}
function bit_rol(a, b) {
return a << b | a >>> 32 - b
}
function str2binl(a) {
var d, b = Array(),
c = (1 << chrsz) - 1;
for (d = 0; d < a.length * chrsz; d += chrsz) b[d >> 5] |= (a.charCodeAt(d / chrsz) & c) << d % 32;
return b
}
function binl2str(a) {
var d, b = "",
c = (1 << chrsz) - 1;
for (d = 0; d < 32 * a.length; d += chrsz) b += String.fromCharCode(a[d >> 5] >>> d % 32 & c);
return b
}
function binl2hex(a) {
var d, b = hexcase ? "0123456789ABCDEF" : "0123456789abcdef",
c = "";
for (d = 0; d < 4 * a.length; d++) c += b.charAt(15 & a[d >> 2] >> 8 * (d % 4) + 4) + b.charAt(15 & a[d >> 2] >> 8 * (d % 4));
return c
}
function binl2b64(a) {
var d, e, f, b = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",
c = "";
for (d = 0; d < 4 * a.length; d += 3)
for (e = (255 & a[d >> 2] >> 8 * (d % 4)) << 16 | (255 & a[d + 1 >> 2] >> 8 * ((d + 1) % 4)) << 8 | 255 & a[d + 2 >> 2] >> 8 * ((d + 2) % 4), f = 0; 4 > f; f++) c += 8 * d + 6 * f > 32 * a.length ? b64pad : b.charAt(63 & e >> 6 * (3 - f));
return c
}
function encode_param(a) {
var b = new Base64;
return b.encode(a)
}
function encode_secret() {
var b, a = appId;
for (b = 0; b < arguments.length; b++) a += arguments[b];
return a = a.replace(/\s/g, ""), hex_md5(a)
}
function decode_result(a) {
var b = new Base64;
return b.decode(b.decode(b.decode(a)))
}
var hexcase = 0,
b64pad = "",
chrsz = 8,
appId = "a01901d3caba1f362d69474674ce477f";
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,112 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/29 16:00
Desc: 日出和日落数据
https://www.timeanddate.com
"""
from io import StringIO
import pandas as pd
import requests
def sunrise_city_list() -> list:
"""
查询日出与日落数据的城市列表
https://www.timeanddate.com/astronomy/china
:return: 所有可以获取的数据的城市列表
:rtype: list
"""
url = "https://www.timeanddate.com/astronomy/china"
r = requests.get(url)
city_list = []
china_city_one_df = pd.read_html(StringIO(r.text))[1]
china_city_two_df = pd.read_html(StringIO(r.text))[2]
city_list.extend([item.lower() for item in china_city_one_df.iloc[:, 0].tolist()])
city_list.extend([item.lower() for item in china_city_one_df.iloc[:, 3].tolist()])
city_list.extend([item.lower() for item in china_city_one_df.iloc[:, 6].tolist()])
city_list.extend([item.lower() for item in china_city_two_df.iloc[:, 0].tolist()])
city_list.extend([item.lower() for item in china_city_two_df.iloc[:, 1].tolist()])
city_list.extend([item.lower() for item in china_city_two_df.iloc[:, 2].tolist()])
city_list.extend([item.lower() for item in china_city_two_df.iloc[:, 3].tolist()])
city_list.extend(
[item.lower() for item in china_city_two_df.iloc[:, 4].dropna().tolist()]
)
return city_list
def sunrise_daily(date: str = "20240428", city: str = "beijing") -> pd.DataFrame:
"""
每日日出日落数据
https://www.timeanddate.com/astronomy/china/shaoxing
:param date: 需要查询的日期, e.g., “20200428”
:type date: str
:param city: 需要查询的城市; 注意输入的格式, e.g., "北京", "上海"
:type city: str
:return: 返回指定日期指定地区的日出日落数据
:rtype: pandas.DataFrame
"""
import urllib3
urllib3.disable_warnings()
if city in sunrise_city_list():
year = date[:4]
month = date[4:6]
url = f"https://www.timeanddate.com/sun/china/{city}?month={month}&year={year}"
r = requests.get(url, verify=False)
table = pd.read_html(StringIO(r.text), header=2)[1]
month_df = table.iloc[:-1,]
day_df = month_df[
month_df.iloc[:, 0].astype(str).str.zfill(2) == date[6:]
].copy()
day_df.index = pd.to_datetime([date] * len(day_df), format="%Y%m%d")
day_df.reset_index(inplace=True)
day_df.rename(columns={"index": "date"}, inplace=True)
day_df["date"] = pd.to_datetime(day_df["date"]).dt.date
return day_df
else:
raise "请输入正确的城市名称"
def sunrise_monthly(date: str = "20240428", city: str = "beijing") -> pd.DataFrame:
"""
每个指定 date 所在月份的每日日出日落数据, 如果当前月份未到月底, 则以预测值填充
https://www.timeanddate.com/astronomy/china/shaoxing
:param date: 需要查询的日期, 这里用来指定 date 所在的月份; e.g., “20200428”
:type date: str
:param city: 需要查询的城市; 注意输入的格式, e.g., "北京", "上海"
:type city: str
:return: 指定 date 所在月份的每日日出日落数据
:rtype: pandas.DataFrame
"""
import urllib3
urllib3.disable_warnings()
if city in sunrise_city_list():
year = date[:4]
month = date[4:6]
url = f"https://www.timeanddate.com/sun/china/{city}?month={month}&year={year}"
r = requests.get(url)
table = pd.read_html(StringIO(r.text), header=2)[1]
month_df = table.iloc[:-1,].copy()
month_df.index = [date[:-2]] * len(month_df)
month_df.reset_index(inplace=True)
month_df.rename(
columns={
"index": "date",
},
inplace=True,
)
return month_df
else:
raise "请输入正确的城市名称"
if __name__ == "__main__":
sunrise_daily_df = sunrise_daily(date="20240428", city="beijing")
print(sunrise_daily_df)
sunrise_monthly_df = sunrise_monthly(date="20240428", city="beijing")
print(sunrise_monthly_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/11/12 14:51
Desc:
"""
@@ -0,0 +1,12 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/11/14 20:32
Desc: 学术板块配置文件
"""
# EPU
epu_home_url = "http://www.policyuncertainty.com/index.html"
# FF-Factor
ff_home_url = "http://mba.tuck.dartmouth.edu/pages/faculty/ken.french/data_library.html"
@@ -0,0 +1,60 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/1/20 22:00
Desc: 经济政策不确定性指数
https://www.policyuncertainty.com/index.html
"""
import pandas as pd
def article_epu_index(symbol: str = "China") -> pd.DataFrame:
"""
经济政策不确定性指数
https://www.policyuncertainty.com/index.html
:param symbol: 指定的国家名称, e.g. “China”
:type symbol: str
:return: 经济政策不确定性指数数据
:rtype: pandas.DataFrame
"""
# 切勿修改 http 否则会读取不到 csv 文件
if symbol == "China New":
symbol = "SCMP_China"
if symbol == "China":
symbol = "SCMP_China"
if symbol == "USA":
symbol = "US"
if symbol == "Hong Kong":
symbol = "HK"
epu_df = pd.read_excel(
io=f"http://www.policyuncertainty.com/media/{symbol}_EPU_Data_Annotated.xlsx",
engine="openpyxl",
)
return epu_df
if symbol in ["Germany", "France", "Italy"]: # 欧洲
symbol = "Europe"
if symbol == "South Korea":
symbol = "Korea"
if symbol == "Spain New":
symbol = "Spain"
if symbol in ["Ireland", "Chile", "Colombia", "Netherlands", "Singapore", "Sweden"]:
epu_df = pd.read_excel(
io=f"http://www.policyuncertainty.com/media/{symbol}_Policy_Uncertainty_Data.xlsx",
engine="openpyxl",
)
return epu_df
if symbol == "Greece":
epu_df = pd.read_excel(
io=f"http://www.policyuncertainty.com/media/FKT_{symbol}_Policy_Uncertainty_Data.xlsx",
engine="openpyxl",
)
return epu_df
url = f"http://www.policyuncertainty.com/media/{symbol}_Policy_Uncertainty_Data.csv"
epu_df = pd.read_csv(url)
return epu_df
if __name__ == "__main__":
article_epu_index_df = article_epu_index(symbol="China")
print(article_epu_index_df)
@@ -0,0 +1,166 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/1/20 22:30
Desc: FF-data-library
https://mba.tuck.dartmouth.edu/pages/faculty/ken.french/data_library.html
"""
from io import StringIO
import pandas as pd
import requests
from akshare.article.cons import ff_home_url
def article_ff_crr() -> pd.DataFrame:
"""
FF多因子模型
https://mba.tuck.dartmouth.edu/pages/faculty/ken.french/data_library.html
:return: FF多因子模型单一表格
:rtype: pandas.DataFrame
"""
res = requests.get(ff_home_url)
# first table
list_index = (
pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[2, :]
.index.tolist()
)
list_0 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[0, :]
.iloc[0]
.split(" ")
if item != ""
]
list_1 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[0, :]
.iloc[1]
.split(" ")
if item != ""
]
list_2 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[0, :]
.iloc[2]
.split(" ")
if item != ""
]
list_0.insert(0, "-")
list_1.insert(0, "-")
list_2.insert(0, "-")
temp_columns = (
pd.read_html(StringIO(res.text), header=0)[4]
.iloc[:, 0]
.str.split(" ", expand=True)
.T[0]
.dropna()
.tolist()
)
table_one = pd.DataFrame(
[list_0, list_1, list_2], index=list_index, columns=temp_columns
).T
# second table
list_index = (
pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[1, :]
.index.tolist()
)
list_0 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[1, :]
.iloc[0]
.split(" ")
if item != ""
]
list_1 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[1, :]
.iloc[1]
.split(" ")
if item != ""
]
list_2 = [
item
for item in pd.read_html(StringIO(res.text), header=0, index_col=0)[4]
.iloc[1, :]
.iloc[2]
.split(" ")
if item != ""
]
list_0.insert(0, "-")
list_1.insert(0, "-")
list_2.insert(0, "-")
temp_columns = (
pd.read_html(StringIO(res.text), header=0)[4]
.iloc[:, 0]
.str.split(" ", expand=True)
.T[1]
.dropna()
.tolist()
)
table_two = pd.DataFrame(
[list_0, list_1, list_2], index=list_index, columns=temp_columns
).T
# third table
df = pd.read_html(StringIO(res.text), header=0, index_col=0)[4].iloc[2, :]
name_list = (
pd.read_html(StringIO(res.text), header=0)[4]
.iloc[:, 0]
.str.split(r" ", expand=True)
.iloc[2, :]
.tolist()
)
value_list_0 = df.iloc[0].split(" ")
value_list_0.insert(0, "-")
value_list_0.insert(1, "-")
value_list_0.insert(8, "-")
value_list_0.insert(15, "-")
value_list_1 = df.iloc[1].split(" ")
value_list_1.insert(0, "-")
value_list_1.insert(1, "-")
value_list_1.insert(8, "-")
value_list_1.insert(15, "-")
value_list_2 = df.iloc[2].split(" ")
value_list_2.insert(0, "-")
value_list_2.insert(1, "-")
value_list_2.insert(8, "-")
value_list_2.insert(15, "-")
name_list.remove("Small Growth Big Value")
name_list.insert(5, "Small Growth")
name_list.insert(6, "Big Value")
temp_list = [item for item in name_list if "Portfolios" not in item]
temp_list.insert(0, "Fama/French Research Portfolios")
temp_list.insert(1, "Size and Book-to-Market Portfolios")
temp_list.insert(8, "Size and Operating Profitability Portfolios")
temp_list.insert(15, "Size and Investment Portfolios")
temp_df = pd.DataFrame([temp_list, value_list_0, value_list_1, value_list_2]).T
temp_df.index = temp_df.iloc[:, 0]
temp_df = temp_df.iloc[:, 1:]
# concat
all_df = pd.DataFrame()
all_df = pd.concat([all_df, table_one])
all_df = pd.concat([all_df, table_two])
temp_df.columns = table_two.columns
all_df = pd.concat([all_df, temp_df])
all_df.reset_index(inplace=True)
all_df.rename(columns={"index": "item"}, inplace=True)
return all_df
if __name__ == "__main__":
article_ff_crr_df = article_ff_crr()
print(article_ff_crr_df)
@@ -0,0 +1,46 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2020/4/10 19:58
Desc: Economic Research from Federal Reserve Bank of St. Louis
https://research.stlouisfed.org/econ/mccracken/fred-databases/
FRED-MD and FRED-QD are large macroeconomic databases designed for the empirical analysis of “big data.” The datasets of monthly and quarterly observations mimic the coverage of datasets already used in the literature, but they add three appealing features. They are updated in real-time through the FRED database. They are publicly accessible, facilitating the replication of empirical work. And they relieve the researcher of the task of incorporating data changes and revisions (a task accomplished by the data desk at the Federal Reserve Bank of St. Louis).
"""
import pandas as pd
def fred_md(date: str = "2020-01") -> pd.DataFrame:
"""
The accompanying paper shows that factors extracted from the FRED-MD dataset share the same predictive content as those based on the various vintages of the so-called Stock-Watson data. In addition, it suggests that diffusion indexes constructed as the partial sum of the factor estimates can potentially be useful for the study of business cycle chronology.
:param date: e.g., "2020-03"; from "2015-01" to now
:type date: str
:return: Monthly Data
:rtype: pandas.DataFrame
"""
url = (
f"https://s3.amazonaws.com/files.fred.stlouisfed.org/fred-md/monthly/{date}.csv"
)
temp_df = pd.read_csv(url)
return temp_df
def fred_qd(date: str = "2020-01") -> pd.DataFrame:
"""
FRED-QD is a quarterly frequency companion to FRED-MD. It is designed to emulate the dataset used in "Disentangling the Channels of the 2007-2009 Recession" by Stock and Watson (2012, NBER WP No. 18094) but also contains several additional series. Comments or suggestions are welcome.
:param date: e.g., "2020-03"; from "2015-01" to now
:type date: str
:return: Quarterly Data
:rtype: pandas.DataFrame
"""
url = f"https://s3.amazonaws.com/files.fred.stlouisfed.org/fred-md/quarterly/{date}.csv"
temp_df = pd.read_csv(url)
return temp_df
if __name__ == "__main__":
fred_md_df = fred_md(date="2023-03")
print(fred_md_df)
fred_qd_df = fred_qd(date="2023-03")
print(fred_qd_df)
@@ -0,0 +1,191 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/1/20 20:51
Desc: 修大成主页-Risk Lab-Realized Volatility; Oxford-Man Institute of Quantitative Finance Realized Library
"""
import json
import pandas as pd
import requests
import urllib3
from bs4 import BeautifulSoup
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
def article_oman_rv(symbol: str = "FTSE", index: str = "rk_th2") -> pd.DataFrame:
"""
Oxford-Man Institute of Quantitative Finance Realized Library 的数据
:param symbol: str ['AEX', 'AORD', 'BFX', 'BSESN', 'BVLG', 'BVSP', 'DJI', 'FCHI', 'FTMIB', 'FTSE', 'GDAXI', 'GSPTSE', 'HSI', 'IBEX', 'IXIC', 'KS11', 'KSE', 'MXX', 'N225', 'NSEI', 'OMXC20', 'OMXHPI', 'OMXSPI', 'OSEAX', 'RUT', 'SMSI', 'SPX', 'SSEC', 'SSMI', 'STI', 'STOXX50E']
:param index: str 指标 ['medrv', 'rk_twoscale', 'bv', 'rv10', 'rv5', 'rk_th2', 'rv10_ss', 'rsv', 'rv5_ss', 'bv_ss', 'rk_parzen', 'rsv_ss']
:return: pandas.DataFrame
The Oxford-Man Institute's "realised library" contains daily non-parametric measures of how volatility financial assets or indexes were in the past. Each day's volatility measure depends solely on financial data from that day. They are driven by the use of the latest innovations in econometric modelling and theory to design them, while we draw our high frequency data from the Thomson Reuters DataScope Tick History database. Realised measures are not volatility forecasts. However, some researchers use these measures as an input into forecasting models. The aim of this line of research is to make financial markets more transparent by exposing how volatility changes through time.
This Library is used as the basis of some of our own research, which effects its scope, and is made available here to encourage the more widespread exploitation of these methods. It is given 'as is' and solely for informational purposes, please read the disclaimer.
The volatility data can be visually explored. We make the complete up-to-date dataset available for download. Lists of assets covered and realized measures available are also available.
| Symbol | Name | Earliest Available | Latest Available |
|-----------|-------------------------------------------|--------------------|-------------------|
| .AEX | AEX index | January 03, 2000 | November 28, 2019 |
| .AORD | All Ordinaries | January 04, 2000 | November 28, 2019 |
| .BFX | Bell 20 Index | January 03, 2000 | November 28, 2019 |
| .BSESN | S&P BSE Sensex | January 03, 2000 | November 28, 2019 |
| .BVLG | PSI All-Share Index | October 15, 2012 | November 28, 2019 |
| .BVSP | BVSP BOVESPA Index | January 03, 2000 | November 28, 2019 |
| .DJI | Dow Jones Industrial Average | January 03, 2000 | November 27, 2019 |
| .FCHI | CAC 40 | January 03, 2000 | November 28, 2019 |
| .FTMIB | FTSE MIB | June 01, 2009 | November 28, 2019 |
| .FTSE | FTSE 100 | January 04, 2000 | November 28, 2019 |
| .GDAXI | DAX | January 03, 2000 | November 28, 2019 |
| .GSPTSE | S&P/TSX Composite index | May 02, 2002 | November 28, 2019 |
| .HSI | HANG SENG Index | January 03, 2000 | November 28, 2019 |
| .IBEX | IBEX 35 Index | January 03, 2000 | November 28, 2019 |
| .IXIC | Nasdaq 100 | January 03, 2000 | November 27, 2019 |
| .KS11 | Korea Composite Stock Price Index (KOSPI) | January 04, 2000 | November 28, 2019 |
| .KSE | Karachi SE 100 Index | January 03, 2000 | November 28, 2019 |
| .MXX | IPC Mexico | January 03, 2000 | November 28, 2019 |
| .N225 | Nikkei 225 | February 02, 2000 | November 28, 2019 |
| .NSEI | NIFTY 50 | January 03, 2000 | November 28, 2019 |
| .OMXC20 | OMX Copenhagen 20 Index | October 03, 2005 | November 28, 2019 |
| .OMXHPI | OMX Helsinki All Share Index | October 03, 2005 | November 28, 2019 |
| .OMXSPI | OMX Stockholm All Share Index | October 03, 2005 | November 28, 2019 |
| .OSEAX | Oslo Exchange All-share Index | September 03, 2001 | November 28, 2019 |
| .RUT | Russel 2000 | January 03, 2000 | November 27, 2019 |
| .SMSI | Madrid General Index | July 04, 2005 | November 28, 2019 |
| .SPX | S&P 500 Index | January 03, 2000 | November 27, 2019 |
| .SSEC | Shanghai Composite Index | January 04, 2000 | November 28, 2019 |
| .SSMI | Swiss Stock Market Index | January 04, 2000 | November 28, 2019 |
| .STI | Straits Times Index | January 03, 2000 | November 28, 2019 |
| .STOXX50E | EURO STOXX 50 | January 03, 2000 | November 28, 2019 |
"""
url = "https://realized.oxford-man.ox.ac.uk/theme/js/visualization-data.js?20191111113154"
res = requests.get(url)
soup = BeautifulSoup(res.text, "lxml")
soup_text = soup.find("p").get_text()
data_json = json.loads(soup_text[soup_text.find("{") : soup_text.rfind("};") + 1])
date_list = data_json[f".{symbol}"]["dates"]
temp_df = pd.DataFrame([date_list, data_json[f".{symbol}"][index]["data"]]).T
temp_df.index = pd.to_datetime(temp_df.iloc[:, 0], unit="ms")
temp_df = temp_df.iloc[:, 1]
temp_df.index.name = "date"
temp_df.name = f"{symbol}-{index}"
return temp_df
def article_oman_rv_short(symbol: str = "FTSE") -> pd.DataFrame:
"""
Oxford-Man Institute of Quantitative Finance Realized Library 的数据
:param symbol: str FTSE: FTSE 100, GDAXI: DAX, RUT: Russel 2000, SPX: S&P 500 Index, STOXX50E: EURO STOXX 50, SSEC: Shanghai Composite Index, N225: Nikkei 225
:return: pandas.DataFrame
The Oxford-Man Institute's "realised library" contains daily non-parametric measures of how volatility financial assets or indexes were in the past. Each day's volatility measure depends solely on financial data from that day. They are driven by the use of the latest innovations in econometric modelling and theory to design them, while we draw our high frequency data from the Thomson Reuters DataScope Tick History database. Realised measures are not volatility forecasts. However, some researchers use these measures as an input into forecasting models. The aim of this line of research is to make financial markets more transparent by exposing how volatility changes through time.
This Library is used as the basis of some of our own research, which effects its scope, and is made available here to encourage the more widespread exploitation of these methods. It is given 'as is' and solely for informational purposes, please read the disclaimer.
The volatility data can be visually explored. We make the complete up-to-date dataset available for download. Lists of assets covered and realized measures available are also available.
"""
url = "https://realized.oxford-man.ox.ac.uk/theme/js/front-page-chart.js"
headers = {
"Accept": "*/*",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Host": "realized.oxford-man.ox.ac.uk",
"Pragma": "no-cache",
"Referer": "https://realized.oxford-man.ox.ac.uk/?from=groupmessage&isappinstalled=0",
"Sec-Fetch-Mode": "no-cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.97 Safari/537.36",
}
res = requests.get(url, headers=headers, verify=False)
soup = BeautifulSoup(res.text, "lxml")
soup_text = soup.find("p").get_text()
data_json = json.loads(soup_text[soup_text.find("{") : soup_text.rfind("}") + 1])
temp_df = pd.DataFrame(data_json[f".{symbol}"]["data"])
temp_df.index = pd.to_datetime(temp_df.iloc[:, 0], unit="ms")
temp_df = temp_df.iloc[:, 1]
temp_df.index.name = "date"
temp_df.name = f"{symbol}"
return temp_df
def article_rlab_rv(symbol: str = "39693") -> pd.DataFrame:
"""
修大成主页-Risk Lab-Realized Volatility
:param symbol: str 股票代码
:return: pandas.DataFrame
1996-01-02 0.000000
1996-01-04 0.000000
1996-01-05 0.000000
1996-01-09 0.000000
1996-01-10 0.000000
...
2019-11-04 0.175107
2019-11-05 0.185112
2019-11-06 0.210373
2019-11-07 0.240808
2019-11-08 0.199549
Name: RV, Length: 5810, dtype: float64
Website
https://dachxiu.chicagobooth.edu/
Objective
We provide up-to-date daily annualized realized volatilities for individual stocks, ETFs, and future contracts, which are estimated from high-frequency data. We are in the process of incorporating equities from global markets.
Data
We collect trades at their highest frequencies available (up to every millisecond for US equities after 2007), and clean them using the prevalent national best bid and offer (NBBO) that are available up to every second. The mid-quotes are calculated based on the NBBOs, so their highest sampling frequencies are also up to every second.
Methodology
We provide quasi-maximum likelihood estimates of volatility (QMLE) based on moving-average models MA(q), using non-zero returns of transaction prices (or mid-quotes if available) sampled up to their highest frequency available, for days with at least 12 observations. We select the best model (q) using Akaike Information Criterion (AIC). For comparison, we report realized volatility (RV) estimates using 5-minute and 15-minute subsampled returns.
References
1. “When Moving-Average Models Meet High-Frequency Data: Uniform Inference on Volatility”, by Rui Da and Dacheng Xiu. 2017.
2. “Quasi-Maximum Likelihood Estimation of Volatility with High Frequency Data”, by Dacheng Xiu. Journal of Econometrics, 159 (2010), 235-250.
3. “How Often to Sample A Continuous-time Process in the Presence of Market Microstructure Noise”, by Yacine Aït-Sahalia, Per Mykland, and Lan Zhang. Review of Financial Studies, 18 (2005), 351416.
4. “The Distribution of Exchange Rate Volatility”, by Torben Andersen, Tim Bollerslev, Francis X. Diebold, and Paul Labys. Journal of the American Statistical Association, 96 (2001), 42-55.
5. “Econometric Analysis of Realized Volatility and Its Use in Estimating Stochastic Volatility Models”, by Ole E BarndorffNielsen and Neil Shephard. Journal of the Royal Statistical Society: Series B, 64 (2002), 253-280.
"""
print("由于服务器在国外, 请稍后, 如果访问失败, 请使用代理工具")
url = "https://dachxiu.chicagobooth.edu/data.php"
payload = {"ticker": symbol}
res = requests.get(url, params=payload, verify=False)
soup = BeautifulSoup(res.text, "lxml")
title_fore = (
pd.DataFrame(soup.find("p").get_text().split(symbol)).iloc[0, 0].strip()
)
title_list = (
pd.DataFrame(soup.find("p").get_text().split(symbol))
.iloc[1, 0]
.strip()
.split("\n")
)
title_list.insert(0, title_fore)
temp_df = pd.DataFrame(soup.find("p").get_text().split(symbol)).iloc[2:, :]
temp_df = temp_df.iloc[:, 0].str.split(" ", expand=True)
temp_df = temp_df.iloc[:, 1:]
temp_df.iloc[:, -1] = temp_df.iloc[:, -1].str.replace(r"\n", "")
temp_df.reset_index(inplace=True)
temp_df.index = pd.to_datetime(temp_df.iloc[:, 1], format="%Y%m%d", errors="coerce")
temp_df = temp_df.iloc[:, 1:]
data_se = temp_df.iloc[:, 1]
data_se.name = "RV"
temp_df = data_se.astype("float", errors="ignore")
temp_df.index.name = "date"
return temp_df
if __name__ == "__main__":
article_rlab_rv_df = article_rlab_rv(symbol="39693")
print(article_rlab_rv_df)
article_oman_rv_short_df = article_oman_rv_short(symbol="FTSE")
print(article_oman_rv_short_df)
article_oman_rv_df = article_oman_rv(symbol="FTSE", index="rk_th2")
print(article_oman_rv_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/11/7 14:06
Desc:
"""
@@ -0,0 +1,189 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/2/4 23:00
Desc: 中国银行保险监督管理委员会-首页-政务信息-行政处罚-银保监分局本级-XXXX行政处罚信息公开表
https://www.nfra.gov.cn/cn/view/pages/ItemList.html?itemPId=923&itemId=4115&itemUrl=ItemListRightList.html&itemName=%E9%93%B6%E4%BF%9D%E7%9B%91%E5%88%86%E5%B1%80%E6%9C%AC%E7%BA%A7&itemsubPId=931&itemsubPName=%E8%A1%8C%E6%94%BF%E5%A4%84%E7%BD%9A#2
提取 具体页面 html 页面的 json 接口
https://www.nfra.gov.cn/cn/static/data/DocInfo/SelectByDocId/data_docId=881446.json
2020 新接口
"""
import warnings
from io import StringIO
import pandas as pd
import requests
from tqdm import tqdm
from akshare.bank.cons import cbirc_headers_without_cookie_2020
def bank_fjcf_total_num(item: str = "分局本级") -> int:
"""
首页-政务信息-行政处罚-银保监分局本级 总页数
https://www.nfra.gov.cn/cn/view/pages/ItemList.html?itemPId=923&itemId=4115&itemUrl=ItemListRightList.html&itemName=%E9%93%B6%E4%BF%9D%E7%9B%91%E5%88%86%E5%B1%80%E6%9C%AC%E7%BA%A7&itemsubPId=931
:param item: choice of {"机关", "本级", "分局本级"}
:type item: str
:return: 总页数
:rtype: int
"""
item_id_list = {
"机关": "4113",
"本级": "4114",
"分局本级": "4115",
}
cbirc_headers = cbirc_headers_without_cookie_2020.copy()
main_url = "https://www.nfra.gov.cn/cbircweb/DocInfo/SelectDocByItemIdAndChild"
params = {
"itemId": item_id_list[item],
"pageSize": "18",
"pageIndex": "1",
}
res = requests.get(main_url, params=params, headers=cbirc_headers)
return int(res.json()["data"]["total"])
def bank_fjcf_total_page(item: str = "分局本级", begin: int = 1) -> int:
"""
获取首页-政务信息-行政处罚-银保监分局本级的总页数
https://www.nfra.gov.cn/cn/view/pages/ItemList.html?itemPId=923&itemId=4115&itemUrl=ItemListRightList.html&itemName=%E9%93%B6%E4%BF%9D%E7%9B%91%E5%88%86%E5%B1%80%E6%9C%AC%E7%BA%A7&itemsubPId=931
:param item: choice of {"机关", "本级", "分局本级"}
:type item: str
:param begin: 开始页数
:type begin: str
:return: 总页数
:rtype: int
"""
item_id_list = {
"机关": "4113",
"本级": "4114",
"分局本级": "4115",
}
cbirc_headers = cbirc_headers_without_cookie_2020.copy()
main_url = "https://www.nfra.gov.cn/cbircweb/DocInfo/SelectDocByItemIdAndChild"
params = {
"itemId": item_id_list[item],
"pageSize": "18",
"pageIndex": str(begin),
}
res = requests.get(main_url, params=params, headers=cbirc_headers)
if res.json()["data"]["total"] / 18 > int(res.json()["data"]["total"] / 18):
total_page = int(res.json()["data"]["total"] / 18) + 1
return total_page
def bank_fjcf_page_url(
page: int = 5, item: str = "分局本级", begin: int = 1
) -> pd.DataFrame:
"""
获取 首页-政务信息-行政处罚-银保监分局本级-每一页的 json 数据
:param page: 需要获取前 page 页的内容, 总页数请通过 ak.bank_fjcf_total_page() 获取
:type page: int
:param item: choice of {"机关", "本级", "分局本级"}
:type item: str
:param begin: 开始页数
:type begin: str
:return: 需要的字段
:rtype: pandas.DataFrame
"""
item_id_list = {
"机关": "4113",
"本级": "4114",
"分局本级": "4115",
}
cbirc_headers = cbirc_headers_without_cookie_2020.copy()
main_url = "https://www.nfra.gov.cn/cbircweb/DocInfo/SelectDocByItemIdAndChild"
temp_df = pd.DataFrame()
for i_page in tqdm(range(begin, page + begin), leave=False):
params = {
"itemId": item_id_list[item],
"pageSize": "18",
"pageIndex": str(i_page),
}
res = requests.get(main_url, params=params, headers=cbirc_headers)
temp_df = pd.concat([temp_df, pd.DataFrame(res.json()["data"]["rows"])])
return temp_df[
["docId", "docSubtitle", "publishDate", "docFileUrl", "docTitle", "generaltype"]
]
def bank_fjcf_table_detail(
page: int = 5, item: str = "分局本级", begin: int = 1
) -> pd.DataFrame:
"""
获取 首页-政务信息-行政处罚-银保监分局本级-XXXX行政处罚信息公开表 数据
:param page: 需要获取前 page 页的内容, 总页数请通过 ak.bank_fjcf_total_page() 获取
:type page: int
:param item: choice of {"机关", "本级", "分局本级"}
:type item: str
:param begin: 开始页面
:type begin: int
:return: 返回所有行政处罚信息公开表的集合, 按第一页到最后一页的顺序排列
:rtype: pandas.DataFrame
"""
id_list = bank_fjcf_page_url(page=page, item=item, begin=begin)["docId"]
big_df = pd.DataFrame()
for item in id_list:
url = f"https://www.nfra.gov.cn/cn/static/data/DocInfo/SelectByDocId/data_docId={item}.json"
res = requests.get(url)
try:
table_list = pd.read_html(StringIO(res.json()["data"]["docClob"]))[0]
if table_list.shape[1] == 2:
table_list = table_list.iloc[:, 1].values.tolist()
else:
table_list = table_list.iloc[:, 3:].values.tolist()
# 部分旧表缺少字段,所以填充
if len(table_list) == 7:
table_list.insert(2, pd.NA)
table_list.insert(3, pd.NA)
table_list.insert(4, pd.NA)
elif len(table_list) == 8:
table_list.insert(1, pd.NA)
table_list.insert(2, pd.NA)
elif len(table_list) == 9:
table_list.insert(2, pd.NA)
elif len(table_list) == 11:
table_list = table_list[2:]
table_list.insert(2, pd.NA)
else:
print(
f"{item} 异常,请通过 https://www.nfra.gov.cn/cn/view/pages/ItemDetail.html?docId={item} 查看"
)
continue
# 部分会变成嵌套列表, 这里还原
table_list = [
item[0] if isinstance(item, list) else item for item in table_list
]
table_list.append(str(item))
table_list.append(res.json()["data"]["publishDate"])
table_df = pd.DataFrame(table_list)
table_df.columns = ["内容"]
big_df = pd.concat(objs=[big_df, table_df.T], ignore_index=True)
# 解决有些页面缺少字段的问题, 都放到 try 里面
except: # noqa: E722
warnings.warn(f"{item} 不是表格型数据,将跳过采集")
continue
if big_df.empty:
return pd.DataFrame()
big_df.columns = [
"行政处罚决定书文号",
"姓名",
"单位", # 20200108 新增
"单位名称",
"主要负责人姓名",
"主要违法违规事实(案由)",
"行政处罚依据",
"行政处罚决定",
"作出处罚决定的机关名称",
"作出处罚决定的日期",
"处罚ID",
"处罚公布日期",
]
return big_df
if __name__ == "__main__":
bank_fjcf_table_detail_df = bank_fjcf_table_detail(page=1, item="机关", begin=1)
print(bank_fjcf_table_detail_df)
@@ -0,0 +1,32 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/4/3 21:06
Desc: 银保监会配置文件
"""
cbirc_headers_without_cookie_2020 = {
"Accept": "*/*",
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Host": "www.nfra.gov.cn",
"Pragma": "no-cache",
"Referer": "http://www.nfra.gov.cn/cn/view/pages/ItemList.html?itemPId=923&itemId=4115&itemUrl=ItemListRightList.html&itemName=%E9%93%B6%E4%BF%9D%E7%9B%91%E5%88%86%E5%B1%80%E6%9C%AC%E7%BA%A7&itemsubPId=931&itemsubPName=%E8%A1%8C%E6%94%BF%E5%A4%84%E7%BD%9A",
"X-Requested-With": "XMLHttpRequest",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.97 Safari/537.36",
}
cbirc_headers_without_cookie_2019 = {
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3",
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Host": "www.nfra.gov.cn",
"Pragma": "no-cache",
"Referer": "http://www.nfra.gov.cn/cn/list/9103/910305/ybjjcf/1.html",
"Upgrade-Insecure-Requests": "1",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.97 Safari/537.36",
}
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/9/30 13:58
Desc:
"""
@@ -0,0 +1,234 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/4/5 17:30
Desc: 东方财富网-行情中心-债券市场-质押式回购
https://quote.eastmoney.com/center/gridlist.html#bond_sz_buyback
"""
import pandas as pd
import requests
def bond_sh_buy_back_em() -> pd.DataFrame:
"""
东方财富网-行情中心-债券市场-上证质押式回购
https://quote.eastmoney.com/center/gridlist.html#bond_sh_buyback
:return: 上证质押式回购
:rtype: pandas.DataFrame
"""
url = "https://push2.eastmoney.com/api/qt/clist/get"
params = {
"np": "1",
"fltt": "1",
"invt": "2",
"fs": "m:1+b:MK0356",
"fields": "f12,f13,f14,f1,f2,f4,f3,f152,f17,f18,f15,f16,f5,f6",
"fid": "f6",
"pn": "1",
"pz": "20",
"po": "1",
"dect": "1",
"wbp2u": "|0|0|0|web",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["diff"])
temp_df.reset_index(inplace=True)
temp_df["index"] = temp_df["index"] + 1
temp_df.rename(
columns={
"index": "序号",
"f2": "最新价",
"f3": "涨跌幅",
"f4": "涨跌额",
"f5": "成交量",
"f6": "成交额",
"f12": "代码",
"f14": "名称",
"f15": "最高",
"f16": "最低",
"f17": "今开",
"f18": "昨收",
},
inplace=True,
)
temp_df = temp_df[
[
"序号",
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"今开",
"最高",
"最低",
"昨收",
"成交量",
"成交额",
]
]
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce") / 1000
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce") / 100
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce") / 1000
temp_df["今开"] = pd.to_numeric(temp_df["今开"], errors="coerce") / 1000
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce") / 1000
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce") / 1000
temp_df["昨收"] = pd.to_numeric(temp_df["昨收"], errors="coerce") / 1000
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
return temp_df
def bond_sz_buy_back_em() -> pd.DataFrame:
"""
东方财富网-行情中心-债券市场-深证质押式回购
https://quote.eastmoney.com/center/gridlist.html#bond_sz_buyback
:return: 深证质押式回购
:rtype: pandas.DataFrame
"""
url = "https://push2.eastmoney.com/api/qt/clist/get"
params = {
"np": "1",
"fltt": "1",
"invt": "2",
"fs": "m:0+b:MK0356",
"fields": "f12,f13,f14,f1,f2,f4,f3,f152,f17,f18,f15,f16,f5,f6",
"fid": "f6",
"pn": "1",
"pz": "20",
"po": "1",
"dect": "1",
"wbp2u": "|0|0|0|web",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["diff"])
temp_df.reset_index(inplace=True)
temp_df["index"] = temp_df["index"] + 1
temp_df.rename(
columns={
"index": "序号",
"f2": "最新价",
"f3": "涨跌幅",
"f4": "涨跌额",
"f5": "成交量",
"f6": "成交额",
"f12": "代码",
"f14": "名称",
"f15": "最高",
"f16": "最低",
"f17": "今开",
"f18": "昨收",
},
inplace=True,
)
temp_df = temp_df[
[
"序号",
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"今开",
"最高",
"最低",
"昨收",
"成交量",
"成交额",
]
]
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce") / 1000
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce") / 100
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce") / 1000
temp_df["今开"] = pd.to_numeric(temp_df["今开"], errors="coerce") / 1000
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce") / 1000
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce") / 1000
temp_df["昨收"] = pd.to_numeric(temp_df["昨收"], errors="coerce") / 1000
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
return temp_df
def bond_buy_back_hist_em(symbol: str = "204001"):
"""
东方财富网-行情中心-债券市场-质押式回购-历史数据
https://quote.eastmoney.com/center/gridlist.html#bond_sh_buyback
:param symbol: 质押式回购代码
:type symbol: str
:return: 历史数据
:rtype: pandas.DataFrame
"""
if symbol.startswith("1"):
market_id = "0"
else:
market_id = "1"
url = "https://push2his.eastmoney.com/api/qt/stock/kline/get"
params = {
"secid": f"{market_id}.{symbol}",
"klt": "101",
"fqt": "1",
"lmt": "10000",
"end": "20500000",
"iscca": "1",
"fields1": "f1,f2,f3,f4,f5,f6,f7,f8",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58,f59,f60,f61,f62,f63,f64",
"forcect": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame([item.split(",") for item in data_json["data"]["klines"]])
temp_df.columns = [
"日期",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"-",
"-",
"-",
"-",
"-",
"-",
"-",
]
temp_df = temp_df[
[
"日期",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
]
]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
return temp_df
if __name__ == "__main__":
bond_sh_buy_back_em_df = bond_sh_buy_back_em()
print(bond_sh_buy_back_em_df)
bond_sz_buy_back_em_df = bond_sz_buy_back_em()
print(bond_sz_buy_back_em_df)
bond_buy_back_hist_em_df = bond_buy_back_hist_em(symbol="204001")
print(bond_buy_back_hist_em_df)
bond_buy_back_hist_em_df = bond_buy_back_hist_em(symbol="131810")
print(bond_buy_back_hist_em_df)
@@ -0,0 +1,58 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2023/9/12 16:50
Desc: 新浪财经-债券-可转债
https://money.finance.sina.com.cn/bond/info/sz128039.html
"""
from io import StringIO
import pandas as pd
import requests
def bond_cb_profile_sina(symbol: str = "sz128039") -> pd.DataFrame:
"""
新浪财经-债券-可转债-详情资料
https://money.finance.sina.com.cn/bond/info/sz128039.html
:param symbol: 带市场标识的转债代码
:type symbol: str
:return: 可转债-详情资料
:rtype: pandas.DataFrame
"""
url = f"https://money.finance.sina.com.cn/bond/info/{symbol}.html"
r = requests.get(url)
temp_df = pd.read_html(StringIO(r.text))[0]
temp_df.columns = ["item", "value"]
return temp_df
def bond_cb_summary_sina(symbol: str = "sh155255") -> pd.DataFrame:
"""
新浪财经-债券-可转债-债券概况
https://money.finance.sina.com.cn/bond/quotes/sh155255.html
:param symbol: 带市场标识的转债代码
:type symbol: str
:return: 可转债-债券概况
:rtype: pandas.DataFrame
"""
url = f"https://money.finance.sina.com.cn/bond/quotes/{symbol}.html"
r = requests.get(url)
temp_df = pd.read_html(StringIO(r.text))[10]
part1 = temp_df.iloc[:, 0:2].copy()
part1.columns = ["item", "value"]
part2 = temp_df.iloc[:, 2:4].copy()
part2.columns = ["item", "value"]
part3 = temp_df.iloc[:, 4:6].copy()
part3.columns = ["item", "value"]
big_df = pd.concat(objs=[part1, part2, part3], ignore_index=True)
return big_df
if __name__ == "__main__":
bond_cb_profile_sina_df = bond_cb_profile_sina(symbol="sz128039")
print(bond_cb_profile_sina_df)
bond_cb_summary_sina_df = bond_cb_summary_sina(symbol="sh155255")
print(bond_cb_summary_sina_df)
@@ -0,0 +1,93 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2024/8/14 11:30
Desc: 同花顺-数据中心-可转债
https://data.10jqka.com.cn/ipo/bond/
"""
import pandas as pd
import requests
def bond_zh_cov_info_ths() -> pd.DataFrame:
"""
同花顺-数据中心-可转债
https://data.10jqka.com.cn/ipo/bond/
:return: 可转债行情
:rtype: pandas.DataFrame
"""
url = "https://data.10jqka.com.cn/ipo/kzz/"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/89.0.4389.90 Safari/537.36",
}
r = requests.get(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["list"])
temp_df.rename(
columns={
"sub_date": "申购日期",
"bond_code": "债券代码",
"bond_name": "债券简称",
"code": "正股代码",
"name": "正股简称",
"sub_code": "申购代码",
"share_code": "原股东配售码",
"sign_date": "中签公布日",
"plan_total": "计划发行量",
"issue_total": "实际发行量",
"issue_price": "-",
"success_rate": "中签率",
"listing_date": "上市日期",
"expire_date": "到期时间",
"price": "转股价格",
"quota": "每股获配额",
"number": "中签号",
"market_id": "-",
"stock_market_id": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"申购日期",
"申购代码",
"原股东配售码",
"每股获配额",
"计划发行量",
"实际发行量",
"中签公布日",
"中签号",
"上市日期",
"正股代码",
"正股简称",
"转股价格",
"到期时间",
"中签率",
]
]
temp_df["申购日期"] = pd.to_datetime(
temp_df["申购日期"], format="%Y-%m-%d", errors="coerce"
).dt.date
temp_df["中签公布日"] = pd.to_datetime(
temp_df["中签公布日"], format="%Y-%m-%d", errors="coerce"
).dt.date
temp_df["上市日期"] = pd.to_datetime(
temp_df["上市日期"], format="%Y-%m-%d", errors="coerce"
).dt.date
temp_df["到期时间"] = pd.to_datetime(
temp_df["到期时间"], format="%Y-%m-%d", errors="coerce"
).dt.date
temp_df["每股获配额"] = pd.to_numeric(temp_df["每股获配额"], errors="coerce")
temp_df["计划发行量"] = pd.to_numeric(temp_df["计划发行量"], errors="coerce")
temp_df["实际发行量"] = pd.to_numeric(temp_df["实际发行量"], errors="coerce")
temp_df["转股价格"] = pd.to_numeric(temp_df["转股价格"], errors="coerce")
return temp_df
if __name__ == "__main__":
bond_zh_cov_info_ths_df = bond_zh_cov_info_ths()
print(bond_zh_cov_info_ths_df)
@@ -0,0 +1,296 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2026/4/10 19:00
Desc: 中国债券信息网-中债指数-中债指数族系-总指数-综合类指数
"""
import pandas as pd
import requests
from akshare.bond.cons import INDEX_MAPPING, PERIOD_MAPPING, INDICATOR_MAPPING
def bond_available_index_cbond():
"""
中国债券信息网-中债指数-中债指数族系 当中, 非指定期限部分
https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQueryResult
:return: 可选项列表
:rtype: list
"""
temp_df = pd.DataFrame(list(INDEX_MAPPING.keys()))
temp_df.reset_index(inplace=True)
temp_df['index'] = temp_df['index'] + 1
temp_df.columns = ['index', 'value']
return temp_df
def bond_index_general_cbond(
index_category: str = "新综合指数", indicator: str = "全价", period: str = "总值"
):
"""
中国债券信息网-中债指数-中债指数族系
https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQueryResult
:param index_category: see result of available_bond_index()
:type index_category: str
:param indicator: choice of {"全价", "净价", "财富", "平均市值法久期", "平均现金流法久期", "平均市值法凸性", "平均现金流法凸性", "平均现金流法到期收益率", "平均市值法到期收益率", "平均基点价值", "平均待偿期", "平均派息率", "指数上日总市值", "财富指数涨跌幅", "全价指数涨跌幅", "净价指数涨跌幅", "现券结算量"}
:type indicator: str
:param period: choice of {"总值", "1年以下", "1-3年", "3-5年", "5-7年", "7-10年", "10年以上", "0-3个月", "3-6个月", "6-9个月", "9-12个月", "0-6个月", "6-12个月"}
:type period: str
:return: 指定指数的指定指标的指定期限分段数据
:rtype: pandas.DataFrame
"""
url = "https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQueryResult"
params = {
"indexid": INDEX_MAPPING[index_category],
"qxlxt": PERIOD_MAPPING[period],
"ltcslx": "",
"zslxt": INDICATOR_MAPPING[indicator],
"zslxt1": INDICATOR_MAPPING[indicator],
"lx": "1",
"locale": "zh_CN",
}
r = requests.post(url, params=params)
raw_json = r.json()
key_col_map = {f"{INDICATOR_MAPPING[indicator]}_{p_code}": freq_col for p_code, freq_col in
raw_json['dqcName'].items()}
data_json = {key: raw_json[key] for key in key_col_map}
temp_df = pd.DataFrame.from_dict(data_json, orient="columns")
temp_df.index = pd.to_datetime(pd.to_numeric(temp_df.index), unit="ms", utc=True).tz_convert("Asia/Shanghai")
temp_df.index.name = "date"
temp_df.rename(columns=key_col_map, inplace=True)
temp_df.reset_index(inplace=True)
temp_df.columns = ["date", "value"]
temp_df['date'] = pd.to_datetime(temp_df['date'], errors="coerce").dt.date
return temp_df
def bond_treasury_index_cbond(
indicator: str = "财富", period: str = "5Y"
) -> pd.DataFrame:
"""
中国债券信息网-中债指数-中债指数族系-总指数-综合类指数-中债-国债指数
https://yield.chinabond.com.cn/cbweb-mn/indices/single_index_query
:param indicator: choice of {"全价", "净价", "财富"}
:type indicator: str
:param period: choice of {'0-1Y', '0-3Y', '0-5Y', '0-10Y', '1-3Y', '1-5Y', '1-10Y',
'3-5Y', '5Y', '7Y', '7-10Y', '10Y', '30Y'}
:type period: str
:return: 国债指数
:rtype: pandas.DataFrame
"""
mapping = {
"0-1Y": "8a8b2cef70bc61380170be069828032b",
"0-3Y": "61f69682dc3ec18fe9664ff59308314a",
"0-5Y": "0beafb51867009998c2f4932bf22ede3",
"0-10Y": "8a8b2cef7832f8920178350801470014",
"1-3Y": "cc1cfe89b0cbd0800420a0e037026407",
"1-5Y": "7c3110e5305f9301482517066427a554",
"1-10Y": "a5d90802e3259978a027267de651106d",
"3-5Y": "8a8b2ca04bf69582014c10b60f376c77",
"5Y": "8a8b2ca03a3feea1013a44b98fc533f5",
"7Y": "2c9081e50e8767dc010e87b6e26c0080",
"7-10Y": "8a8b2c8f5a492a01015a4ac986480043",
"10Y": "8a8b2ca04b666362014b723482bc4f49",
"30Y": "8a8b2cef77b239980177b485d20a6379",
}
url = "https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQueryResult"
params = {
"indexid": mapping[period],
"qxlxt": "00",
"ltcslx": "",
"zslxt": INDICATOR_MAPPING[indicator],
"zslxt1": INDICATOR_MAPPING[indicator],
"lx": "1",
"locale": "zh_CN",
}
r = requests.post(url, params=params)
raw_json = r.json()
key_col_map = {f"{INDICATOR_MAPPING[indicator]}_{p_code}": freq_col for p_code, freq_col in
raw_json['dqcName'].items()}
data_json = {key: raw_json[key] for key in key_col_map}
temp_df = pd.DataFrame.from_dict(data_json, orient="columns")
temp_df.index = pd.to_datetime(pd.to_numeric(temp_df.index), unit="ms", utc=True).tz_convert("Asia/Shanghai")
temp_df.index.name = "date"
temp_df.rename(columns=key_col_map, inplace=True)
temp_df.reset_index(inplace=True)
temp_df.columns = ["date", "value"]
temp_df['date'] = pd.to_datetime(temp_df['date'], errors="coerce").dt.date
return temp_df
def bond_new_composite_index_cbond(
indicator: str = "财富", period: str = "总值"
) -> pd.DataFrame:
"""
中国债券信息网-中债指数-中债指数族系-总指数-综合类指数-中债-新综合指数
https://yield.chinabond.com.cn/cbweb-mn/indices/single_index_query
:param indicator: choice of {"全价", "净价", "财富", "平均市值法久期", "平均现金流法久期", "平均市值法凸性",
"平均现金流法凸性", "平均现金流法到期收益率", "平均市值法到期收益率", "平均基点价值", "平均待偿期", "平均派息率",
"指数上日总市值", "财富指数涨跌幅", "全价指数涨跌幅", "净价指数涨跌幅", "现券结算量"}
:type indicator: str
:param period: choice of {"总值", "1年以下", "1-3年", "3-5年", "5-7年", "7-10年", "10年以上", "0-3个月",
"3-6个月", "6-9个月", "9-12个月", "0-6个月", "6-12个月"}
:type period: str
:return: 新综合指数
:rtype: pandas.DataFrame
"""
indicator_map = {
"全价": "QJZS",
"净价": "JJZS",
"财富": "CFZS",
"平均市值法久期": "PJSZFJQ",
"平均现金流法久期": "PJXJLFJQ",
"平均市值法凸性": "PJSZFTX",
"平均现金流法凸性": "PJXJLFTX",
"平均现金流法到期收益率": "PJDQSYL",
"平均市值法到期收益率": "PJSZFDQSYL",
"平均基点价值": "PJJDJZ",
"平均待偿期": "PJDCQ",
"平均派息率": "PJPXL",
"指数上日总市值": "ZSZSZ",
"财富指数涨跌幅": "CFZSZDF",
"全价指数涨跌幅": "QJZSZDF",
"净价指数涨跌幅": "JJZSZDF",
"现券结算量": "XQJSL",
}
period_map = {
"总值": "00",
"1年以下": "01",
"1-3年": "02",
"3-5年": "03",
"5-7年": "04",
"7-10年": "05",
"10年以上": "06",
"0-3个月": "07",
"3-6个月": "08",
"6-9个月": "09",
"9-12个月": "10",
"0-6个月": "11",
"6-12个月": "12",
}
url = "https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQuery"
params = {
"indexid": "8a8b2ca0332abed20134ea76d8885831",
"": "", # noqa: F601
"qxlxt": period_map[period],
"": "", # noqa: F601
"ltcslx": "",
"": "", # noqa: F601
"zslxt": indicator_map[indicator], # noqa: F601
"": "", # noqa: F601
"zslxt": indicator_map[indicator], # noqa: F601
"": "", # noqa: F601
"lx": "1",
"": "", # noqa: F601
"locale": "",
}
r = requests.post(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(
data_json[f"{indicator_map[indicator]}_{period_map[period]}"],
orient="index",
)
temp_df.reset_index(inplace=True)
temp_df.columns = ["date", "value"]
temp_df["date"] = temp_df["date"].astype(float)
temp_df["date"] = (
pd.to_datetime(temp_df["date"], unit="ms", errors="coerce", utc=True)
.dt.tz_convert("Asia/Shanghai")
.dt.date
)
temp_df["value"] = pd.to_numeric(temp_df["value"], errors="coerce")
return temp_df
def bond_composite_index_cbond(
indicator: str = "财富", period: str = "总值"
) -> pd.DataFrame:
"""
中国债券信息网-中债指数-中债指数族系-总指数-综合类指数-中债-综合指数
https://yield.chinabond.com.cn/cbweb-mn/indices/single_index_query
:param indicator: choice of {"全价", "净价", "财富", "平均市值法久期", "平均现金流法久期", "平均市值法凸性",
"平均现金流法凸性", "平均现金流法到期收益率", "平均市值法到期收益率", "平均基点价值", "平均待偿期", "平均派息率",
"指数上日总市值", "财富指数涨跌幅", "全价指数涨跌幅", "净价指数涨跌幅", "现券结算量"}
:type indicator: str
:param period: choice of {"总值", "1年以下", "1-3年", "3-5年", "5-7年", "7-10年", "10年以上", "0-3个月",
"3-6个月", "6-9个月", "9-12个月", "0-6个月", "6-12个月"}
:type period: str
:return: 新综合指数
:rtype: pandas.DataFrame
"""
indicator_map = {
"全价": "QJZS",
"净价": "JJZS",
"财富": "CFZS",
"平均市值法久期": "PJSZFJQ",
"平均现金流法久期": "PJXJLFJQ",
"平均市值法凸性": "PJSZFTX",
"平均现金流法凸性": "PJXJLFTX",
"平均现金流法到期收益率": "PJDQSYL",
"平均市值法到期收益率": "PJSZFDQSYL",
"平均基点价值": "PJJDJZ",
"平均待偿期": "PJDCQ",
"平均派息率": "PJPXL",
"指数上日总市值": "ZSZSZ",
"财富指数涨跌幅": "CFZSZDF",
"全价指数涨跌幅": "QJZSZDF",
"净价指数涨跌幅": "JJZSZDF",
"现券结算量": "XQJSL",
}
period_map = {
"总值": "00",
"1年以下": "01",
"1-3年": "02",
"3-5年": "03",
"5-7年": "04",
"7-10年": "05",
"10年以上": "06",
"0-3个月": "07",
"3-6个月": "08",
"6-9个月": "09",
"9-12个月": "10",
"0-6个月": "11",
"6-12个月": "12",
}
url = "https://yield.chinabond.com.cn/cbweb-mn/indices/singleIndexQuery"
params = {
"indexid": "2c90818811afed8d0111c0c672b31578",
"": "", # noqa: F601
"qxlxt": period_map[period],
"": "", # noqa: F601
"zslxt": indicator_map[indicator],
"": "", # noqa: F601
"lx": "1",
"": "", # noqa: F601
"locale": "",
}
r = requests.post(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(
data_json[f"{indicator_map[indicator]}_{period_map[period]}"],
orient="index",
)
temp_df.reset_index(inplace=True)
temp_df.columns = ["date", "value"]
temp_df["date"] = pd.to_datetime(temp_df["date"].astype(int), errors="coerce", unit="ms").dt.date
temp_df["value"] = pd.to_numeric(temp_df["value"], errors="coerce")
return temp_df
if __name__ == "__main__":
bond_new_composite_index_cbond_df = bond_new_composite_index_cbond(
indicator="财富", period="总值"
)
print(bond_new_composite_index_cbond_df)
bond_composite_index_cbond_df = bond_composite_index_cbond(
indicator="财富", period="总值"
)
print(bond_composite_index_cbond_df)
bond_index_general_cbond_df = bond_index_general_cbond(index_category="新综合指数", indicator="全价", period="总值")
print(bond_index_general_cbond_df)
bond_treasury_index_cbond_df = bond_treasury_index_cbond(indicator="财富", period="5Y")
print(bond_treasury_index_cbond_df)
@@ -0,0 +1,190 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/10/1 17:00
Desc: 中国外汇交易中心暨全国银行间同业拆借中心
中国外汇交易中心暨全国银行间同业拆借中心-市场数据-债券市场行情-现券市场做市报价
中国外汇交易中心暨全国银行间同业拆借中心-市场数据-债券市场行情-现券市场成交行情
https://www.chinamoney.com.cn/chinese/mkdatabond/
"""
from io import StringIO
import pandas as pd
import requests
from akshare.bond.bond_china_money import bond_china_close_return_map
from akshare.utils.cons import headers
def bond_spot_quote() -> pd.DataFrame:
"""
中国外汇交易中心暨全国银行间同业拆借中心-市场数据-债券市场行情-现券市场做市报价
https://www.chinamoney.com.cn/chinese/mkdatabond/
:return: 现券市场做市报价
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-md-bond/CbMktMakQuot"
payload = {
"flag": "1",
"lang": "cn",
}
r = requests.post(url=url, data=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.columns = [
"_",
"_",
"报价机构",
"_",
"_",
"_",
"债券简称",
"_",
"_",
"_",
"_",
"买入/卖出收益率",
"_",
"买入/卖出净价",
"_",
"_",
"_",
]
temp_df = temp_df[
[
"报价机构",
"债券简称",
"买入/卖出净价",
"买入/卖出收益率",
]
]
temp_df["买入净价"] = (
temp_df["买入/卖出净价"].str.split("/", expand=True).iloc[:, 0]
)
temp_df["卖出净价"] = (
temp_df["买入/卖出净价"].str.split("/", expand=True).iloc[:, 1]
)
temp_df["买入收益率"] = (
temp_df["买入/卖出收益率"].str.split("/", expand=True).iloc[:, 0]
)
temp_df["卖出收益率"] = (
temp_df["买入/卖出收益率"].str.split("/", expand=True).iloc[:, 1]
)
del temp_df["买入/卖出净价"]
del temp_df["买入/卖出收益率"]
temp_df["买入净价"] = pd.to_numeric(temp_df["买入净价"], errors="coerce")
temp_df["卖出净价"] = pd.to_numeric(temp_df["卖出净价"], errors="coerce")
temp_df["买入收益率"] = pd.to_numeric(temp_df["买入收益率"], errors="coerce")
temp_df["卖出收益率"] = pd.to_numeric(temp_df["卖出收益率"], errors="coerce")
return temp_df
def bond_spot_deal() -> pd.DataFrame:
"""
中国外汇交易中心暨全国银行间同业拆借中心-市场数据-债券市场行情-现券市场成交行情
https://www.chinamoney.com.cn/chinese/mkdatabond/
:return: 现券市场成交行情
:rtype: pandas.DataFrame
"""
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-md-bond/CbtPri"
payload = {
"flag": "1",
"lang": "cn",
"bondName": "",
}
r = requests.post(url=url, data=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.columns = [
"_",
"_",
"债券简称",
"_",
"_",
"_",
"_",
"涨跌",
"_",
"_",
"_",
"加权收益率",
"成交净价",
"_",
"_",
"最新收益率",
"-",
"交易量",
"_",
"_",
"_",
"_",
]
temp_df = temp_df[
[
"债券简称",
"成交净价",
"最新收益率",
"涨跌",
"加权收益率",
"交易量",
]
]
temp_df["成交净价"] = pd.to_numeric(temp_df["成交净价"], errors="coerce")
temp_df["最新收益率"] = pd.to_numeric(temp_df["最新收益率"], errors="coerce")
temp_df["涨跌"] = pd.to_numeric(temp_df["涨跌"], errors="coerce")
temp_df["加权收益率"] = pd.to_numeric(temp_df["加权收益率"], errors="coerce")
temp_df["交易量"] = pd.to_numeric(temp_df["交易量"], errors="coerce")
return temp_df
def bond_china_yield(
start_date: str = "20200204", end_date: str = "20210124"
) -> pd.DataFrame:
"""
中国债券信息网-国债及其他债券收益率曲线
https://www.chinabond.com.cn/
https://yield.chinabond.com.cn/cbweb-pbc-web/pbc/historyQuery?startDate=2019-02-07&endDate=2020-02-04&gjqx=0&qxId=ycqx&locale=cn_ZH
注意: end_date - start_date 应该小于一年
:param start_date: 需要查询的日期, 返回在该日期之后一年内的数据
:type start_date: str
:param end_date: 需要查询的日期, 返回在该日期之前一年内的数据
:type end_date: str
:return: 返回在指定日期之间之前一年内的数据
:rtype: pandas.DataFrame
"""
url = "https://yield.chinabond.com.cn/cbweb-pbc-web/pbc/historyQuery"
params = {
"startDate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"endDate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
"gjqx": "0",
"qxId": "ycqx",
"locale": "cn_ZH",
}
res = requests.get(url, params=params, headers=headers)
data_text = res.text.replace("&nbsp", "")
data_df = pd.read_html(StringIO(data_text), header=0)[1]
data_df["日期"] = pd.to_datetime(data_df["日期"], errors="coerce").dt.date
data_df["3月"] = pd.to_numeric(data_df["3月"], errors="coerce")
data_df["6月"] = pd.to_numeric(data_df["6月"], errors="coerce")
data_df["1年"] = pd.to_numeric(data_df["1年"], errors="coerce")
data_df["3年"] = pd.to_numeric(data_df["3年"], errors="coerce")
data_df["5年"] = pd.to_numeric(data_df["5年"], errors="coerce")
data_df["7年"] = pd.to_numeric(data_df["7年"], errors="coerce")
data_df["10年"] = pd.to_numeric(data_df["10年"], errors="coerce")
data_df["30年"] = pd.to_numeric(data_df["30年"], errors="coerce")
data_df.sort_values(by="日期", inplace=True)
data_df.reset_index(inplace=True, drop=True)
return data_df
if __name__ == "__main__":
bond_spot_quote_df = bond_spot_quote()
print(bond_spot_quote_df)
bond_spot_deal_df = bond_spot_deal()
print(bond_spot_deal_df)
bond_china_yield_df = bond_china_yield(start_date="20210201", end_date="20220201")
print(bond_china_yield_df)
@@ -0,0 +1,390 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/6/27 16:00
Desc: 收盘收益率曲线历史数据
https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1
"""
from functools import lru_cache
import pandas as pd
import requests
from akshare.utils.tqdm import get_tqdm
def __bond_register_service() -> requests.Session:
"""
将服务注册到网站中,则该 IP 在 24 小时内可以直接访问
https://www.chinamoney.com.cn
:return: 访问过的 Session
:rtype: requests.Session
"""
session = requests.Session()
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/108.0.0.0 Safari/537.36",
}
session.get(
url="https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1",
headers=headers,
)
cookies_dict = session.cookies.get_dict()
cookies_str = "; ".join(f"{k}={v}" for k, v in cookies_dict.items())
# 此处需要通过未访问的游览器,首次打开
# https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1
# 页面进行人工获取
data = {"key": "TThwSjc2NWkzV0VSOVRzOA=="}
headers = {
"Accept": "application/json, text/javascript, */*; q=0.01",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "en",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Content-Length": "22",
"Cookie": cookies_str,
"Content-Type": "application/x-www-form-urlencoded; charset=UTF-8",
"Host": "www.chinamoney.com.cn",
"Origin": "https://www.chinamoney.com.cn",
"Pragma": "no-cache",
"Referer": "https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1",
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/108.0.0.0 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
session.post(
url="https://www.chinamoney.com.cn/dqs/rest/cm-u-rbt/apply",
data=data,
headers=headers,
)
# 20231127 新增部分 https://github.com/akfamily/akshare/issues/4299
cookies_dict = session.cookies.get_dict()
cookies_str = "; ".join(f"{k}={v}" for k, v in cookies_dict.items())
headers = {
"Accept": "application/json, text/javascript, /; q=0.01",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "en",
"Connection": "keep-alive",
"Content-Length": "0",
"Cookie": cookies_str,
"Content-Type": "application/x-www-form-urlencoded; charset=UTF-8",
"Host": "www.chinamoney.com.cn",
"Origin": "https://www.chinamoney.com.cn",
"Referer": "https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1",
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/108.0.0.0 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
session.post(
url="https://www.chinamoney.com.cn/lss/rest/cm-s-account/getSessionUser",
headers=headers,
)
return session
@lru_cache()
def bond_china_close_return_map() -> pd.DataFrame:
"""
收盘收益率曲线历史数据
https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1
:return: 收盘收益率曲线历史数据
:rtype: pandas.DataFrame
"""
headers = {
"Accept": "application/json, text/javascript, */*; q=0.01",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Content-Length": "0",
"Host": "www.chinamoney.com.cn",
"Origin": "https://www.chinamoney.com.cn",
"Pragma": "no-cache",
"Referer": "https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/108.0.0.0 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bk-currency/ClsYldCurvCurvGO"
try:
r = requests.get(url, headers=headers)
data_json = r.json()
except: # noqa: E722
session = __bond_register_service()
r = session.get(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
return temp_df
def bond_china_close_return(
symbol: str = "国债",
period: str = "1",
start_date: str = "20231101",
end_date: str = "20231101",
) -> pd.DataFrame:
"""
收盘收益率曲线历史数据
https://www.chinamoney.com.cn/chinese/bkcurvclosedyhis/?bondType=CYCC000&reference=1
:param symbol: 需要获取的指标
:type period: choice of {'0.1', '0.5', '1'}
:param period: 期限间隔
:type symbol: str
:param start_date: 开始日期, 结束日期和开始日期不要超过 1 个月
:type start_date: str
:param end_date: 结束日期, 结束日期和开始日期不要超过 1 个月
:type end_date: str
:return: 收盘收益率曲线历史数据
:rtype: pandas.DataFrame
"""
name_code_df = bond_china_close_return_map()
symbol_code = name_code_df[name_code_df["cnLabel"] == symbol]["value"].values[0]
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bk-currency/ClsYldCurvHis"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/108.0.0.0 Safari/537.36",
}
params = {
"lang": "CN",
"reference": "1,2,3",
"bondType": symbol_code,
"startDate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"endDate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
"termId": period,
"pageNum": "1",
"pageSize": "50",
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
del temp_df["newDateValue"]
temp_df.columns = [
"日期",
"期限",
"到期收益率",
"即期收益率",
"远期收益率",
]
temp_df = temp_df[
[
"日期",
"期限",
"到期收益率",
"即期收益率",
"远期收益率",
]
]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["期限"] = pd.to_numeric(temp_df["期限"], errors="coerce")
temp_df["到期收益率"] = pd.to_numeric(temp_df["到期收益率"], errors="coerce")
temp_df["即期收益率"] = pd.to_numeric(temp_df["即期收益率"], errors="coerce")
temp_df["远期收益率"] = pd.to_numeric(temp_df["远期收益率"], errors="coerce")
return temp_df
def macro_china_swap_rate(
start_date: str = "20231101", end_date: str = "20231204"
) -> pd.DataFrame:
"""
FR007 利率互换曲线历史数据; 只能获取近一年的数据
https://www.chinamoney.com.cn/chinese/bkcurvfxhis/?cfgItemType=72&curveType=FR007
:param start_date: 开始日期, 开始和结束日期不得超过一个月
:type start_date: str
:param end_date: 结束日期, 开始和结束日期不得超过一个月
:type end_date: str
:return: FR007利率互换曲线历史数据
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
start_date = "-".join([start_date[:4], start_date[4:6], start_date[6:]])
end_date = "-".join([end_date[:4], end_date[4:6], end_date[6:]])
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bk-shibor/IfccHis"
params = {
"cfgItemType": "72",
"interestRateType": "0",
"startDate": start_date,
"endDate": end_date,
"bidAskType": "",
"lang": "CN",
"quoteTime": "全部",
"pageSize": "5000",
"pageNum": "1",
}
headers = {
"Accept": "application/json, text/javascript, */*; q=0.01",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Content-Length": "0",
"Host": "www.chinamoney.com.cn",
"Origin": "https://www.chinamoney.com.cn",
"Pragma": "no-cache",
"Referer": "https://www.chinamoney.com.cn/chinese/bkcurvfxhis/?cfgItemType=72&curveType=FR007",
"sec-ch-ua": '"Google Chrome";v="107", "Chromium";v="107", "Not=A?Brand";v="24"',
"sec-ch-ua-mobile": "?0",
"sec-ch-ua-platform": '"Windows"',
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
r = requests.post(url, data=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.columns = [
"日期",
"_",
"_",
"时刻",
"_",
"_",
"_",
"_",
"_",
"价格类型",
"_",
"曲线名称",
"_",
"_",
"_",
"_",
"data",
]
price_df = pd.DataFrame([item for item in temp_df["data"]])
price_df.columns = [
"1M",
"3M",
"6M",
"9M",
"1Y",
"2Y",
"3Y",
"4Y",
"5Y",
"7Y",
"10Y",
]
big_df = pd.concat(objs=[temp_df, price_df], axis=1)
big_df = big_df[
[
"日期",
"曲线名称",
"时刻",
"价格类型",
"1M",
"3M",
"6M",
"9M",
"1Y",
"2Y",
"3Y",
"4Y",
"5Y",
"7Y",
"10Y",
]
]
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce").dt.date
big_df["1M"] = pd.to_numeric(big_df["1M"], errors="coerce")
big_df["3M"] = pd.to_numeric(big_df["3M"], errors="coerce")
big_df["6M"] = pd.to_numeric(big_df["6M"], errors="coerce")
big_df["9M"] = pd.to_numeric(big_df["9M"], errors="coerce")
big_df["1Y"] = pd.to_numeric(big_df["1Y"], errors="coerce")
big_df["2Y"] = pd.to_numeric(big_df["2Y"], errors="coerce")
big_df["3Y"] = pd.to_numeric(big_df["3Y"], errors="coerce")
big_df["4Y"] = pd.to_numeric(big_df["4Y"], errors="coerce")
big_df["5Y"] = pd.to_numeric(big_df["5Y"], errors="coerce")
big_df["7Y"] = pd.to_numeric(big_df["7Y"], errors="coerce")
big_df["10Y"] = pd.to_numeric(big_df["10Y"], errors="coerce")
big_df.sort_values(["日期"], inplace=True, ignore_index=True)
return big_df
def macro_china_bond_public() -> pd.DataFrame:
"""
中国-债券信息披露-债券发行
https://www.chinamoney.com.cn/chinese/xzjfx/
:return: 债券发行
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bond-an/bnBondEmit"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
}
payload = {
"enty": "",
"bondType": "",
"bondNameCode": "",
"leadUnderwriter": "",
"pageNo": "1",
"pageSize": "10",
"limit": "1",
}
r = requests.post(url, data=payload, headers=headers)
data_json = r.json()
total_page = int(data_json["data"]["pageTotalSize"]) + 1
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(1, total_page), leave=False):
payload.update({"pageNo": page})
r = requests.post(url, data=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.columns = [
"债券全称",
"债券类型",
"-",
"发行日期",
"-",
"计息方式",
"-",
"债券期限",
"-",
"债券评级",
"-",
"价格",
"计划发行量",
]
big_df = big_df[
[
"债券全称",
"债券类型",
"发行日期",
"计息方式",
"价格",
"债券期限",
"计划发行量",
"债券评级",
]
]
big_df["价格"] = pd.to_numeric(big_df["价格"], errors="coerce")
big_df["计划发行量"] = pd.to_numeric(big_df["计划发行量"], errors="coerce")
return big_df
if __name__ == "__main__":
bond_china_close_return_df = bond_china_close_return(
symbol="同业存单(AAA)", period="1", start_date="20240607", end_date="20240607"
)
print(bond_china_close_return_df)
macro_china_swap_rate_df = macro_china_swap_rate(
start_date="20251010", end_date="20251208"
)
print(macro_china_swap_rate_df)
macro_china_bond_public_df = macro_china_bond_public()
print(macro_china_bond_public_df)
@@ -0,0 +1,344 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/5/16 19:00
Desc: 债券-集思录-可转债
集思录:https://www.jisilu.cn/data/cbnew/#cb
"""
from io import StringIO
import pandas as pd
import requests
import time
from akshare.utils import demjson
def bond_cb_index_jsl() -> pd.DataFrame:
"""
首页-可转债-集思录可转债等权指数
https://www.jisilu.cn/web/data/cb/index
:return: 集思录可转债等权指数
:rtype: pandas.DataFrame
"""
url = "https://www.jisilu.cn/webapi/cb/index_history/"
r = requests.get(url)
data_dict = demjson.decode(r.text)["data"]
temp_df = pd.DataFrame(data_dict)
return temp_df
def bond_cb_jsl(cookie: str = None) -> pd.DataFrame:
"""
集思录可转债
https://www.jisilu.cn/data/cbnew/#cb
:param cookie: 输入获取到的游览器 cookie
:type cookie: str
:return: 集思录可转债
:rtype: pandas.DataFrame
"""
url = "https://www.jisilu.cn/data/cbnew/cb_list_new/"
headers = {
"accept": "application/json, text/javascript, */*; q=0.01",
"accept-encoding": "gzip, deflate, br",
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8",
"cache-control": "no-cache",
"content-length": "220",
"content-type": "application/x-www-form-urlencoded; charset=UTF-8",
"cookie": cookie,
"origin": "https://www.jisilu.cn",
"pragma": "no-cache",
"referer": "https://www.jisilu.cn/data/cbnew/",
"sec-ch-ua": '" Not;A Brand";v="99", "Google Chrome";v="91", "Chromium";v="91"',
"sec-ch-ua-mobile": "?0",
"sec-fetch-dest": "empty",
"sec-fetch-mode": "cors",
"sec-fetch-site": "same-origin",
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/91.0.4472.164 Safari/537.36",
"x-requested-with": "XMLHttpRequest",
}
params = {
"___jsl": f"LST___t={int(time.time() * 1000)}",
}
payload = {
"fprice": "",
"tprice": "",
"curr_iss_amt": "",
"volume": "",
"svolume": "",
"premium_rt": "",
"ytm_rt": "",
"market": "",
"rating_cd": "",
"is_search": "N",
"market_cd[]": "shmb", # noqa: F601
"market_cd[]": "shkc", # noqa: F601
"market_cd[]": "szmb", # noqa: F601
"market_cd[]": "szcy", # noqa: F601
"btype": "",
"listed": "Y",
"qflag": "N",
"sw_cd": "",
"bond_ids": "",
"rp": "50",
}
r = requests.post(url, params=params, json=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame([item["cell"] for item in data_json["rows"]])
temp_df.rename(
columns={
"bond_id": "代码",
"bond_nm": "转债名称",
"price": "现价",
"increase_rt": "涨跌幅",
"stock_id": "正股代码",
"stock_nm": "正股名称",
"sprice": "正股价",
"sincrease_rt": "正股涨跌",
"pb": "正股PB",
"convert_price": "转股价",
"convert_value": "转股价值",
"premium_rt": "转股溢价率",
"dblow": "双低",
"rating_cd": "债券评级",
"put_convert_price": "回售触发价",
"force_redeem_price": "强赎触发价",
"convert_amt_ratio": "转债占比",
"maturity_dt": "到期时间",
"year_left": "剩余年限",
"curr_iss_amt": "剩余规模",
"volume": "成交额",
"turnover_rt": "换手率",
"ytm_rt": "到期税前收益",
},
inplace=True,
)
temp_df = temp_df[
[
"代码",
"转债名称",
"现价",
"涨跌幅",
"正股代码",
"正股名称",
"正股价",
"正股涨跌",
"正股PB",
"转股价",
"转股价值",
"转股溢价率",
"债券评级",
"回售触发价",
"强赎触发价",
"转债占比",
"到期时间",
"剩余年限",
"剩余规模",
"成交额",
"换手率",
"到期税前收益",
"双低",
]
]
temp_df["到期时间"] = pd.to_datetime(temp_df["到期时间"], errors="coerce").dt.date
temp_df["现价"] = pd.to_numeric(temp_df["现价"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["正股价"] = pd.to_numeric(temp_df["正股价"], errors="coerce")
temp_df["正股涨跌"] = pd.to_numeric(temp_df["正股涨跌"], errors="coerce")
temp_df["正股PB"] = pd.to_numeric(temp_df["正股PB"], errors="coerce")
temp_df["转股价"] = pd.to_numeric(temp_df["转股价"], errors="coerce")
temp_df["转股价值"] = pd.to_numeric(temp_df["转股价值"], errors="coerce")
temp_df["转股溢价率"] = pd.to_numeric(temp_df["转股溢价率"], errors="coerce")
temp_df["回售触发价"] = pd.to_numeric(temp_df["回售触发价"], errors="coerce")
temp_df["强赎触发价"] = pd.to_numeric(temp_df["强赎触发价"], errors="coerce")
temp_df["转债占比"] = pd.to_numeric(temp_df["转债占比"], errors="coerce")
temp_df["剩余年限"] = pd.to_numeric(temp_df["剩余年限"], errors="coerce")
temp_df["剩余规模"] = pd.to_numeric(temp_df["剩余规模"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["换手率"] = pd.to_numeric(temp_df["换手率"], errors="coerce")
temp_df["到期税前收益"] = pd.to_numeric(temp_df["到期税前收益"], errors="coerce")
return temp_df
def bond_cb_redeem_jsl() -> pd.DataFrame:
"""
集思录可转债-强赎
https://www.jisilu.cn/data/cbnew/#redeem
:return: 集思录可转债-强赎
:rtype: pandas.DataFrame
"""
url = "https://www.jisilu.cn/data/cbnew/redeem_list/"
headers = {
"Accept": "application/json, text/javascript, */*; q=0.01",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Content-Length": "5",
"Content-Type": "application/x-www-form-urlencoded; charset=UTF-8",
"Host": "www.jisilu.cn",
"Origin": "https://www.jisilu.cn",
"Pragma": "no-cache",
"Referer": "https://www.jisilu.cn/data/cbnew/",
"sec-ch-ua": '" Not A;Brand";v="99", "Chromium";v="101", "Google Chrome";v="101"',
"sec-ch-ua-mobile": "?0",
"sec-ch-ua-platform": '"Windows"',
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/101.0.4951.67 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {
"___jsl": "LST___t=1653394005966",
}
payload = {
"rp": "50",
}
r = requests.post(url, params=params, json=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame([item["cell"] for item in data_json["rows"]])
temp_df.rename(
columns={
"bond_id": "代码",
"bond_nm": "名称",
"price": "现价",
"stock_id": "正股代码",
"stock_nm": "正股名称",
"margin_flg": "-",
"btype": "-",
"orig_iss_amt": "规模",
"curr_iss_amt": "剩余规模",
"convert_dt": "转股起始日",
"convert_price": "转股价",
"next_put_dt": "-",
"redeem_dt": "-",
"force_redeem": "-",
"redeem_flag": "-",
"redeem_price": "-",
"redeem_price_ratio": "强赎触发比",
"real_force_redeem_price": "强赎价",
"redeem_remain_days": "-",
"redeem_real_days": "-",
"redeem_total_days": "-",
"recount_dt": "-",
"redeem_count_days": "-",
"redeem_tc": "强赎条款",
"sprice": "正股价",
"delist_dt": "最后交易日",
"maturity_dt": "到期日",
"redeem_icon": "强赎状态",
"redeem_orders": "-",
"at_maturity": "-",
"redeem_count": "强赎天计数",
"after_next_put_dt": "-",
"force_redeem_price": "强赎触发价",
},
inplace=True,
)
temp_df = temp_df[
[
"代码",
"名称",
"现价",
"正股代码",
"正股名称",
"规模",
"剩余规模",
"转股起始日",
"最后交易日",
"到期日",
"转股价",
"强赎触发比",
"强赎触发价",
"正股价",
"强赎价",
"强赎天计数",
"强赎条款",
"强赎状态",
]
]
temp_df["现价"] = pd.to_numeric(temp_df["现价"], errors="coerce")
temp_df["规模"] = pd.to_numeric(temp_df["规模"], errors="coerce")
temp_df["剩余规模"] = pd.to_numeric(temp_df["剩余规模"], errors="coerce")
temp_df["转股起始日"] = pd.to_datetime(
temp_df["转股起始日"], errors="coerce"
).dt.date
temp_df["最后交易日"] = pd.to_datetime(
temp_df["最后交易日"], errors="coerce"
).dt.date
temp_df["到期日"] = pd.to_datetime(temp_df["到期日"], errors="coerce").dt.date
temp_df["转股价"] = pd.to_numeric(temp_df["转股价"], errors="coerce")
temp_df["强赎触发比"] = pd.to_numeric(
temp_df["强赎触发比"].str.strip("%"), errors="coerce"
)
temp_df["强赎触发价"] = pd.to_numeric(temp_df["强赎触发价"], errors="coerce")
temp_df["正股价"] = pd.to_numeric(temp_df["正股价"], errors="coerce")
temp_df["强赎价"] = pd.to_numeric(temp_df["强赎价"], errors="coerce")
temp_df["强赎天计数"] = temp_df["强赎天计数"].replace(
r"^.*?(\d{1,2}\/\d{1,2} \| \d{1,2}).*?$", r"\1", regex=True
)
temp_df["强赎状态"] = temp_df["强赎状态"].map(
{
"R": "已公告强赎",
"O": "公告要强赎",
"G": "公告不强赎",
"B": "已满足强赎条件",
"": "",
}
)
return temp_df
def bond_cb_adj_logs_jsl(symbol: str = "128013") -> pd.DataFrame:
"""
集思录-可转债转股价-调整记录
https://www.jisilu.cn/data/cbnew/#cb
:param symbol: 可转债代码
:type symbol: str
:return: 转股价调整记录
:rtype: pandas.DataFrame
"""
url = f"https://www.jisilu.cn/data/cbnew/adj_logs/?bond_id={symbol}"
r = requests.get(url)
data_text = r.text
if "</table>" not in data_text:
# 1. 该可转债没有转股价调整记录,服务端返回文本 '暂无数据'
# 2. 无效可转债代码,服务端返回 {"timestamp":1639565628,"isError":1,"msg":"无效代码格式"}
# 以上两种情况,返回空的 DataFrame
return pd.DataFrame()
else:
temp_df = pd.read_html(StringIO(data_text), parse_dates=True)[0]
temp_df.columns = [item.replace(" ", "") for item in temp_df.columns]
temp_df["下修前转股价"] = pd.to_numeric(
temp_df["下修前转股价"], errors="coerce"
)
temp_df["下修后转股价"] = pd.to_numeric(
temp_df["下修后转股价"], errors="coerce"
)
temp_df["下修底价"] = pd.to_numeric(temp_df["下修底价"], errors="coerce")
temp_df["股东大会日"] = pd.to_datetime(
temp_df["股东大会日"], format="%Y-%m-%d", errors="coerce"
).dt.date
temp_df["新转股价生效日期"] = pd.to_datetime(
temp_df["新转股价生效日期"], format="%Y-%m-%d", errors="coerce"
).dt.date
return temp_df
if __name__ == "__main__":
bond_cb_index_jsl_df = bond_cb_index_jsl()
print(bond_cb_index_jsl_df)
bond_cb_jsl_df = bond_cb_jsl(cookie="")
print(bond_cb_jsl_df)
bond_cb_redeem_jsl_df = bond_cb_redeem_jsl()
print(bond_cb_redeem_jsl_df)
bond_cb_adj_logs_jsl_df = bond_cb_adj_logs_jsl(symbol="128013")
print(bond_cb_adj_logs_jsl_df)
@@ -0,0 +1,147 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/4/5 17:00
Desc: 东方财富网-数据中心-经济数据-中美国债收益率
https://data.eastmoney.com/cjsj/zmgzsyl.html
"""
import pandas as pd
import requests
from akshare.utils.tqdm import get_tqdm
def bond_zh_us_rate(start_date: str = "19901219") -> pd.DataFrame:
"""
东方财富网-数据中心-经济数据-中美国债收益率
https://data.eastmoney.com/cjsj/zmgzsyl.html
:param start_date: 开始统计时间
:type start_date: str
:return: 中美国债收益率
:rtype: pandas.DataFrame
"""
url = "https://datacenter.eastmoney.com/api/data/get"
params = {
"type": "RPTA_WEB_TREASURYYIELD",
"sty": "ALL",
"st": "SOLAR_DATE",
"sr": "-1",
"token": "894050c76af8597a853f5b408b759f5d",
"p": "1",
"ps": "500",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
total_page = data_json["result"]["pages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(1, total_page + 1), leave=False):
params = {
"type": "RPTA_WEB_TREASURYYIELD",
"sty": "ALL",
"st": "SOLAR_DATE",
"sr": "-1",
"token": "894050c76af8597a853f5b408b759f5d",
"p": page,
"ps": "500",
"pageNo": page,
"pageNum": page,
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
for col in temp_df.columns:
if temp_df[col].isnull().all(): # 检查列是否包含 None 或 NaN
temp_df[col] = pd.to_numeric(temp_df[col], errors="coerce")
if big_df.empty:
big_df = temp_df
else:
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
temp_date_list = pd.to_datetime(big_df["SOLAR_DATE"]).dt.date.to_list()
if pd.to_datetime(start_date) in pd.date_range(
temp_date_list[-1], temp_date_list[0]
):
break
big_df.rename(
columns={
"SOLAR_DATE": "日期",
"EMM00166462": "中国国债收益率5年",
"EMM00166466": "中国国债收益率10年",
"EMM00166469": "中国国债收益率30年",
"EMM00588704": "中国国债收益率2年",
"EMM01276014": "中国国债收益率10年-2年",
"EMG00001306": "美国国债收益率2年",
"EMG00001308": "美国国债收益率5年",
"EMG00001310": "美国国债收益率10年",
"EMG00001312": "美国国债收益率30年",
"EMG01339436": "美国国债收益率10年-2年",
"EMM00000024": "中国GDP年增率",
"EMG00159635": "美国GDP年增率",
},
inplace=True,
)
big_df = big_df[
[
"日期",
"中国国债收益率2年",
"中国国债收益率5年",
"中国国债收益率10年",
"中国国债收益率30年",
"中国国债收益率10年-2年",
"中国GDP年增率",
"美国国债收益率2年",
"美国国债收益率5年",
"美国国债收益率10年",
"美国国债收益率30年",
"美国国债收益率10年-2年",
"美国GDP年增率",
]
]
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce")
big_df["中国国债收益率2年"] = pd.to_numeric(
big_df["中国国债收益率2年"], errors="coerce"
)
big_df["中国国债收益率5年"] = pd.to_numeric(
big_df["中国国债收益率5年"], errors="coerce"
)
big_df["中国国债收益率10年"] = pd.to_numeric(
big_df["中国国债收益率10年"], errors="coerce"
)
big_df["中国国债收益率30年"] = pd.to_numeric(
big_df["中国国债收益率30年"], errors="coerce"
)
big_df["中国国债收益率10年-2年"] = pd.to_numeric(
big_df["中国国债收益率10年-2年"], errors="coerce"
)
big_df["中国GDP年增率"] = pd.to_numeric(big_df["中国GDP年增率"], errors="coerce")
big_df["美国国债收益率2年"] = pd.to_numeric(
big_df["美国国债收益率2年"], errors="coerce"
)
big_df["美国国债收益率5年"] = pd.to_numeric(
big_df["美国国债收益率5年"], errors="coerce"
)
big_df["美国国债收益率10年"] = pd.to_numeric(
big_df["美国国债收益率10年"], errors="coerce"
)
big_df["美国国债收益率30年"] = pd.to_numeric(
big_df["美国国债收益率30年"], errors="coerce"
)
big_df["美国国债收益率10年-2年"] = pd.to_numeric(
big_df["美国国债收益率10年-2年"], errors="coerce"
)
big_df["美国GDP年增率"] = pd.to_numeric(big_df["美国GDP年增率"], errors="coerce")
big_df.sort_values("日期", inplace=True)
big_df.set_index(["日期"], inplace=True)
big_df = big_df[pd.to_datetime(start_date) :]
big_df.reset_index(inplace=True)
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
return big_df
if __name__ == "__main__":
bond_zh_us_rate_df = bond_zh_us_rate(start_date="19901219")
print(bond_zh_us_rate_df)
@@ -0,0 +1,104 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/2/4 17:00
Desc: 新浪财经-债券-中国/美国国债收益率
https://vip.stock.finance.sina.com.cn/mkt/#hs_z
"""
import pandas as pd
import requests
def bond_gb_zh_sina(symbol: str = "中国10年期国债") -> pd.DataFrame:
"""
新浪财经-债券-中国国债收益率行情数据
https://stock.finance.sina.com.cn/forex/globalbd/cn10yt.html
:param symbol: choice of {"中国1年期国债", "中国2年期国债", "中国3年期国债", "中国5年期国债", "中国7年期国债", "中国10年期国债", "中国15年期国债", "中国20年期国债", "中国30年期国债"}
:type symbol: str
:return: 中国国债收益率行情数据
:rtype: pandas.DataFrame
"""
symbol_map = {
"中国1年期国债": "CN1YT",
"中国2年期国债": "CN2YT",
"中国3年期国债": "CN3YT",
"中国5年期国债": "CN5YT",
"中国7年期国债": "CN7YT",
"中国10年期国债": "CN10YT",
"中国15年期国债": "CN15YT",
"中国20年期国债": "CN20YT",
"中国30年期国债": "CN30YT",
}
url = f"https://bond.finance.sina.com.cn/hq/gb/daily?symbol={symbol_map[symbol]}"
r = requests.get(url)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"date",
"open",
"high",
"low",
"close",
"volume",
]
temp_df["date"] = pd.to_datetime(temp_df["date"], errors="coerce").dt.date
temp_df["open"] = pd.to_numeric(temp_df["open"], errors="coerce")
temp_df["high"] = pd.to_numeric(temp_df["high"], errors="coerce")
temp_df["low"] = pd.to_numeric(temp_df["low"], errors="coerce")
temp_df["close"] = pd.to_numeric(temp_df["close"], errors="coerce")
temp_df["volume"] = pd.to_numeric(temp_df["volume"], errors="coerce")
return temp_df
def bond_gb_us_sina(symbol: str = "美国10年期国债") -> pd.DataFrame:
"""
新浪财经-债券-美国国债收益率行情数据
https://stock.finance.sina.com.cn/forex/globalbd/cn10yt.html
:param symbol: choice of {"美国1月期国债", "美国2月期国债", "美国3月期国债", "美国4月期国债", "美国6月期国债", "美国1年期国债", "美国2年期国债", "美国3年期国债", "美国5年期国债", "美国7年期国债", "美国10年期国债", "美国20年期国债", "美国30年期国债"}
:type symbol: str
:return: 美国国债收益率行情数据
:rtype: pandas.DataFrame
"""
symbol_map = {
"美国1月期国债": "US1MT",
"美国2月期国债": "US2MT",
"美国3月期国债": "US3MT",
"美国4月期国债": "US4MT",
"美国6月期国债": "US6MT",
"美国1年期国债": "US1YT",
"美国2年期国债": "US2YT",
"美国3年期国债": "US3YT",
"美国5年期国债": "US5YT",
"美国7年期国债": "US7YT",
"美国10年期国债": "US10YT",
"美国20年期国债": "US20YT",
"美国30年期国债": "US30YT",
}
url = f"https://bond.finance.sina.com.cn/hq/gb/daily?symbol={symbol_map[symbol]}"
r = requests.get(url)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"date",
"open",
"high",
"low",
"close",
"volume",
]
temp_df["date"] = pd.to_datetime(temp_df["date"], errors="coerce").dt.date
temp_df["open"] = pd.to_numeric(temp_df["open"], errors="coerce")
temp_df["high"] = pd.to_numeric(temp_df["high"], errors="coerce")
temp_df["low"] = pd.to_numeric(temp_df["low"], errors="coerce")
temp_df["close"] = pd.to_numeric(temp_df["close"], errors="coerce")
temp_df["volume"] = pd.to_numeric(temp_df["volume"], errors="coerce")
return temp_df
if __name__ == "__main__":
bond_gb_zh_sina_df = bond_gb_zh_sina(symbol="中国10年期国债")
print(bond_gb_zh_sina_df)
bond_gb_us_sina_df = bond_gb_us_sina(symbol="美国10年期国债")
print(bond_gb_us_sina_df)
@@ -0,0 +1,231 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/5/10 14:00
Desc: 中国外汇交易中心暨全国银行间同业拆借中心
https://www.chinamoney.com.cn/chinese/scsjzqxx/
"""
import functools
import pandas as pd
import requests
from akshare.bond.bond_china import bond_china_close_return_map
from akshare.utils.tqdm import get_tqdm
@functools.lru_cache()
def bond_info_cm_query(symbol: str = "评级等级") -> pd.DataFrame:
"""
中国外汇交易中心暨全国银行间同业拆借中心-查询相关指标的参数
https://www.chinamoney.com.cn/chinese/scsjzqxx/
:param symbol: choice of {"主承销商", "债券类型", "息票类型", "发行年份", "评级等级"}
:type symbol: str
:return: 查询相关指标的参数
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
if symbol == "主承销商":
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bond-md/EntyFullNameSearchCondition"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/109.0.0.0 Safari/537.36"
}
r = requests.post(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["enty"])
temp_df.columns = ["code", "name"]
temp_df = temp_df[["name", "code"]]
return temp_df
else:
symbol_map = {
"债券类型": "bondType",
"息票类型": "couponType",
"发行年份": "issueYear",
"评级等级": "bondRtngShrt",
}
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bond-md/BondBaseInfoSearchCondition"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/109.0.0.0 Safari/537.36"
}
r = requests.post(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"][f"{symbol_map[symbol]}"])
if temp_df.shape[1] == 1:
temp_df.columns = ["name"]
temp_df["code"] = temp_df["name"]
temp_df.columns = ["code", "name"]
temp_df = temp_df[["name", "code"]]
return temp_df
@functools.lru_cache()
def bond_info_cm(
bond_name: str = "",
bond_code: str = "",
bond_issue: str = "",
bond_type: str = "",
coupon_type: str = "",
issue_year: str = "",
underwriter: str = "",
grade: str = "",
) -> pd.DataFrame:
"""
中国外汇交易中心暨全国银行间同业拆借中心-数据-债券信息-信息查询
https://www.chinamoney.com.cn/chinese/scsjzqxx/
:param bond_name: 债券名称
:type bond_name: str
:param bond_code: 债券代码
:type bond_code: str
:param bond_issue: 发行人/受托机构
:type bond_issue: str
:param bond_type: 债券类型
:type bond_type: str
:param coupon_type: 息票类型
:type coupon_type: str
:param issue_year: 发行年份
:type issue_year: str
:param underwriter: 主承销商
:type underwriter: str
:param grade: 评级等级
:type grade: str
:return: 信息查询结果
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
if bond_type:
bond_type_df = bond_info_cm_query(symbol="债券类型")
bond_type_df_value = bond_type_df[bond_type_df["name"] == bond_type][
"code"
].values[0]
else:
bond_type_df_value = ""
if coupon_type:
coupon_type_df = bond_info_cm_query(symbol="息票类型")
coupon_type_df_value = coupon_type_df[coupon_type_df["name"] == coupon_type][
"code"
].values[0]
else:
coupon_type_df_value = ""
if underwriter:
underwriter_df = bond_info_cm_query(symbol="主承销商")
underwriter_value = underwriter_df[underwriter_df["name"] == underwriter][
"code"
].values[0]
else:
underwriter_value = ""
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bond-md/BondMarketInfoList2"
payload = {
"pageNo": "1",
"pageSize": "15",
"bondName": bond_name,
"bondCode": bond_code,
"issueEnty": bond_issue,
"bondType": bond_type_df_value if bond_type_df_value else "",
"bondSpclPrjctVrty": "",
"couponType": coupon_type_df_value if coupon_type_df_value else "",
"issueYear": issue_year,
"entyDefinedCode": underwriter_value if underwriter_value else "",
"rtngShrt": grade,
}
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/109.0.0.0 Safari/537.36"
}
r = requests.post(url, data=payload, headers=headers)
data_json = r.json()
total_page = data_json["data"]["pageTotal"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(1, total_page + 1), leave=False):
payload.update({"pageNo": page})
r = requests.post(url, data=payload, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["resultList"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.rename(
columns={
"bondDefinedCode": "查询代码",
"bondName": "债券简称",
"bondCode": "债券代码",
"issueStartDate": "发行日期",
"issueEndDate": "-",
"bondTypeCode": "-",
"bondType": "债券类型",
"entyFullName": "发行人/受托机构",
"entyDefinedCode": "-",
"debtRtng": "最新债项评级",
"isin": "-",
"inptTp": "-",
},
inplace=True,
)
big_df = big_df[
[
"债券简称",
"债券代码",
"发行人/受托机构",
"债券类型",
"发行日期",
"最新债项评级",
"查询代码",
]
]
return big_df
@functools.lru_cache()
def bond_info_detail_cm(symbol: str = "淮安农商行CDSD2022021012") -> pd.DataFrame:
"""
中国外汇交易中心暨全国银行间同业拆借中心-数据-债券信息-信息查询-债券详情
https://www.chinamoney.com.cn/chinese/zqjc/?bondDefinedCode=egfjh08154
:param symbol: 债券简称
:type symbol: str
:return: 债券详情
:rtype: pandas.DataFrame
"""
bond_china_close_return_map()
url = "https://www.chinamoney.com.cn/ags/ms/cm-u-bond-md/BondDetailInfo"
inner_bond_info_cm_df = bond_info_cm(bond_name=symbol)
bond_code = inner_bond_info_cm_df["查询代码"].values[0]
payload = {"bondDefinedCode": bond_code}
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/109.0.0.0 Safari/537.36",
"host": "www.chinamoney.com.cn",
"origin": "https://www.chinamoney.com.cn",
"referer": "https://www.chinamoney.com.cn/chinese/zqjc/?bondDefinedCode=egfjh08154",
}
r = requests.post(url, data=payload, headers=headers)
data_json = r.json()
data_dict = data_json["data"]["bondBaseInfo"]
if data_dict["creditRateEntyList"]:
del data_dict["creditRateEntyList"]
if data_dict["exerciseInfoList"]:
del data_dict["exerciseInfoList"]
temp_df = pd.DataFrame.from_dict(data_dict, orient="index")
temp_df.reset_index(inplace=True)
temp_df.columns = ["name", "value"]
return temp_df
if __name__ == "__main__":
bond_info_cm_df = bond_info_cm(
bond_name="",
bond_code="",
bond_issue="",
bond_type="短期融资券",
coupon_type="零息式",
issue_year="2019",
grade="A-1",
underwriter="重庆农村商业银行股份有限公司",
)
print(bond_info_cm_df)
bond_info_detail_cm_df = bond_info_detail_cm(symbol="19渝机电CP002")
print(bond_info_detail_cm_df)
@@ -0,0 +1,574 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2024/6/19 22:00
Desc: 巨潮资讯-数据中心-专题统计-债券报表-债券发行
http://webapi.cninfo.com.cn/#/thematicStatistics
"""
import pandas as pd
import requests
import py_mini_racer
from akshare.datasets import get_ths_js
def _get_file_content_cninfo(file: str = "cninfo.js") -> str:
"""
获取 JS 文件的内容
:param file: JS 文件名
:type file: str
:return: 文件内容
:rtype: str
"""
setting_file_path = get_ths_js(file)
with open(setting_file_path, encoding="utf-8") as f:
file_data = f.read()
return file_data
def bond_treasure_issue_cninfo(
start_date: str = "20210910", end_date: str = "20211109"
) -> pd.DataFrame:
"""
巨潮资讯-数据中心-专题统计-债券报表-债券发行-国债发行
http://webapi.cninfo.com.cn/#/thematicStatistics
:param start_date: 开始统计时间
:type start_date: str
:param end_date: 结束统计数据
:type end_date: str
:return: 国债发行
:rtype: pandas.DataFrame
"""
url = "http://webapi.cninfo.com.cn/api/sysapi/p_sysapi1120"
js_code = py_mini_racer.MiniRacer()
js_content = _get_file_content_cninfo("cninfo.js")
js_code.eval(js_content)
mcode = js_code.call("getResCode1")
headers = {
"Accept": "*/*",
"Accept-Enckey": mcode,
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Content-Length": "0",
"Host": "webapi.cninfo.com.cn",
"Origin": "http://webapi.cninfo.com.cn",
"Pragma": "no-cache",
"Proxy-Connection": "keep-alive",
"Referer": "http://webapi.cninfo.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/93.0.4577.63 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {
"sdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"edate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
}
r = requests.post(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.rename(
columns={
"F009D": "缴款日",
"SECNAME": "债券简称",
"DECLAREDATE": "公告日期",
"F004D": "发行起始日",
"F003D": "发行终止日",
"F008N": "单位面值",
"SECCODE": "债券代码",
"F007N": "发行价格",
"F006N": "计划发行总量",
"F005N": "实际发行总量",
"F028N": "增发次数",
"BONDNAME": "债券名称",
"F014V": "发行对象",
"F002V": "交易市场",
"F013V": "发行方式",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"发行起始日",
"发行终止日",
"计划发行总量",
"实际发行总量",
"发行价格",
"单位面值",
"缴款日",
"增发次数",
"交易市场",
"发行方式",
"发行对象",
"公告日期",
"债券名称",
]
]
temp_df["发行起始日"] = pd.to_datetime(
temp_df["发行起始日"], errors="coerce"
).dt.date
temp_df["发行终止日"] = pd.to_datetime(
temp_df["发行终止日"], errors="coerce"
).dt.date
temp_df["缴款日"] = pd.to_datetime(temp_df["缴款日"], errors="coerce").dt.date
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
temp_df["计划发行总量"] = pd.to_numeric(temp_df["计划发行总量"], errors="coerce")
temp_df["实际发行总量"] = pd.to_numeric(temp_df["实际发行总量"], errors="coerce")
temp_df["发行价格"] = pd.to_numeric(temp_df["发行价格"], errors="coerce")
temp_df["单位面值"] = pd.to_numeric(temp_df["单位面值"], errors="coerce")
temp_df["增发次数"] = pd.to_numeric(temp_df["增发次数"], errors="coerce")
return temp_df
def bond_local_government_issue_cninfo(
start_date: str = "20210911", end_date: str = "20211110"
) -> pd.DataFrame:
"""
巨潮资讯-数据中心-专题统计-债券报表-债券发行-地方债发行
http://webapi.cninfo.com.cn/#/thematicStatistics
:param start_date: 开始统计时间
:type start_date: str
:param end_date: 开始统计时间
:type end_date: str
:return: 地方债发行
:rtype: pandas.DataFrame
"""
url = "http://webapi.cninfo.com.cn/api/sysapi/p_sysapi1121"
js_code = py_mini_racer.MiniRacer()
js_content = _get_file_content_cninfo("cninfo.js")
js_code.eval(js_content)
mcode = js_code.call("getResCode1")
headers = {
"Accept": "*/*",
"Accept-Enckey": mcode,
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Content-Length": "0",
"Host": "webapi.cninfo.com.cn",
"Origin": "http://webapi.cninfo.com.cn",
"Pragma": "no-cache",
"Proxy-Connection": "keep-alive",
"Referer": "http://webapi.cninfo.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/93.0.4577.63 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {
"sdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"edate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
}
r = requests.post(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.rename(
columns={
"F009D": "缴款日",
"SECNAME": "债券简称",
"DECLAREDATE": "公告日期",
"F004D": "发行起始日",
"F003D": "发行终止日",
"F008N": "单位面值",
"SECCODE": "债券代码",
"F007N": "发行价格",
"F006N": "计划发行总量",
"F005N": "实际发行总量",
"F028N": "增发次数",
"BONDNAME": "债券名称",
"F014V": "发行对象",
"F002V": "交易市场",
"F013V": "发行方式",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"发行起始日",
"发行终止日",
"计划发行总量",
"实际发行总量",
"发行价格",
"单位面值",
"缴款日",
"增发次数",
"交易市场",
"发行方式",
"发行对象",
"公告日期",
"债券名称",
]
]
temp_df["发行起始日"] = pd.to_datetime(
temp_df["发行起始日"], errors="coerce"
).dt.date
temp_df["发行终止日"] = pd.to_datetime(
temp_df["发行终止日"], errors="coerce"
).dt.date
temp_df["缴款日"] = pd.to_datetime(temp_df["缴款日"], errors="coerce").dt.date
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
temp_df["计划发行总量"] = pd.to_numeric(temp_df["计划发行总量"], errors="coerce")
temp_df["实际发行总量"] = pd.to_numeric(temp_df["实际发行总量"], errors="coerce")
temp_df["发行价格"] = pd.to_numeric(temp_df["发行价格"], errors="coerce")
temp_df["单位面值"] = pd.to_numeric(temp_df["单位面值"], errors="coerce")
temp_df["增发次数"] = pd.to_numeric(temp_df["增发次数"], errors="coerce")
return temp_df
def bond_corporate_issue_cninfo(
start_date: str = "20210911", end_date: str = "20211110"
) -> pd.DataFrame:
"""
巨潮资讯-数据中心-专题统计-债券报表-债券发行-企业债发行
http://webapi.cninfo.com.cn/#/thematicStatistics
:param start_date: 开始统计时间
:type start_date: str
:param end_date: 开始统计时间
:type end_date: str
:return: 企业债发行
:rtype: pandas.DataFrame
"""
url = "http://webapi.cninfo.com.cn/api/sysapi/p_sysapi1122"
js_code = py_mini_racer.MiniRacer()
js_content = _get_file_content_cninfo("cninfo.js")
js_code.eval(js_content)
mcode = js_code.call("getResCode1")
headers = {
"Accept": "*/*",
"Accept-Enckey": mcode,
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Content-Length": "0",
"Host": "webapi.cninfo.com.cn",
"Origin": "http://webapi.cninfo.com.cn",
"Pragma": "no-cache",
"Proxy-Connection": "keep-alive",
"Referer": "http://webapi.cninfo.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/93.0.4577.63 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {
"sdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"edate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
}
r = requests.post(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.rename(
columns={
"SECNAME": "债券简称",
"DECLAREDATE": "公告日期",
"F004D": "交易所网上发行终止日",
"F003D": "交易所网上发行起始日",
"F008N": "发行面值",
"SECCODE": "债券代码",
"F007N": "发行价格",
"F006N": "实际发行总量",
"F005N": "计划发行总量",
"F022N": "最小认购单位",
"F017V": "承销方式",
"F052N": "最低认购额",
"F015V": "发行范围",
"BONDNAME": "债券名称",
"F014V": "发行对象",
"F013V": "发行方式",
"F023V": "募资用途说明",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"公告日期",
"交易所网上发行起始日",
"交易所网上发行终止日",
"计划发行总量",
"实际发行总量",
"发行面值",
"发行价格",
"发行方式",
"发行对象",
"发行范围",
"承销方式",
"最小认购单位",
"募资用途说明",
"最低认购额",
"债券名称",
]
]
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
temp_df["交易所网上发行起始日"] = pd.to_datetime(
temp_df["交易所网上发行起始日"], errors="coerce"
).dt.date
temp_df["交易所网上发行终止日"] = pd.to_datetime(
temp_df["交易所网上发行终止日"], errors="coerce"
).dt.date
temp_df["计划发行总量"] = pd.to_numeric(temp_df["计划发行总量"], errors="coerce")
temp_df["实际发行总量"] = pd.to_numeric(temp_df["实际发行总量"], errors="coerce")
temp_df["发行面值"] = pd.to_numeric(temp_df["发行面值"], errors="coerce")
temp_df["发行价格"] = pd.to_numeric(temp_df["发行价格"], errors="coerce")
temp_df["最小认购单位"] = pd.to_numeric(temp_df["最小认购单位"], errors="coerce")
temp_df["最低认购额"] = pd.to_numeric(temp_df["最低认购额"], errors="coerce")
return temp_df
def bond_cov_issue_cninfo(
start_date: str = "20210913", end_date: str = "20211112"
) -> pd.DataFrame:
"""
巨潮资讯-数据中心-专题统计-债券报表-债券发行-可转债发行
http://webapi.cninfo.com.cn/#/thematicStatistics
:param start_date: 开始统计时间
:type start_date: str
:param end_date: 开始统计时间
:type end_date: str
:return: 可转债发行
:rtype: pandas.DataFrame
"""
url = "http://webapi.cninfo.com.cn/api/sysapi/p_sysapi1123"
js_code = py_mini_racer.MiniRacer()
js_content = _get_file_content_cninfo("cninfo.js")
js_code.eval(js_content)
mcode = js_code.call("getResCode1")
headers = {
"Accept": "*/*",
"Accept-Enckey": mcode,
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Content-Length": "0",
"Host": "webapi.cninfo.com.cn",
"Origin": "http://webapi.cninfo.com.cn",
"Pragma": "no-cache",
"Proxy-Connection": "keep-alive",
"Referer": "http://webapi.cninfo.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/93.0.4577.63 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
params = {
"sdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"edate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
}
r = requests.post(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.rename(
columns={
"F029D": "发行起始日",
"SECNAME": "债券简称",
"F027D": "转股开始日期",
"F003D": "发行终止日",
"F007N": "发行面值",
"F053D": "转股终止日期",
"F005N": "计划发行总量",
"F051D": "网上申购日期",
"F026N": "初始转股价格",
"F066N": "网上申购数量下限",
"F052N": "发行价格",
"BONDNAME": "债券名称",
"F014V": "发行对象",
"F002V": "交易市场",
"F032V": "网上申购简称",
"F086V": "转股代码",
"DECLAREDATE": "公告日期",
"F028D": "债权登记日",
"F004D": "优先申购日",
"F068D": "网上申购中签结果公告日及退款日",
"F054D": "优先申购缴款日",
"F008N": "网上申购数量上限",
"SECCODE": "债券代码",
"F006N": "实际发行总量",
"F067N": "网上申购单位",
"F065N": "配售价格",
"F017V": "承销方式",
"F015V": "发行范围",
"F013V": "发行方式",
"F021V": "募资用途说明",
"F031V": "网上申购代码",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"公告日期",
"发行起始日",
"发行终止日",
"计划发行总量",
"实际发行总量",
"发行面值",
"发行价格",
"发行方式",
"发行对象",
"发行范围",
"承销方式",
"募资用途说明",
"初始转股价格",
"转股开始日期",
"转股终止日期",
"网上申购日期",
"网上申购代码",
"网上申购简称",
"网上申购数量上限",
"网上申购数量下限",
"网上申购单位",
"网上申购中签结果公告日及退款日",
"优先申购日",
"配售价格",
"债权登记日",
"优先申购缴款日",
"转股代码",
"交易市场",
"债券名称",
]
]
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
temp_df["发行起始日"] = pd.to_datetime(
temp_df["发行起始日"], errors="coerce"
).dt.date
temp_df["发行终止日"] = pd.to_datetime(
temp_df["发行终止日"], errors="coerce"
).dt.date
temp_df["转股开始日期"] = pd.to_datetime(
temp_df["转股开始日期"], errors="coerce"
).dt.date
temp_df["转股终止日期"] = pd.to_datetime(
temp_df["转股终止日期"], errors="coerce"
).dt.date
temp_df["转股终止日期"] = pd.to_datetime(
temp_df["转股终止日期"], errors="coerce"
).dt.date
temp_df["网上申购日期"] = pd.to_datetime(
temp_df["网上申购日期"], errors="coerce"
).dt.date
temp_df["网上申购中签结果公告日及退款日"] = pd.to_datetime(
temp_df["网上申购中签结果公告日及退款日"], errors="coerce"
).dt.date
temp_df["债权登记日"] = pd.to_datetime(
temp_df["债权登记日"], errors="coerce"
).dt.date
temp_df["优先申购日"] = pd.to_datetime(
temp_df["优先申购日"], errors="coerce"
).dt.date
temp_df["优先申购缴款日"] = pd.to_datetime(
temp_df["优先申购缴款日"], errors="coerce"
).dt.date
temp_df["计划发行总量"] = pd.to_numeric(temp_df["计划发行总量"], errors="coerce")
temp_df["实际发行总量"] = pd.to_numeric(temp_df["实际发行总量"], errors="coerce")
temp_df["发行面值"] = pd.to_numeric(temp_df["发行面值"], errors="coerce")
temp_df["发行价格"] = pd.to_numeric(temp_df["发行价格"], errors="coerce")
temp_df["初始转股价格"] = pd.to_numeric(temp_df["初始转股价格"], errors="coerce")
temp_df["网上申购数量上限"] = pd.to_numeric(
temp_df["网上申购数量上限"], errors="coerce"
)
temp_df["网上申购数量下限"] = pd.to_numeric(
temp_df["网上申购数量下限"], errors="coerce"
)
temp_df["网上申购单位"] = pd.to_numeric(temp_df["网上申购单位"], errors="coerce")
temp_df["配售价格"] = pd.to_numeric(temp_df["配售价格"], errors="coerce")
return temp_df
def bond_cov_stock_issue_cninfo() -> pd.DataFrame:
"""
巨潮资讯-数据中心-专题统计-债券报表-债券发行-可转债转股
http://webapi.cninfo.com.cn/#/thematicStatistics
:return: 可转债转股
:rtype: pandas.DataFrame
"""
url = "http://webapi.cninfo.com.cn/api/sysapi/p_sysapi1124"
js_code = py_mini_racer.MiniRacer()
js_content = _get_file_content_cninfo("cninfo.js")
js_code.eval(js_content)
mcode = js_code.call("getResCode1")
headers = {
"Accept": "*/*",
"Accept-Enckey": mcode,
"Accept-Encoding": "gzip, deflate",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Content-Length": "0",
"Host": "webapi.cninfo.com.cn",
"Origin": "http://webapi.cninfo.com.cn",
"Pragma": "no-cache",
"Proxy-Connection": "keep-alive",
"Referer": "http://webapi.cninfo.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/93.0.4577.63 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
}
r = requests.post(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["records"])
temp_df.rename(
columns={
"F003N": "转股价格",
"SECNAME": "债券简称",
"DECLAREDATE": "公告日期",
"F005D": "自愿转换期终止日",
"F004D": "自愿转换期起始日",
"F017V": "标的股票",
"BONDNAME": "债券名称",
"F002V": "转股简称",
"F001V": "转股代码",
"SECCODE": "债券代码",
},
inplace=True,
)
temp_df = temp_df[
[
"债券代码",
"债券简称",
"公告日期",
"转股代码",
"转股简称",
"转股价格",
"自愿转换期起始日",
"自愿转换期终止日",
"标的股票",
"债券名称",
]
]
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
temp_df["自愿转换期起始日"] = pd.to_datetime(
temp_df["自愿转换期起始日"], errors="coerce"
).dt.date
temp_df["自愿转换期终止日"] = pd.to_datetime(
temp_df["自愿转换期终止日"], errors="coerce"
).dt.date
temp_df["转股价格"] = pd.to_numeric(temp_df["转股价格"], errors="coerce")
return temp_df
if __name__ == "__main__":
bond_treasure_issue_cninfo_df = bond_treasure_issue_cninfo(
start_date="20210910", end_date="20211109"
)
print(bond_treasure_issue_cninfo_df)
bond_local_government_issue_cninfo_df = bond_local_government_issue_cninfo(
start_date="20210911", end_date="20211110"
)
print(bond_local_government_issue_cninfo_df)
bond_corporate_issue_cninfo_df = bond_corporate_issue_cninfo(
start_date="20210911", end_date="20211110"
)
print(bond_corporate_issue_cninfo_df)
bond_cov_issue_cninfo_df = bond_cov_issue_cninfo(
start_date="20210913", end_date="20211112"
)
print(bond_cov_issue_cninfo_df)
bond_cov_stock_issue_cninfo_df = bond_cov_stock_issue_cninfo()
print(bond_cov_stock_issue_cninfo_df)
@@ -0,0 +1,70 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/3/16 9:00
Desc:中国银行间市场交易商协会(https://www.nafmii.org.cn/)
孔雀开屏(http://zhuce.nafmii.org.cn/fans/publicQuery/manager)的债券基本信息数据
"""
import pandas as pd
import requests
def bond_debt_nafmii(page: str = "1") -> pd.DataFrame:
"""
中国银行间市场交易商协会-非金融企业债务融资工具注册信息系统
http://zhuce.nafmii.org.cn/fans/publicQuery/manager
:param page: 输入数字页码
:type page: int
:return: 指定 sector 和 indicator 的数据
:rtype: pandas.DataFrame
"""
url = "http://zhuce.nafmii.org.cn/fans/publicQuery/releFileProjDataGrid"
payload = {
"regFileName": "",
"itemType": "",
"startTime": "",
"endTime": "",
"entityName": "",
"leadManager": "",
"regPrdtType": "",
"page": page,
"rows": 50,
}
payload.update({"page": page})
r = requests.post(url, data=payload)
data_json = r.json() # 数据类型为 json 格式
temp_df = pd.DataFrame(data_json["rows"])
temp_df.rename(
columns={
"firstIssueAmount": "金额",
"isReg": "注册或备案",
"regFileName": "债券名称",
"regNoticeNo": "注册通知书文号",
"regPrdtType": "品种",
"releaseTime": "更新日期",
"projPhase": "项目状态",
},
inplace=True,
)
if "注册通知书文号" not in temp_df.columns:
temp_df["注册通知书文号"] = pd.NA
temp_df = temp_df[
[
"债券名称",
"品种",
"注册或备案",
"金额",
"注册通知书文号",
"更新日期",
"项目状态",
]
]
temp_df["金额"] = pd.to_numeric(temp_df["金额"], errors="coerce")
temp_df["更新日期"] = pd.to_datetime(temp_df["更新日期"], errors="coerce").dt.date
return temp_df
if __name__ == "__main__":
bond_debt_nafmii_df = bond_debt_nafmii(page="1")
print(bond_debt_nafmii_df)
@@ -0,0 +1,92 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/3/5 12:55
Desc: 上登债券信息网-债券成交概览
http://bond.sse.com.cn/data/statistics/overview/turnover/
"""
from io import BytesIO
import pandas as pd
import requests
def bond_cash_summary_sse(date: str = "20210111") -> pd.DataFrame:
"""
上登债券信息网-市场数据-市场统计-市场概览-债券现券市场概览
http://bond.sse.com.cn/data/statistics/overview/bondow/
:param date: 指定日期
:type date: str
:return: 债券成交概览
:rtype: pandas.DataFrame
"""
url = "http://query.sse.com.cn/commonExcelDd.do"
headers = {
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
"Referer": "http://bond.sse.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4280.88 Safari/537.36",
}
params = {
"sqlId": "COMMON_SSEBOND_SCSJ_SCTJ_SCGL_ZQXQSCGL_CX_L",
"TRADE_DATE": f"{date[:4]}-{date[4:6]}-{date[6:]}",
}
r = requests.get(url, params=params, headers=headers)
temp_df = pd.read_excel(BytesIO(r.content), engine="xlrd")
temp_df.columns = [
"债券现货",
"托管只数",
"托管市值",
"托管面值",
"数据日期",
]
temp_df["托管只数"] = pd.to_numeric(temp_df["托管只数"])
temp_df["托管市值"] = pd.to_numeric(temp_df["托管市值"])
temp_df["托管面值"] = pd.to_numeric(temp_df["托管面值"])
temp_df["数据日期"] = pd.to_datetime(temp_df["数据日期"]).dt.date
return temp_df
def bond_deal_summary_sse(date: str = "20210104") -> pd.DataFrame:
"""
上登债券信息网-市场数据-市场统计-市场概览-债券成交概览
http://bond.sse.com.cn/data/statistics/overview/turnover/
:param date: 指定日期
:type date: str
:return: 债券成交概览
:rtype: pandas.DataFrame
"""
url = "http://query.sse.com.cn/commonExcelDd.do"
headers = {
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
"Referer": "http://bond.sse.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4280.88 Safari/537.36",
}
params = {
"sqlId": "COMMON_SSEBOND_SCSJ_SCTJ_SCGL_ZQCJGL_CX_L",
"TRADE_DATE": f"{date[:4]}-{date[4:6]}-{date[6:]}",
}
r = requests.get(url, params=params, headers=headers)
temp_df = pd.read_excel(BytesIO(r.content))
temp_df.columns = [
"债券类型",
"当日成交笔数",
"当日成交金额",
"当年成交笔数",
"当年成交金额",
"数据日期",
]
temp_df["当日成交笔数"] = pd.to_numeric(temp_df["当日成交笔数"])
temp_df["当日成交金额"] = pd.to_numeric(temp_df["当日成交金额"])
temp_df["当年成交笔数"] = pd.to_numeric(temp_df["当年成交笔数"])
temp_df["当年成交金额"] = pd.to_numeric(temp_df["当年成交金额"])
temp_df["数据日期"] = pd.to_datetime(temp_df["数据日期"]).dt.date
return temp_df
if __name__ == "__main__":
bond_cash_summary_sse_df = bond_cash_summary_sse(date="20210111")
print(bond_cash_summary_sse_df)
bond_summary_sse_df = bond_deal_summary_sse(date="20210111")
print(bond_summary_sse_df)
@@ -0,0 +1,714 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/7/4 15:00
Desc: 新浪财经-债券-沪深可转债-实时行情数据和历史行情数据
https://vip.stock.finance.sina.com.cn/mkt/#hskzz_z
"""
import datetime
import re
import pandas as pd
import py_mini_racer
import requests
from akshare.bond.cons import (
zh_sina_bond_hs_cov_count_url,
zh_sina_bond_hs_cov_payload,
zh_sina_bond_hs_cov_url,
zh_sina_bond_hs_cov_hist_url,
)
from akshare.stock.cons import hk_js_decode
from akshare.utils import demjson
from akshare.utils.func import fetch_paginated_data
from akshare.utils.tqdm import get_tqdm
def _get_zh_bond_hs_cov_page_count() -> int:
"""
新浪财经-行情中心-债券-沪深可转债的总页数
https://vip.stock.finance.sina.com.cn/mkt/#hskzz_z
:return: 总页数
:rtype: int
"""
params = {
"node": "hskzz_z",
}
r = requests.get(zh_sina_bond_hs_cov_count_url, params=params)
page_count = int(re.findall(re.compile(r"\d+"), r.text)[0]) / 80
if isinstance(page_count, int):
return page_count
else:
return int(page_count) + 1
def bond_zh_hs_cov_spot() -> pd.DataFrame:
"""
新浪财经-债券-沪深可转债的实时行情数据; 大量抓取容易封IP
https://vip.stock.finance.sina.com.cn/mkt/#hskzz_z
:return: 所有沪深可转债在当前时刻的实时行情数据
:rtype: pandas.DataFrame
"""
big_df = pd.DataFrame()
page_count = _get_zh_bond_hs_cov_page_count()
zh_sina_bond_hs_payload_copy = zh_sina_bond_hs_cov_payload.copy()
tqdm = get_tqdm()
for page in tqdm(range(1, page_count + 1), leave=False):
zh_sina_bond_hs_payload_copy.update({"page": page})
res = requests.get(zh_sina_bond_hs_cov_url, params=zh_sina_bond_hs_payload_copy)
data_json = demjson.decode(res.text)
big_df = pd.concat(objs=[big_df, pd.DataFrame(data_json)], ignore_index=True)
return big_df
def bond_zh_hs_cov_daily(symbol: str = "sh010107") -> pd.DataFrame:
"""
新浪财经-债券-沪深可转债的历史行情数据, 大量抓取容易封 IP
https://vip.stock.finance.sina.com.cn/mkt/#hskzz_z
:param symbol: 沪深可转债代码; e.g., sh010107
:type symbol: str
:return: 指定沪深可转债代码的日 K 线数据
:rtype: pandas.DataFrame
"""
r = requests.get(
zh_sina_bond_hs_cov_hist_url.format(
symbol, datetime.datetime.now().strftime("%Y_%m_%d")
)
)
js_code = py_mini_racer.MiniRacer()
js_code.eval(hk_js_decode)
dict_list = js_code.call(
"d", r.text.split("=")[1].split(";")[0].replace('"', "")
) # 执行js解密代码
data_df = pd.DataFrame(dict_list)
data_df["date"] = pd.to_datetime(data_df["date"]).dt.date
return data_df
def _code_id_map() -> dict:
"""
东方财富-股票和市场代码
https://quote.eastmoney.com/center/gridlist.html#hs_a_board
:return: 股票和市场代码
:rtype: dict
"""
url = "https://80.push2.eastmoney.com/api/qt/clist/get"
params = {
"pn": "1",
"pz": "100",
"po": "1",
"np": "1",
"ut": "bd1d9ddb04089700cf9c27f6f7426281",
"fltt": "2",
"invt": "2",
"fid": "f12",
"fs": "m:1 t:2,m:1 t:23",
"fields": "f3,f12",
}
temp_df = fetch_paginated_data(url, params)
temp_df["market_id"] = 1
temp_df.rename(columns={"f12": "sh_code", "market_id": "sh_id"}, inplace=True)
code_id_dict = dict(zip(temp_df["sh_code"], temp_df["sh_id"]))
params = {
"pn": "1",
"pz": "100",
"po": "1",
"np": "1",
"ut": "bd1d9ddb04089700cf9c27f6f7426281",
"fltt": "2",
"invt": "2",
"fid": "f3",
"fs": "m:0 t:6,m:0 t:80",
"fields": "f3,f12",
}
temp_df_sz = fetch_paginated_data(url, params)
temp_df_sz["sz_id"] = 0
code_id_dict.update(dict(zip(temp_df_sz["f12"], temp_df_sz["sz_id"])))
return code_id_dict
def bond_zh_hs_cov_min(
symbol: str = "sz128039",
period: str = "15",
adjust: str = "",
start_date: str = "1979-09-01 09:32:00",
end_date: str = "2222-01-01 09:32:00",
) -> pd.DataFrame:
"""
东方财富网-可转债-分时行情
https://quote.eastmoney.com/concept/sz128039.html
:param symbol: 转债代码
:type symbol: str
:param period: choice of {'1', '5', '15', '30', '60'}
:type period: str
:param adjust: choice of {'', 'qfq', 'hfq'}
:type adjust: str
:param start_date: 开始日期
:type start_date: str
:param end_date: 结束日期
:type end_date: str
:return: 分时行情
:rtype: pandas.DataFrame
"""
market_type = {"sh": "1", "sz": "0"}
if period == "1":
url = "https://push2.eastmoney.com/api/qt/stock/trends2/get"
params = {
"secid": f"{market_type[symbol[:2]]}.{symbol[2:]}",
"fields1": "f1,f2,f3,f4,f5,f6,f7,f8,f9,f10,f11,f12,f13",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58",
"iscr": "0",
"iscca": "0",
"ut": "f057cbcbce2a86e2866ab8877db1d059",
"ndays": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
[item.split(",") for item in data_json["data"]["trends"]]
)
temp_df.columns = [
"时间",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"最新价",
]
temp_df.index = pd.to_datetime(temp_df["时间"])
temp_df = temp_df[start_date:end_date]
temp_df.reset_index(drop=True, inplace=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["时间"] = pd.to_datetime(temp_df["时间"]).astype(
str
) # show datatime here
return temp_df
else:
adjust_map = {
"": "0",
"qfq": "1",
"hfq": "2",
}
url = "https://push2his.eastmoney.com/api/qt/stock/kline/get"
params = {
"secid": f"{market_type[symbol[:2]]}.{symbol[2:]}",
"klt": period,
"fqt": adjust_map[adjust],
"lmt": "66",
"end": "20500000",
"iscca": "1",
"fields1": "f1,f2,f3,f4,f5",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58,f59,f60,f61",
"ut": "7eea3edcaed734bea9cbfc24409ed989",
"forcect": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
[item.split(",") for item in data_json["data"]["klines"]]
)
temp_df.columns = [
"时间",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"振幅",
"涨跌幅",
"涨跌额",
"换手率",
]
temp_df.index = pd.to_datetime(temp_df["时间"])
temp_df = temp_df[start_date:end_date]
temp_df.reset_index(drop=True, inplace=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["振幅"] = pd.to_numeric(temp_df["振幅"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["换手率"] = pd.to_numeric(temp_df["换手率"], errors="coerce")
temp_df["时间"] = pd.to_datetime(temp_df["时间"]).astype(str)
temp_df = temp_df[
[
"时间",
"开盘",
"收盘",
"最高",
"最低",
"涨跌幅",
"涨跌额",
"成交量",
"成交额",
"振幅",
"换手率",
]
]
return temp_df
def bond_zh_hs_cov_pre_min(symbol: str = "sh113570") -> pd.DataFrame:
"""
东方财富网-可转债-分时行情-盘前
https://quote.eastmoney.com/concept/sz128039.html
:param symbol: 转债代码
:type symbol: str
:return: 分时行情-盘前
:rtype: pandas.DataFrame
"""
market_type = {"sh": "1", "sz": "0"}
url = "https://push2.eastmoney.com/api/qt/stock/trends2/get"
params = {
"fields1": "f1,f2,f3,f4,f5,f6,f7,f8,f9,f10,f11,f12,f13",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58",
"ndays": "1",
"iscr": "1",
"iscca": "0",
"secid": f"{market_type[symbol[:2]]}.{symbol[2:]}",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame([item.split(",") for item in data_json["data"]["trends"]])
temp_df.columns = [
"时间",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"最新价",
]
temp_df.index = pd.to_datetime(temp_df["时间"])
temp_df.reset_index(drop=True, inplace=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["时间"] = pd.to_datetime(temp_df["时间"]).astype(str)
return temp_df
def bond_zh_cov() -> pd.DataFrame:
"""
东方财富网-数据中心-新股数据-可转债数据
https://data.eastmoney.com/kzz/default.html
:return: 可转债数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"sortColumns": "PUBLIC_START_DATE",
"sortTypes": "-1",
"pageSize": "500",
"pageNumber": "1",
"reportName": "RPT_BOND_CB_LIST",
"columns": "ALL",
"quoteColumns": "f2~01~CONVERT_STOCK_CODE~CONVERT_STOCK_PRICE,"
"f235~10~SECURITY_CODE~TRANSFER_PRICE,f236~10~SECURITY_CODE~TRANSFER_VALUE,"
"f2~10~SECURITY_CODE~CURRENT_BOND_PRICE,f237~10~SECURITY_CODE~TRANSFER_PREMIUM_RATIO,"
"f239~10~SECURITY_CODE~RESALE_TRIG_PRICE,f240~10~SECURITY_CODE~REDEEM_TRIG_PRICE,"
"f23~01~CONVERT_STOCK_CODE~PBV_RATIO",
"source": "WEB",
"client": "WEB",
}
r = requests.get(url, params=params)
data_json = r.json()
total_page = data_json["result"]["pages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(1, total_page + 1), leave=False):
params.update({"pageNumber": page})
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.columns = [
"债券代码",
"_",
"_",
"债券简称",
"_",
"上市时间",
"正股代码",
"_",
"信用评级",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"发行规模",
"申购上限",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"申购代码",
"_",
"申购日期",
"_",
"_",
"中签号发布日",
"原股东配售-股权登记日",
"正股简称",
"原股东配售-每股配售额",
"_",
"中签率",
"-",
"_",
"_",
"_",
"_",
"_",
"正股价",
"转股价",
"转股价值",
"债现价",
"转股溢价率",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
]
big_df = big_df[
[
"债券代码",
"债券简称",
"申购日期",
"申购代码",
"申购上限",
"正股代码",
"正股简称",
"正股价",
"转股价",
"转股价值",
"债现价",
"转股溢价率",
"原股东配售-股权登记日",
"原股东配售-每股配售额",
"发行规模",
"中签号发布日",
"中签率",
"上市时间",
"信用评级",
]
]
big_df["申购上限"] = pd.to_numeric(big_df["申购上限"], errors="coerce")
big_df["正股价"] = pd.to_numeric(big_df["正股价"], errors="coerce")
big_df["转股价"] = pd.to_numeric(big_df["转股价"], errors="coerce")
big_df["转股价值"] = pd.to_numeric(big_df["转股价值"], errors="coerce")
big_df["债现价"] = pd.to_numeric(big_df["债现价"], errors="coerce")
big_df["转股溢价率"] = pd.to_numeric(big_df["转股溢价率"], errors="coerce")
big_df["原股东配售-每股配售额"] = pd.to_numeric(
big_df["原股东配售-每股配售额"], errors="coerce"
)
big_df["发行规模"] = pd.to_numeric(big_df["发行规模"], errors="coerce")
big_df["中签率"] = pd.to_numeric(big_df["中签率"], errors="coerce")
big_df["中签号发布日"] = pd.to_datetime(
big_df["中签号发布日"], errors="coerce"
).dt.date
big_df["上市时间"] = pd.to_datetime(big_df["上市时间"], errors="coerce").dt.date
big_df["申购日期"] = pd.to_datetime(big_df["申购日期"], errors="coerce").dt.date
big_df["原股东配售-股权登记日"] = pd.to_datetime(
big_df["原股东配售-股权登记日"], errors="coerce"
).dt.date
big_df["债现价"] = big_df["债现价"].fillna(100)
return big_df
def bond_cov_comparison() -> pd.DataFrame:
"""
东方财富网-行情中心-债券市场-可转债比价表
https://quote.eastmoney.com/center/fullscreenlist.html#convertible_comparison
:return: 可转债比价表数据
:rtype: pandas.DataFrame
"""
url = "https://16.push2.eastmoney.com/api/qt/clist/get"
params = {
"pn": "1",
"pz": "100",
"po": "1",
"np": "1",
"ut": "bd1d9ddb04089700cf9c27f6f7426281",
"fltt": "2",
"invt": "2",
"fid": "f243",
"fs": "b:MK0354",
"fields": "f1,f152,f2,f3,f12,f13,f14,f227,f228,f229,f230,f231,f232,f233,f234,"
"f235,f236,f237,f238,f239,f240,f241,f242,f26,f243",
}
temp_df = fetch_paginated_data(url, params)
temp_df.columns = [
"序号",
"_",
"转债最新价",
"转债涨跌幅",
"转债代码",
"_",
"转债名称",
"上市日期",
"_",
"纯债价值",
"_",
"正股最新价",
"正股涨跌幅",
"_",
"正股代码",
"_",
"正股名称",
"转股价",
"转股价值",
"转股溢价率",
"纯债溢价率",
"回售触发价",
"强赎触发价",
"到期赎回价",
"开始转股日",
"申购日期",
]
temp_df = temp_df[
[
"序号",
"转债代码",
"转债名称",
"转债最新价",
"转债涨跌幅",
"正股代码",
"正股名称",
"正股最新价",
"正股涨跌幅",
"转股价",
"转股价值",
"转股溢价率",
"纯债溢价率",
"回售触发价",
"强赎触发价",
"到期赎回价",
"纯债价值",
"开始转股日",
"上市日期",
"申购日期",
]
]
return temp_df
def bond_zh_cov_info(
symbol: str = "123121", indicator: str = "基本信息"
) -> pd.DataFrame:
"""
https://data.eastmoney.com/kzz/detail/123121.html
东方财富网-数据中心-新股数据-可转债详情
:param symbol: 可转债代码
:type symbol: str
:param indicator: choice of {"基本信息", "中签号", "筹资用途", "重要日期"}
:type indicator: str
:return: 可转债详情
:rtype: pandas.DataFrame
"""
indicator_map = {
"基本信息": "RPT_BOND_CB_LIST",
"中签号": "RPT_CB_BALLOTNUM",
"筹资用途": "RPT_BOND_BS_OPRFINVESTITEM",
"重要日期": "RPT_CB_IMPORTANTDATE",
}
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_BOND_CB_LIST",
"columns": "ALL",
"quoteColumns": "f2~01~CONVERT_STOCK_CODE~CONVERT_STOCK_PRICE,f235~10~SECURITY_CODE~TRANSFER_PRICE,"
"f236~10~SECURITY_CODE~TRANSFER_VALUE,f2~10~SECURITY_CODE~CURRENT_BOND_PRICE,"
"f237~10~SECURITY_CODE~TRANSFER_PREMIUM_RATIO,f239~10~SECURITY_CODE~RESALE_TRIG_PRICE,"
"f240~10~SECURITY_CODE~REDEEM_TRIG_PRICE,f23~01~CONVERT_STOCK_CODE~PBV_RATIO",
"quoteType": "0",
"source": "WEB",
"client": "WEB",
"filter": f'(SECURITY_CODE="{symbol}")',
}
if indicator == "基本信息":
params.update(
{
"reportName": indicator_map[indicator],
"quoteColumns": "f2~01~CONVERT_STOCK_CODE~CONVERT_STOCK_PRICE,f235~10~SECURITY_CODE~TRANSFER_PRICE,"
"f236~10~SECURITY_CODE~TRANSFER_VALUE,f2~10~SECURITY_CODE~CURRENT_BOND_PRICE,"
"f237~10~SECURITY_CODE~TRANSFER_PREMIUM_RATIO,f239~10~SECURITY_CODE~RESALE_TRIG_PRICE,"
"f240~10~SECURITY_CODE~REDEEM_TRIG_PRICE,f23~01~CONVERT_STOCK_CODE~PBV_RATIO",
}
)
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(data_json["result"]["data"])
return temp_df
elif indicator == "中签号":
params.update(
{
"reportName": indicator_map[indicator],
"quoteColumns": "",
}
)
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(data_json["result"]["data"])
return temp_df
elif indicator == "筹资用途":
params.update(
{
"reportName": indicator_map[indicator],
"quoteColumns": "",
"sortColumns": "SORT",
"sortTypes": "1",
}
)
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(data_json["result"]["data"])
return temp_df
elif indicator == "重要日期":
params.update(
{
"reportName": indicator_map[indicator],
"quoteColumns": "",
}
)
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame.from_dict(data_json["result"]["data"])
return temp_df
else:
return pd.DataFrame()
def bond_zh_cov_value_analysis(symbol: str = "113527") -> pd.DataFrame:
"""
https://data.eastmoney.com/kzz/detail/113527.html
东方财富网-数据中心-新股数据-可转债数据-价值分析-溢价率分析
:param symbol: 可转债代码
:type symbol: str
:return: 可转债价值分析
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/get"
params = {
"sty": "ALL",
"token": "894050c76af8597a853f5b408b759f5d",
"st": "date",
"sr": "1",
"source": "WEB",
"type": "RPTA_WEB_KZZ_LS",
"filter": f'(zcode="{symbol}")',
"p": "1",
"ps": "8000",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"日期",
"-",
"-",
"转股价值",
"纯债价值",
"纯债溢价率",
"转股溢价率",
"收盘价",
"-",
"-",
"-",
"-",
"-",
]
temp_df = temp_df[
[
"日期",
"收盘价",
"纯债价值",
"转股价值",
"纯债溢价率",
"转股溢价率",
]
]
temp_df["收盘价"] = pd.to_numeric(temp_df["收盘价"], errors="coerce")
temp_df["纯债价值"] = pd.to_numeric(temp_df["纯债价值"], errors="coerce")
temp_df["转股价值"] = pd.to_numeric(temp_df["转股价值"], errors="coerce")
temp_df["纯债溢价率"] = pd.to_numeric(temp_df["纯债溢价率"], errors="coerce")
temp_df["转股溢价率"] = pd.to_numeric(temp_df["转股溢价率"], errors="coerce")
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
return temp_df
if __name__ == "__main__":
bond_zh_hs_cov_min_df = bond_zh_hs_cov_min(
symbol="sz128039",
period="1",
adjust="hfq",
start_date="1979-09-01 09:32:00",
end_date="2222-01-01 09:32:00",
)
print(bond_zh_hs_cov_min_df)
bond_zh_hs_cov_pre_min_df = bond_zh_hs_cov_pre_min(symbol="sz128039")
print(bond_zh_hs_cov_pre_min_df)
bond_zh_hs_cov_daily_df = bond_zh_hs_cov_daily(symbol="sz128039")
print(bond_zh_hs_cov_daily_df)
bond_zh_hs_cov_spot_df = bond_zh_hs_cov_spot()
print(bond_zh_hs_cov_spot_df)
bond_zh_cov_df = bond_zh_cov()
print(bond_zh_cov_df)
bond_cov_comparison_df = bond_cov_comparison()
print(bond_cov_comparison_df)
bond_zh_cov_info_df = bond_zh_cov_info(symbol="123121", indicator="基本信息")
print(bond_zh_cov_info_df)
bond_zh_cov_value_analysis_df = bond_zh_cov_value_analysis(symbol="113527")
print(bond_zh_cov_value_analysis_df)
@@ -0,0 +1,151 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/6/18 18:30
Desc: 新浪财经-债券-沪深债券-实时行情数据和历史行情数据
https://vip.stock.finance.sina.com.cn/mkt/#hs_z
"""
import datetime
import re
import pandas as pd
import requests
import py_mini_racer
from akshare.bond.cons import (
zh_sina_bond_hs_count_url,
zh_sina_bond_hs_payload,
zh_sina_bond_hs_url,
zh_sina_bond_hs_hist_url,
)
from akshare.stock.cons import hk_js_decode
from akshare.utils import demjson
from akshare.utils.tqdm import get_tqdm
def get_zh_bond_hs_page_count() -> int:
"""
行情中心首页-债券-沪深债券的总页数
https://vip.stock.finance.sina.com.cn/mkt/#hs_z
:return: 总页数
:rtype: int
"""
params = {
"node": "hs_z",
}
res = requests.get(zh_sina_bond_hs_count_url, params=params)
page_count = int(re.findall(re.compile(r"\d+"), res.text)[0]) / 80
if isinstance(page_count, int):
return page_count
else:
return int(page_count) + 1
def bond_zh_hs_spot(start_page: str = "1", end_page: str = "10") -> pd.DataFrame:
"""
新浪财经-债券-沪深债券-实时行情数据, 大量抓取容易封IP
https://vip.stock.finance.sina.com.cn/mkt/#hs_z
:param start_page: 分页起始页
:type start_page: str
:param end_page: 分页结束页
:type end_page: str
:return: 所有沪深债券在当前时刻的实时行情数据
:rtype: pandas.DataFrame
"""
page_count = get_zh_bond_hs_page_count()
page_count = int(page_count)
zh_sina_bond_hs_payload_copy = zh_sina_bond_hs_payload.copy()
tqdm = get_tqdm()
big_df = pd.DataFrame()
start_page = int(start_page)
end_page = int(end_page) + 1 if int(end_page) + 1 <= page_count else page_count
for page in tqdm(range(start_page, end_page), leave=False):
zh_sina_bond_hs_payload_copy.update({"page": page})
r = requests.get(zh_sina_bond_hs_url, params=zh_sina_bond_hs_payload_copy)
data_json = demjson.decode(r.text)
temp_df = pd.DataFrame(data_json)
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.columns = [
"代码",
"-",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"买入",
"卖出",
"昨收",
"今开",
"最高",
"最低",
"成交量",
"成交额",
"-",
"-",
"-",
"-",
"-",
"-",
]
big_df = big_df[
[
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"买入",
"卖出",
"昨收",
"今开",
"最高",
"最低",
"成交量",
"成交额",
]
]
big_df["买入"] = pd.to_numeric(big_df["买入"], errors="coerce")
big_df["卖出"] = pd.to_numeric(big_df["卖出"], errors="coerce")
big_df["昨收"] = pd.to_numeric(big_df["昨收"], errors="coerce")
big_df["今开"] = pd.to_numeric(big_df["今开"], errors="coerce")
big_df["最高"] = pd.to_numeric(big_df["最高"], errors="coerce")
big_df["最低"] = pd.to_numeric(big_df["最低"], errors="coerce")
big_df["最新价"] = pd.to_numeric(big_df["最新价"], errors="coerce")
return big_df
def bond_zh_hs_daily(symbol: str = "sh010107") -> pd.DataFrame:
"""
新浪财经-债券-沪深债券-历史行情数据, 大量抓取容易封 IP
https://vip.stock.finance.sina.com.cn/mkt/#hs_z
:param symbol: 沪深债券代码; e.g., sh010107
:type symbol: str
:return: 指定沪深债券代码的日 K 线数据
:rtype: pandas.DataFrame
"""
r = requests.get(
zh_sina_bond_hs_hist_url.format(
symbol, datetime.datetime.now().strftime("%Y_%m_%d")
)
)
js_code = py_mini_racer.MiniRacer()
js_code.eval(hk_js_decode)
dict_list = js_code.call(
"d", r.text.split("=")[1].split(";")[0].replace('"', "")
) # 执行 js 解密代码
data_df = pd.DataFrame(dict_list)
data_df["date"] = pd.to_datetime(data_df["date"], errors="coerce").dt.date
data_df["open"] = pd.to_numeric(data_df["open"], errors="coerce")
data_df["high"] = pd.to_numeric(data_df["high"], errors="coerce")
data_df["low"] = pd.to_numeric(data_df["low"], errors="coerce")
data_df["close"] = pd.to_numeric(data_df["close"], errors="coerce")
return data_df
if __name__ == "__main__":
bond_zh_hs_spot_df = bond_zh_hs_spot(start_page="1", end_page="5")
print(bond_zh_hs_spot_df)
bond_zh_hs_daily_df = bond_zh_hs_daily(symbol="sh010107")
print(bond_zh_hs_daily_df)
@@ -0,0 +1,408 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/4/10 10:21
Desc: 债券配置文件
"""
INDEX_MAPPING: dict[str, str] = {
"新综合指数": "8a8b2ca0332abed20134ea76d8885831",
"高等级科技创新债券综合指数": "4d4aa3607fb4ba663b4587de4a624b24",
"长江养老年金基金债券指数": "5846dca288299ac125539d6600c07853",
"中信证券挂钩DR浮动利率政策性银行债活跃券指数": "11c92fe0df3940c3ea172bfec5126593",
"股份制商业银行同业存单指数": "1398633fe32c4076f596530652d2f9bb",
"金融高质量发展主题信用债指数": "20e35c92ef7b9a439fcaa8fce5835ea5",
"交易所国债指数": "2c9081e50e8767dc010e87a4bdd20041",
"进出口行债券总指数": "8a8b2ca054ef4e4e0154f0c515eb0002",
"市场隐含评级AA信用债指数": "8a8b2cef6ab893c2016aba4c8ee7009f",
"房地产行业信用债指数": "8a8b2cef73b68e6a0173b92f5e1774c5",
"重庆市地方政府债指数": "8a8b2cef744be6d401744ebe4e6568c2",
"甘肃省地方政府债指数": "8a8b2cef74608045017461d9115400c8",
"公司信用类科技创新债券指数": "8641b0cb4c1f39c372dbcf5516b9c615",
"长三角绿色债券指数": "8a8b2c8364aa0bb20164abfd957f000f",
"企业债AA-指数": "8a8b2ca0406a93470140800885d20b7f",
"中国高等级债券指数": "8a8b2ca047bd1dfe0147d317b62e2158",
"中高等级公司信用类债券指数": "ef82cc4ba2540191dcdce19559153a3d",
"系统重要性银行债券指数": "928c2552e9b15d784f02b13b53392d53",
"红利现金流高等级股债金波动率控制1.5%指数": "b6b0f49ce87604657e97133968cb85bc",
"中高等级粤港澳大湾区绿色债券指数": "cc2b58ce2230e6097b7b32447406c783",
"投资级公司信用债综合指数": "4e808b033318be271f9b2063693a12ef",
"中高等级绿色金融债券指数": "562d8e2d9d331c99a7a9f9fefded6907",
"高等级科技创新债券指数": "0366fa8fafe2d1b12c62e4ffe11b97fe",
"北京农商银行中高信用等级农村商业银行金融债券指数": "185bb3883f838a1fdfe60e9ca37f4b43",
"货币市场基金可投资债券指数": "2c9081e918ad26f40118e90afbee66ae",
"高信用等级债券指数": "2c9081e91da03927011dcc4fae9f6171",
"非银金融行业信用债指数": "3396aaec56be7ba3378976c9387380f3",
"商业银行无固定期限资本债券市场隐含评级AA指数": "3d75e320abd5c3440ddd156de1ee622e",
"京津冀公司信用类债券指数": "8a8b2cef6d4bc1c2016d4ca23ef4251b",
"京津冀债券综合指数": "8a8b2cef6d4bc1c2016d4caa15e8254a",
"工行关键期限国债指数": "8a8b2cef6e1ee681016e200a8aa50400",
"广东省地方政府债指数": "8a8b2cef7109a09c01710c14d2a74415",
"厦门市地方政府债指数": "8a8b2cef732135fd017322a8e7c80113",
"商业银行无固定期限资本债券AAA指数": "6b12c39d52c331dd5e3d1aabc4d9b5a6",
"粤港澳大湾区绿色债券综合指数": "7fd4e2eda73794d409e592448adb8c25",
"中高等级科技创新绿色普惠主题信用债指数": "865e39d03b6fd073781dbf1477a6cca1",
"红利自由现金流低波股债恒定比例10/90指数": "8961444e141891490cba185d6b59cba2",
"高信用等级企业债指数": "8a8b2ca03e4dd765013e6312d6462a1b",
"农行乡村振兴债券指数": "e8df331cfd44e54f338bf2811716c6da",
"城市商业银行及农村商业银行同业存单AAA指数": "8b8f70506d65f4675233a32c903ad552",
"股债恒定组合10/90指数": "978a5b988dfe640d0d083981803d0675",
"国信证券深圳市国有企业信用债精选指数": "9d895a4e2d56d6829590a5eb3ccf285d",
"商业银行无固定期限资本债券指数": "a096ce5c63c2a1df2240b876c868c3ed",
"银行间碳中和债券指数": "ac478f286376cf14bf6cbc68ca0aa284",
"中高等级信用债综合指数": "b10fd010c80946bf881ca39dca62e49a",
"贵阳银行西部高质量发展信用债精选指数": "c1dc7e964c26475afa239b00594b8275",
"投资优选国际信用评级投资级活跃信用债指数": "d20fbfd3ed04a7261a0572967ffc06c3",
"红利现金流高等级股债金波动率控制1%指数": "188b64de57c782a3b8a9359ff08f113d",
"东方证券科技创新信用债精选指数": "2adeb5d8aa35cbcb0ea4a05614a75a08",
"进出口行新发关键期限债券指数": "2e8da3759b4f83e0f0752147738f7fc9",
"商业银行二级资本债券AAA指数": "3f6da52f1d57886271979d928af5a203",
"粤港澳大湾区信用债指数": "8a8b2cef74b8f0c10174bac93afe436a",
"投资优选信用债指数": "8a8b2cef771ce12601771df60d924fdb",
"科技创新绿色普惠主题信用债指数": "6b227923cd44064bbf239a69f70f09ae",
"中国高等级债券指数(美元)": "8a8b2c8f581cfb2f01581db3fd830001",
"信用债总指数": "8a8b2ca038d716f10138dadde8416adc",
"高等级科技创新及绿色债券指数": "f1df5dcfb61be8a2fbcbc119db98b149",
"中邮理财高等级绿色债券精选指数": "f22aea49f4b11a53bd787b013253d5be",
"平安人寿ESG整合策略信用债指数": "f711877ede9c7aa67bfe326721c2137e",
"战略性新兴产业信用债指数": "f72725181b56144d3f9b55f1b6e60102",
"商业银行债券AAA指数": "9883fcadeac6d8c22204f0c749e4cf08",
"AAA评级债券综合指数": "b017c9c53c7ad6586b3446129c152616",
"高等级黄河流域绿色债券指数": "bfbeeed1994639dcd0e0b94fda306b56",
"高等级公司信用类债券综合指数": "c9a7185542022826b09dcc2ab72be8b1",
"中信证券高等级同业存单指数": "0857793c945697daf6a9873ff42825f4",
"浦银理财新质生产力发展债券指数": "103c0fdb82c06b6b9d7ec09f28b8b615",
"银行间国债指数": "2c9081e50e8767dc010e87b559ee0078",
"交易所高等级科技创新债券指数": "44a33e0c99dffbce14774eb52415a5b0",
"银行间资产支持证券指数": "8a8b2ca055eba5e10155ed6ebc530895",
"中国气候相关债券指数": "8a8b2ca056b9a4450156bb2be8df0002",
"招商银行优选信用债指数": "8a8b2cef6dd6cd77016dd88a7e7d002c",
"福建省地方政府债指数": "8a8b2cef732135fd017322145858008e",
"市场隐含评级AA+及以上信用债指数": "8a8b2cef734f8f3701735061131b014a",
"青海省地方政府债指数": "8a8b2cef74608045017461f9e203012a",
"红利自由现金流低波股债恒定比例25/75指数": "6bae070303eed9cf867fd5011a0e47bb",
"投资优选信用债分散指数": "6dd638194bb5a5f2de90bd7133192953",
"高信用等级城市商业银行及农村商业银行债券指数": "81303c95d362b50182547f7385469b7b",
"金融机构二级资本债券总指数": "8a8b2c8368edcfd70168f08992c6153a",
"新中期票据总指数": "8a8b2ca0375f977f0138c2c322474b06",
"高收益中期票据指数": "8a8b2ca03e29cab5013e3a180e064537",
"商业银行二级资本债券指数": "b379a2dacd92d19ca805021c0d336ee8",
"高信用等级商业银行无固定期限及二级资本债券指数": "ca7f4de2681f726e0d1268fd6f646788",
"银行间科技创新债券指数": "4bde3b669a49e81e8de90e8df7687128",
"金融行业信用债指数": "594b0c6f18d6dd3c6af0830d784058fa",
"高等级科技创新债券行业精选指数": "1287a4c6c7bce84cbe9eab904468b9d5",
"固定利率债券指数": "2c9081e50e8767dc010e87954b780011",
"中信证券挂钩LPR浮动利率政策性银行债活跃券指数": "430f1876233c711f505500edce079236",
"广西壮族自治区公司信用类债券指数": "8a8b2cef6b00accd016b022cffbb0009",
"长三角债券综合指数": "8a8b2cef6b29dfac016b2bc115460040",
"个人住房抵押贷款资产支持证券指数": "8a8b2cef6b96053a016b982c95e7001f",
"青岛市地方政府债指数": "8a8b2cef7307763001730a5c824524ce",
"煤炭行业信用债指数": "8a8b2cef73bbb4c60173bc59a0c90006",
"安徽省公司信用类债券指数": "8a8b2c8367bdf89e0167c05355f201fb",
"企业债AA+指数": "8a8b2ca0408e9fa701409edf078f26c0",
"挂钩DR浮动利率政策性银行债指数": "db78a8ddda8a6ac88bc193055906740a",
"红利自由现金流低波股债恒定比例20/80指数": "e638c5f176c772ddaf59e947af2d052e",
"金融机构科技创新债券指数": "ecac759d61e1c09314d6f2577c20ce6c",
"中豫信增河南省信用债指数": "f7948f9be0732d45e18f1d5c8190757f",
"红利现金流中高等级股债金波动率控制1%指数": "8a9ab2cac146e25febba515cfa08d8cc",
"电力行业优质转型企业信用债指数": "947d07b68357a6e40c93bf839efc2187",
"工行熊猫债30指数": "9eee3a194d1f035ce0cf4307a5b9b69f",
"申万宏源ESG绿色信用债精选指数": "a3dc0ed6ba8ab442783109d769baed5e",
"天府信用增进公司增信债券指数": "aa0b6304e290a57bcda90e1358e13de9",
"京津冀绿色债券综合指数": "d0df76dc4485ecd520c870d81703645c",
"高等级科技创新绿色普惠主题信用债指数": "61c04cb52c2decb1cbba80292ab46ccd",
"高信用等级数字经济产业信用债指数": "373e09025763c56cf01201234a794658",
"中银理财高等级乡村振兴债券指数": "398f40c1c8dd2081f6e1ee478b768dbb",
"国有大型商业银行及股份制商业银行债券指数": "469f1601d2b76750b82945b145e90992",
"民营企业公司信用类债券指数": "8a8b2cef6b4dec2d016b4ebb4ec36c3f",
"湖南省地方政府债指数": "8a8b2cef7132d3800171333ba262010c",
"贵州省地方政府债指数": "8a8b2cef730c9c8f01730e79bade0185",
"新疆维吾尔自治区(新疆生产建设兵团)地方政府债指数": "8a8b2cef7465a6a201746603d1a1005d",
"国寿资产ESG信用债精选指数": "8a8b2cef7a11e7fc017a13fe7446002a",
"中邮理财高等级科技创新债券精选指数": "773ade3d59c36dc1e13146c1866a8ccb",
"平安理财ESG优选绿色债券指数": "89019c1cbbe64a34698165eecc7e7417",
"中高等级公司债利差因子指数": "8a8b2c836393f4480163950643d92795",
"长三角公司信用类债券指数": "8a8b2c83649fbee90164a24dbbc00013",
"中信证券精选高等级资产支持证券指数": "8a8b2c83689643bc0168985a433e000e",
"交易所科技创新债券指数": "963fc157a1f34898dd4071a355ea13bd",
"中银理财高信用等级同业存单指数": "987527eff930a4986a5044a80cadae9e",
"中银绿色债券指数": "abea1402e6dd628d02118bca571783cb",
"国有大型商业银行同业存单指数": "af109288145de0c9a36332a4fb3d06c1",
"中高等级长江经济带绿色债券指数": "d3c82122ac871f08eb5bf877065e5377",
"AAA信用债综合指数": "05d235f4268241c25e36b27e13b13023",
"红利自由现金流低波股债金恒定比例指数": "0ff243f048cbd219f59fb92ab8ae4941",
"申万宏源中小微企业主题优选信用债指数": "1997fbc5e0a91db36e53c4540ae51cdd",
"企业债总指数": "2c90818811d3f4fa01123837e6b30d4a",
"商业银行债券指数": "2c9081e918ad26f401195c3a76a7210f",
"公司债总指数": "8a8b2ca050d9e35d0150da6758462c78",
"长江经济带债券综合指数": "8a8b2cef709854b501709a027fe4002f",
"信用债价值因子权重调整策略指数": "8a8b2cef7422b3f30174234f30fd0005",
"黑龙江省地方政府债指数": "8a8b2cef7456338c017457a55ccc07cc",
"碳中和绿色债券指数": "8a8b2cef7823857e01782469e9210080",
"投资优选政策性金融债指数": "8a8b2cef7a404137017a424e54cb7859",
"中金公司乡村振兴信用债精选指数": "8a8b2cef7a4fb448017a515401a53fc4",
"高等级公司信用类债券指数": "6fb584528c4d4aad6194d5a39a3b93a1",
"京津冀科技创新债券指数": "74bdb50a9cbf9a45903346968a951bd3",
"渤海银行新质生产力主题科技创新债券指数": "81a92ec45e9d90aa8961e9ac278fc435",
"长三角地方政府债指数": "8a8b2c836303c237016304feb2160006",
"AAA科技创新债券指数": "dff644648a8a007efd6a5b94970c0b89",
"投资级中资美元债指数": "8a962d8c69c31e1e016a0f26a9c0010a",
"成渝地区双城经济圈国有企业信用债精选指数": "03ffb378810766ab90ec7e959fadc3c0",
"投资优选活跃信用债指数": "103a161c9927a9ae41e38f0887bbd33e",
"北银理财绿色发展风险平价指数": "2c666b22d481c7eadb52992baa62591c",
"中高等级科技创新债券综合指数": "3b02fa47414f502add64f1e77e9e67b7",
"个人住房抵押贷款资产支持证券精选指数": "3b824a1426bea356799ca15d730ad6d1",
"红利自由现金流低波股债金恒定比例10/85/5指数": "48643ba4f9bd31f07ec8efdc44ebf761",
"高信用等级同业存单指数": "48fc8dfb472c5498c6612cd5151647d8",
"中国绿色债券精选指数": "8a8b2ca053fd435d0153fefc94100001",
"长三角中高等级信用债指数": "8a8b2cef6b4dec2d016b4fc04e286e57",
"江西省地方政府债指数": "8a8b2cef732135fd017321b8405e0005",
"江苏省地方政府债指数": "8a8b2c8368a5b6da0168a6bd29e80017",
"中信证券国债及地方政府债精选指数": "8a8b2c83694a824d01694c5d53d6000a",
"国债及政策性银行债指数": "8a8b2c8f5a62e9ca015a645fe3b60001",
"高信用等级公司信用类债券综合指数": "8a8b2ca038f905c70139b9b3ab9660bb",
"银行间高等级科技创新债券指数": "e4498669d5496afed08bdf7ff8695681",
"公路行业信用债指数": "e65b5cdf6e3e04c7892bdfd1ccc1e2dc",
"投资优选国际信用评级投资级信用债分散指数": "f5517678561c457f03b6d74c06440a3d",
"高信用等级农村商业银行债券优选指数": "f8cbf35f3095aa44006f7fc7c506176d",
"科技创新债券指数": "a485ef64ce0ae0f1f5cc088671e87d8f",
"科技创新债券综合指数": "afb3fe2d59b5165a0175bac95b8c3da0",
"高等级信用债指数": "d04f2fb3e1012c78b8acdecf2c93979f",
"中高等级公司信用类债券综合指数": "5911892524d8b384666a88d75200c9df",
"中高等级京津冀绿色债券指数": "00474c7a00eb73ca32a23a6861b4a418",
"城市商业银行及农村商业银行债券AAA指数": "13fe6e5cd6a84a3038b8a5d46c7a38cb",
"浦发银行绿色低碳股债优选指数": "2bdda0eb4cac30c07217f95a25a7a85f",
"金融债券总指数": "2c9081e50e8767dc010e87a9d5650060",
"离岸人民币中国主权及政策性金融债指数": "8a8b2cef6dcc80c0016dcf2444650bb7",
"安徽省地方政府债指数": "8a8b2cef7311c2e7017312b23a650130",
"AA国有企业信用债优选指数": "6b0d067864ff1675e96f3c49652fb73e",
"中高等级信用债指数": "6cdea6720316fd5d69494b4bc0f8129c",
"工行熊猫债AAA指数": "738751b4c9e76c9b7701fb0c201b70f1",
"国有大型商业银行及股份制商业银行同业存单指数": "78598fc1ac4a8f2d327577e0481b065c",
"黄金保值国开行债券风险平价指数": "806f9278922270298ee3e12c6d624ee5",
"交行长三角ESG优选信用债指数": "ebd9f5ac057709c3fe5a375773e0c62d",
"中信证券ESG优选信用债指数": "ece99ed16ea8c4c9d59befed1175f823",
"数字经济产业信用债指数": "fa87c88adac6b304de5654c29b1569e1",
"投资级公司信用债精选指数": "8d397b018e0ce97d58dedc3ef41ddf36",
"中信证券久期轮动政策性金融债指数": "9c6218292a77139d38f12ac6ef85d138",
"红利自由现金流低波股债恒定比例30/70指数": "d33a29eb4d1e1111af1e4b7097cca597",
"高等级信用债综合指数": "5b78d41604e06e90b720144a6a956c67",
"投资级公司科技创新债券精选指数": "0572b7d527231c98e4fc0de8abe2c7c2",
"交易所信用债AAA指数": "05f743ba6a11b907de8307b89c4fc618",
"高信用等级城市商业银行及农村商业银行同业存单指数": "0bb01422038bb4086e8baa8f648574e8",
"高信用等级商业银行债券指数": "1a985201e4c5ceecdde9610e43a0fd35",
"投资优选科技创新债券指数": "2ac380e3d3d941de8351f1fff8e6bda5",
"固定利率金融债指数": "2c9081e50e8767dc010e87ad08140068",
"银行间高等级碳中和债券指数": "37a60515edb02fe8dab961d9c7035a95",
"同业存单AA+指数": "429c1ff7661c2abacdbcb5718a3cb5f6",
"平安-可投资级信用债指数": "8a8b2ca0515fc8a60151618b84483c9a",
"农发行债券总指数": "8a8b2ca0540790160154091b513d370e",
"浙江省地方政府债指数": "8a8b2cef7109a09c01710c1c2d04478e",
"上海市地方政府债指数": "8a8b2cef7408f4280174096a89a04112",
"陕西省地方政府债指数": "8a8b2cef74510d2f01745168e5670004",
"资产支持证券指数": "8a8b2cef74510d2f0174529d5a9f35b4",
"吉林省地方政府债指数": "8a8b2cef74608045017461ccceff0073",
"海南省地方政府债指数": "8a8b2cef74608045017461fe1768015f",
"ESG优选信用债指数": "8a8b2cef75860ac0017587c644a02fde",
"中金公司绿色资产支持证券指数": "8a8b2cef783d454901783f2c468307ec",
"市场隐含评级AA+信用债指数": "8a8b2c836775df980167784a77520d4b",
"同业存单总指数": "8a8b2c8f611af5db01611cb3586c00f0",
"公司信用类债券指数": "8a8b2ca03a59370a013a676d717923da",
"高收益企业债指数": "8a8b2ca03e88932b013e88b9d6290001",
"企业债AAA指数": "8a8b2ca0408e9fa7014094a20f21001f",
"AAA公司信用类债券综合指数": "e6b1e2fc01692f8fcd22ba50e501231a",
"AAA公司信用类债券指数": "96377056fc894287b4a76ceebaca2808",
"投资优选绿色债券指数": "984c68bfc0b9263aaad7bd9af36888a3",
"系统重要性银行同业存单指数": "a08e1c9454a616491f5bf6431f2591b0",
"投资级主题绿色债券优选指数": "be73e8263fc20359521707abd6db45b3",
"高等级央企信用债精选指数": "cbfd21590b4805df8df7d9de222f8f7d",
"红利现金流中高等级股债波动率控制1.5%指数": "d31602c38de87265603df05d6cf9dd59",
"中高等级科技创新及绿色债券指数": "5ec55de5ac980c543c2d9bf25d6e423b",
"金融高质量发展主题债券综合指数": "60bb107af9b99b8fb7c6a28ef4b171da",
"商业银行无固定期限及二级资本债券指数": "0b96ff2a2948a75625e2319b49446633",
"国开行债券总指数": "2c908188111fac07011125068f91044d",
"综合指数": "2c90818811afed8d0111c0c672b31578",
"固定利率企业债指数": "2c9081e918ad26f40118adb5d6910004",
"中期票据总指数": "2c9081e91ebc9e41011ec8c7c0440001",
"黄金保值债券风险平价指数": "3b9c19a3dd638fd2672c0728fce892a0",
"广西壮族自治区地方政府债指数": "8a8b2cef7311c2e7017313a860bb03dc",
"新疆维吾尔自治区地方政府债指数": "8a8b2cef74510d2f017453365ea0367c",
"天津市地方政府债指数": "8a8b2cef7456338c017458e2e0da3e33",
"投资优选综合指数": "8a8b2cef7682625f0176835c7a840070",
"绿色债券综合指数": "85f86947411dd367018d7f8fde1dc295",
"市场隐含评级AAA信用债指数": "8a8b2c836775df980167785153790d6b",
"中国铁路债券指数": "8a8b2c8f5bea4d1b015bebe640530038",
"企业债AA指数": "8a8b2ca0408e9fa70140949f012d0002",
"地方政府债指数": "8a8b2ca0447ffe14014486b77f2a0002",
"国泰海通陕川渝国企信用增强债券精选指数": "de861828ae11bc5f498a330c650fdf5a",
"银行间高等级绿色债券指数": "9fa9718155dceab39e5149af665f68a7",
"红利现金流高等级股债波动率控制1.5%指数": "a7f952e6f6ad14b1c66f5f950ed476de",
"红利自由现金流低波股债恒定比例5/95指数": "c3bb7afced9999ce291380c0fc4dbca5",
"绿色普惠主题金融债券优选指数": "d69df7413ed6e76fa5b9b20ba9e7c0ec",
"建筑工程行业信用债指数": "0af700ba10feefc9a5191983eaadfc51",
"长三角绿色债券综合指数": "2551cfa3eea577a3ca71d51bceca6f8f",
"银行间债券总指数": "2c9081e50e8767dc010e87a3326c0039",
"交易所AAA科技创新债券指数": "2d90f08c90b2e886bf6f6df549af950c",
"AAA信用债指数": "3a2e8c74d7265e3e9aedfd8d1681836b",
"银行间市场信用债AAA指数": "3c94ebab97ab6edf12ca14e452977115",
"共同富裕主题债券指数": "430a7631f7ea66036a91f37e8b4b1c9c",
"中国绿色债券指数": "8a8b2ca054079016015408674cce0017",
"优选投资级信用债指数": "8a8b2cef771294700177144288381a6c",
"投资优选地方政府债指数": "8a8b2cef7a404137017a4245018a7011",
"湖北省地方政府债指数": "8a8b2c8368e383220168e4bae68500c9",
"兴业绿色债券指数": "8a8b2c8f57df2edc0157e1163014176e",
"银行普通债券AAA指数": "e36b9dc1620a0dc7ee027cca1663c526",
"中期票据AAA指数": "9ced53d3f93b8cb9509a80d294086876",
"黄金保值信用债风险平价指数": "b099abb287eebad09994ab481fe67f24",
"浦发银行ESG精选债券指数": "6357eef4131197707f812ea9a7530a53",
"北银理财京津冀企业高质量发展多元投资指数": "25895ebd4694c235a33aa9d360b04764",
"固定利率国债指数": "2c9081e50e8767dc010e87a6a60b0050",
"浮动利率金融债指数": "2c9081e50e8767dc010e87b3b1d60070",
"AAA公司信用类科技创新债券指数": "3279a06da6f3a8e8a6429d32b0917cb7",
"云南省地方政府债指数": "8a8b2cef7132d3800171330128ec0002",
"辽宁省地方政府债指数": "8a8b2cef73265c58017326e66e310005",
"长江经济带绿色债券综合指数": "7ebdf1292c65a1bcfcdab7546919312c",
"关键期限国债指数": "8a8b2ca04b1e4a5b014b2a23197c72c5",
"红利现金流中高等级股债波动率控制1%指数": "982441730a41cb3f45cf58bf0a21f2ee",
"北京银行高信用等级城市商业银行债券指数": "b9a6d06e9b6458c9062f08a1dc75fd30",
"中信证券个人汽车抵押贷款资产支持证券指数": "5cb7d4be4facd5353ac243620ebf2bde",
"中高等级长三角绿色债券指数": "1432826c10c29fdd3b75258378e45aa1",
"天风国际ESG优选中资美元债指数": "2d3ac1a7ccda4e7aadc605e2b1ca0c9b",
"工行绿色债券指数": "31d4a4934ca82e11892f6bbb9be0ea04",
"红利现金流中高等级股债金波动率控制1.5%指数": "47a631e45ce8b99708de3ecd775b64b7",
"京津冀绿色债券指数": "8a8b2cef6db2c0f4016db432c17f0667",
"河南省地方政府债指数": "8a8b2cef730c9c8f01730d1816ce0066",
"内蒙古自治区地方政府债指数": "8a8b2cef7311c2e701731364881d032a",
"制造行业信用债指数": "8a8b2cef73c6017e0173c882dd1c7801",
"粤港澳大湾区绿色债券指数": "8a8b2cef747519b5017476a72ce653a2",
"科技创新及绿色债券指数": "7dc84c0f21a71b97931fd7abadc78433",
"投资级公司绿色债券精选指数": "80e6aa811418a5b9ac810c93ac381fed",
"市场隐含评级AAA+信用债指数": "8a8b2c836775df9801677851e4360d74",
"高等级公司信用类科技创新债券指数": "eba5e43f73c9d877657d88d3e00ad90c",
"银行间绿色债券指数": "9da7e47f35b11c98cced95e4fb71b596",
"高等级战略性新兴产业信用债指数": "adf7158832226e8e7361b78d0f5e4798",
"红利自由现金流低波股债恒定比例15/85指数": "d0203aedec448bec95845ba349cc9e78",
"电力行业信用债指数": "5cc7a4278c0c1cc0f82dc018c3c15fd1",
"科技创新绿色普惠主题债券综合指数": "5e21777b1e179d595ebd9a78a6b89bf7",
"中高等级战略性新兴产业信用债指数": "05b2d2e9b40a7f2324774c0b32f8cd70",
"浮动利率债券指数": "2c9081e50e8767dc010e8797a5d70019",
"京津冀地方政府债指数": "8a8b2cef6d4bc1c2016d4c96069c24fb",
"宁波市地方政府债指数": "8a8b2cef73077630017307dc4339007c",
"钢铁行业信用债指数": "8a8b2cef73c0db220173c140495c0058",
"北京市地方政府债指数": "8a8b2cef7456338c017456818eba000a",
"山西省地方政府债指数": "8a8b2cef746080450174619484ea000c",
"宁夏回族自治区地方政府债指数": "8a8b2cef7460804501746219b518020a",
"西藏自治区地方政府债指数": "8a8b2cef7465a6a2017465f9dc55000a",
"投资优选国债指数": "8a8b2cef7a35f47f017a37c76654232d",
"挂钩LPR浮动利率政策性银行债指数": "678165887609e2cb84fa87251c33fc08",
"银行金融债券AAA指数": "81d917dad85d7ce95f51bc644484e1ff",
"市场隐含评级AAA-信用债指数": "8a8b2c836775df980167785085850d62",
"国有大型商业银行及股份制商业银行二级资本债券指数": "8a8b2c8367f69e950167f7b549f00005",
"高信用等级中期票据指数": "8a8b2ca03d393e7c013d39c667963351",
"高信用等级银行金融债券指数": "f187fd9f8ee0d88f9a59323d6a709e34",
"同业存单AAA指数": "b15ef8073f38d8962cd7728a857f5cc8",
"中高等级科技创新债券指数": "b7c74a6569cb5a38d7f1ab3ed20ca62b",
"商业银行二级资本债券市场隐含评级AA指数": "c511c7a1a872fb2ca258474e95a45ab8",
"高等级绿色公司信用类债券指数": "d8fbee7a51ae5901ea48aa7948bda83f",
"银行间AAA科技创新债券指数": "571d2417bcf35b5dc808f3c480349090",
"黄河流域绿色债券综合指数": "608e6e23ec091fdc8c879481ac979b19",
"国债总指数": "2c9081e50e8767dc010e879acb220021",
"长江经济带地方政府债指数": "8a8b2cef709d7b1201709f29b09f0084",
"山东省地方政府债指数": "8a8b2cef70eaba740170ed2c79b44c04",
"四川省地方政府债指数": "8a8b2cef7109a09c01710c04f8bb41fd",
"深圳市地方政府债指数": "8a8b2cef7224de5f0172265a948a0089",
"河北省地方政府债指数": "8a8b2cef730c9c8f01730d8ca18b00ee",
"大连市地方政府债指数": "8a8b2cef73265c580173273fe9e2008d",
"信用债价值因子精选策略指数": "8a8b2cef73a1f4f80173a2c0b2a4000e",
"粤港澳大湾区债券综合指数": "8a8b2cef74adbfab0174afbea5434943",
"利差驱动股债稳健指数": "890fcfb97ea76876563dfc1771652a22",
"中债信用增进公司增信债券指数": "8a8b2ca03de1b1db013de91f3a6f2aee",
"银行金融债券指数": "eae41b72f13a22c9b24a0a5887789000",
"乡村振兴债券综合指数": "cec6a61bd8827e306fcba8f195a4903f",
}
INDICATOR_MAPPING = {
"全价": "QJZS",
"净价": "JJZS",
"财富": "CFZS",
"平均市值法久期": "PJSZFJQ",
"平均现金流法久期": "PJXJLFJQ",
"平均市值法凸性": "PJSZFTX",
"平均现金流法凸性": "PJXJLFTX",
"平均现金流法到期收益率": "PJDQSYL",
"平均市值法到期收益率": "PJSZFDQSYL",
"平均基点价值": "PJJDJZ",
"平均待偿期": "PJDCQ",
"平均派息率": "PJPXL",
"指数上日总市值": "ZSZSZ",
"财富指数涨跌幅": "CFZSZDF",
"全价指数涨跌幅": "QJZSZDF",
"净价指数涨跌幅": "JJZSZDF",
"现券结算量": "XQJSL",
}
PERIOD_MAPPING = {
"总值": "00",
"1年以下": "01",
"1-3年": "02",
"3-5年": "03",
"5-7年": "04",
"7-10年": "05",
"10年以上": "06",
"0-3个月": "07",
"3-6个月": "08",
"6-9个月": "09",
"9-12个月": "10",
"0-6个月": "11",
"6-12个月": "12",
}
# bond-cov-sina
zh_sina_bond_hs_cov_url = "http://vip.stock.finance.sina.com.cn/quotes_service/api/json_v2.php/Market_Center.getHQNodeDataSimple"
zh_sina_bond_hs_cov_count_url = "http://vip.stock.finance.sina.com.cn/quotes_service/api/json_v2.php/Market_Center.getHQNodeStockCountSimple"
zh_sina_bond_hs_cov_hist_url = (
"https://finance.sina.com.cn/realstock/company/{}/hisdata/klc_kl.js?d={}"
)
zh_sina_bond_hs_cov_payload = {
"page": "1",
"num": "80",
"sort": "symbol",
"asc": "1",
"node": "hskzz_z",
"_s_r_a": "page",
}
# bond-sina
zh_sina_bond_hs_url = "http://vip.stock.finance.sina.com.cn/quotes_service/api/json_v2.php/Market_Center.getHQNodeData"
zh_sina_bond_hs_count_url = "http://vip.stock.finance.sina.com.cn/quotes_service/api/json_v2.php/Market_Center.getHQNodeStockCountSimple"
zh_sina_bond_hs_hist_url = (
"https://finance.sina.com.cn/realstock/company/{}/hisdata/klc_kl.js?d={}"
)
zh_sina_bond_hs_payload = {
"page": "1",
"num": "80",
"sort": "symbol",
"asc": "1",
"node": "hs_z",
"_s_r_a": "page",
}
# headers
SHORT_HEADERS = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/61.0.3163.91 Safari/537.36"
}
# quote
MARKET_QUOTE_URL = "http://www.chinamoney.com.cn/ags/ms/cm-u-md-bond/CbMktMakQuot?flag=1&lang=cn&abdAssetEncdShrtDesc=&emaEntyEncdShrtDesc="
MARKET_QUOTE_PAYLOAD = {
"flag": "1",
"lang": "cn",
"abdAssetEncdShrtDesc": "",
"emaEntyEncdShrtDesc": "",
}
# trade
MARKET_TRADE_URL = (
"http://www.chinamoney.com.cn/ags/ms/cm-u-md-bond/CbtPri?lang=cn&flag=1&bondName="
)
MARKET_TRADE_PAYLOAD = {"lang": "cn", "flag": "1", "bondName": ""}
@@ -0,0 +1,173 @@
"""
Yang-Zhang-s-Realized-Volatility-Automated-Estimation-in-Python
https://github.com/hugogobato/Yang-Zhang-s-Realized-Volatility-Automated-Estimation-in-Python
论文地址:https://www.jstor.org/stable/10.1086/209650
"""
import warnings
import numpy as np
import pandas as pd
def rv_from_stock_zh_a_hist_min_em(
symbol="000001",
start_date="2021-10-20 09:30:00",
end_date="2024-11-01 15:00:00",
period="1",
adjust="hfq",
) -> pd.DataFrame:
"""
从东方财富网获取股票的分钟级历史行情数据,并进行数据清洗和格式化为计算 yz 已实现波动率所需的数据格式
https://quote.eastmoney.com/concept/sh603777.html?from=classic
:param symbol: 股票代码,如"000001"
:type symbol: str
:param start_date: 开始日期时间,格式"YYYY-MM-DD HH:MM:SS"
:type start_date: str
:param end_date: 结束日期时间,格式"YYYY-MM-DD HH:MM:SS"
:type end_date: str
:param period: 时间周期,可选{'1','5','15','30','60'}分钟
:type period: str
:param adjust: 复权方式,可选{'','qfq'(前复权),'hfq'(后复权)}
:type adjust: str
:return: 整理后的分钟行情数据,包含Date(索引),Open,High,Low,Close列
:rtype: pandas.DataFrame
"""
from akshare.stock_feature.stock_hist_em import stock_zh_a_hist_min_em
temp_df = stock_zh_a_hist_min_em(
symbol=symbol,
start_date=start_date,
end_date=end_date,
period=period,
adjust=adjust,
)
temp_df.rename(
columns={
"时间": "Date",
"开盘": "Open",
"最高": "High",
"最低": "Low",
"收盘": "Close",
},
inplace=True,
)
temp_df = temp_df[temp_df["Open"] != 0]
temp_df["Date"] = pd.to_datetime(temp_df["Date"])
temp_df.set_index(keys="Date", inplace=True)
return temp_df
def rv_from_futures_zh_minute_sina(
symbol: str = "IF2008", period: str = "5"
) -> pd.DataFrame:
"""
从新浪财经获取期货的分钟级历史行情数据,并进行数据清洗和格式化
https://vip.stock.finance.sina.com.cn/quotes_service/view/qihuohangqing.html#titlePos_3
:param symbol: 期货合约代码,如"IF2008"代表沪深300期货2020年8月合约
:type symbol: str
:param period: 时间周期,可选{'1','5','15','30','60'}分钟
:type period: str
:return: 整理后的分钟行情数据,包含Date(索引),Open,High,Low,Close列
:rtype: pandas.DataFrame
"""
from akshare.futures.futures_zh_sina import futures_zh_minute_sina
temp_df = futures_zh_minute_sina(symbol=symbol, period=period)
temp_df.rename(
columns={
"datetime": "Date",
"open": "Open",
"high": "High",
"low": "Low",
"close": "Close",
},
inplace=True,
)
temp_df["Date"] = pd.to_datetime(temp_df["Date"])
temp_df.set_index(keys="Date", inplace=True)
return temp_df
def volatility_yz_rv(data: pd.DataFrame) -> pd.DataFrame:
(
"""
波动率-已实现波动率-Yang-Zhang 已实现波动率(Yang-Zhang Realized Volatility)
https://github.com/hugogobato/Yang-Zhang-s-Realized-Volatility-Automated-Estimation-in-Python
论文地址:https://www.jstor.org/stable/10.1086/209650
基于以下公式计算:
RV^2 = Vo + k*Vc + (1-k)*Vrs
其中:
- Vo: 隔夜波动率, Vo = 1/(n-1)*sum(Oi-Obar)^2
Oi为标准化开盘价, Obar为标准化开盘价均值
- Vc: 收盘波动率, Vc = 1/(n-1)*sum(ci-Cbar)^2
ci为标准化收盘价, Cbar为标准化收盘价均值
- k: 权重系数, k = 0.34/(1.34+(n+1)/(n-1))
n为样本数量
- Vrs: Rogers-Satchell波动率代理, Vrs = ui(ui-ci)+di(di-ci)
ui = ln(Hi/Oi), ci = ln(Ci/Oi), di = ln(Li/Oi), oi = ln(Oi/Ci-1)
Hi/Li/Ci/Oi分别为最高价/最低价/收盘价/开盘价
:param data: 包含 OHLC(开高低收) 价格的 pandas.DataFrame
:type data: pandas.DataFrame
:return: 包含 Yang-Zhang 实现波动率的 pandas.DataFrame
:rtype: pandas.DataFrame
要求输入数据包含以下列:
- Open: 开盘价
- High: 最高价
- Low: 最低价
- Close: 收盘价
# yang_zhang_rv formula is give as:
# RV^2 = Vo + k*Vc + (1-k)*Vrs
# where Vo = 1/(n-1)*sum(Oi-Obar)^2
# with oi = normalized opening price at time t and Obar = mean of normalized opening prices
# Vc = = 1/(n-1)*sum(ci-Cbar)^2
# with ci = normalized close price at time t and Cbar = mean of normalized close prices
# k = 0.34/(1.34+(n+1)/(n-1))
# with n = total number of days or time periods considered
# Vrs (Rogers & Satchell RV proxy) = ui(ui-ci)+di(di-ci)
# with ui = ln(Hi/Oi), ci = ln(Ci/Oi), di=(Li/Oi), oi = ln(Oi/Ci-1)
# where Hi = high price at time t and Li = low price at time t
"""
""
)
warnings.filterwarnings("ignore")
data["ui"] = np.log(np.divide(data["High"][1:], data["Open"][1:]))
data["ci"] = np.log(np.divide(data["Close"][1:], data["Open"][1:]))
data["di"] = np.log(np.divide(data["Low"][1:], data["Open"][1:]))
data["oi"] = np.log(np.divide(data["Open"][1:], data["Close"][: len(data) - 1]))
data = data[1:]
data["RS"] = data["ui"] * (data["ui"] - data["ci"]) + data["di"] * (
data["di"] - data["ci"]
)
rs_var = data["RS"].groupby(pd.Grouper(freq="1D")).mean().dropna()
vc_and_vo = data[["oi", "ci"]].groupby(pd.Grouper(freq="1D")).var().dropna()
n = int(len(data) / len(rs_var))
k = 0.34 / (1.34 + (n + 1) / (n - 1))
yang_zhang_rv = np.sqrt((1 - k) * rs_var + vc_and_vo["oi"] + vc_and_vo["ci"] * k)
yang_zhang_rv_df = pd.DataFrame(yang_zhang_rv)
yang_zhang_rv_df.rename(columns={0: "yz_rv"}, inplace=True)
yang_zhang_rv_df.reset_index(inplace=True)
yang_zhang_rv_df.columns = ["date", "rv"]
yang_zhang_rv_df["date"] = pd.to_datetime(
yang_zhang_rv_df["date"], errors="coerce"
).dt.date
return yang_zhang_rv_df
if __name__ == "__main__":
futures_df = rv_from_futures_zh_minute_sina(symbol="IF2008", period="1")
volatility_yz_rv_df = volatility_yz_rv(data=futures_df)
print(volatility_yz_rv_df)
stock_df = rv_from_stock_zh_a_hist_min_em(
symbol="000001",
start_date="2021-10-20 09:30:00",
end_date="2024-11-01 15:00:00",
period="5",
adjust="",
)
volatility_yz_rv_df = volatility_yz_rv(data=stock_df)
print(volatility_yz_rv_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2020/10/23 13:51
Desc:
"""
@@ -0,0 +1,63 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/9/5 15:41
Desc: 芝加哥商业交易所-比特币成交量报告
https://datacenter.jin10.com/reportType/dc_cme_btc_report
"""
import pandas as pd
import requests
def crypto_bitcoin_cme(date: str = "20230830") -> pd.DataFrame:
"""
芝加哥商业交易所-比特币成交量报告
https://datacenter.jin10.com/reportType/dc_cme_btc_report
:param date: Specific date, e.g., "20230830"
:type date: str
:return: 比特币成交量报告
:rtype: pandas.DataFrame
"""
url = "https://datacenter-api.jin10.com/reports/list"
params = {
"category": "cme",
"date": "-".join([date[:4], date[4:6], date[6:]]),
"attr_id": "4",
}
headers = {
"accept": "*/*",
"accept-encoding": "gzip, deflate, br",
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8",
"cache-control": "no-cache",
"origin": "https://datacenter.jin10.com",
"pragma": "no-cache",
"referer": "https://datacenter.jin10.com/",
"sec-ch-ua": '" Not;A Brand";v="99", "Google Chrome";v="91", "Chromium";v="91"',
"sec-ch-ua-mobile": "?0",
"sec-fetch-dest": "empty",
"sec-fetch-mode": "cors",
"sec-fetch-site": "same-site",
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.106 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "",
"x-version": "1.0.0",
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(
[item for item in data_json["data"]["values"]],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
temp_df["电子交易合约"] = pd.to_numeric(temp_df["电子交易合约"], errors="coerce")
temp_df["场内成交合约"] = pd.to_numeric(temp_df["场内成交合约"], errors="coerce")
temp_df["场外成交合约"] = pd.to_numeric(temp_df["场外成交合约"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["未平仓合约"] = pd.to_numeric(temp_df["未平仓合约"], errors="coerce")
temp_df["持仓变化"] = pd.to_numeric(temp_df["持仓变化"], errors="coerce")
return temp_df
if __name__ == "__main__":
crypto_bitcoin_cme_df = crypto_bitcoin_cme(date="20230830")
print(crypto_bitcoin_cme_df)
@@ -0,0 +1,79 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/8/31 23:00
Desc: 金十数据-比特币持仓报告
https://datacenter.jin10.com/dc_report?name=bitcoint
"""
import pandas as pd
import requests
def crypto_bitcoin_hold_report():
"""
金十数据-比特币持仓报告
https://datacenter.jin10.com/dc_report?name=bitcoint
:return: 比特币持仓报告
:rtype: pandas.DataFrame
"""
url = "https://datacenter-api.jin10.com/bitcoin_treasuries/list"
headers = {
"X-App-Id": "lnFP5lxse24wPgtY",
"X-Version": "1.0.0",
}
r = requests.get(url, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["values"])
temp_df.columns = [
"代码",
"公司名称-英文",
"国家/地区",
"市值",
"比特币占市值比重",
"持仓成本",
"持仓占比",
"持仓量",
"当日持仓市值",
"查询日期",
"公告链接",
"_",
"分类",
"倍数",
"_",
"公司名称-中文",
]
temp_df = temp_df[
[
"代码",
"公司名称-英文",
"公司名称-中文",
"国家/地区",
"市值",
"比特币占市值比重",
"持仓成本",
"持仓占比",
"持仓量",
"当日持仓市值",
"查询日期",
"公告链接",
"分类",
"倍数",
]
]
temp_df["市值"] = pd.to_numeric(temp_df["市值"], errors="coerce")
temp_df["比特币占市值比重"] = pd.to_numeric(
temp_df["比特币占市值比重"], errors="coerce"
)
temp_df["持仓成本"] = pd.to_numeric(temp_df["持仓成本"], errors="coerce")
temp_df["持仓占比"] = pd.to_numeric(temp_df["持仓占比"], errors="coerce")
temp_df["持仓量"] = pd.to_numeric(temp_df["持仓量"], errors="coerce")
temp_df["当日持仓市值"] = pd.to_numeric(temp_df["当日持仓市值"], errors="coerce")
temp_df["倍数"] = pd.to_numeric(temp_df["倍数"], errors="coerce")
temp_df["查询日期"] = pd.to_datetime(temp_df["查询日期"], errors="coerce").dt.date
return temp_df
if __name__ == "__main__":
crypto_bitcoin_hold_report_df = crypto_bitcoin_hold_report()
print(crypto_bitcoin_hold_report_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2020/3/6 16:40
Desc:
"""
@@ -0,0 +1,184 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/7/24 18:30
Desc: currencybeacon 提供的外汇数据
该网站需要先注册后获取 API 使用
https://currencyscoop.com/
"""
import pandas as pd
import requests
def currency_latest(
base: str = "USD", symbols: str = "", api_key: str = ""
) -> pd.DataFrame:
"""
Latest data from currencyscoop.com
https://currencyscoop.com/api-documentation
:param base: The base currency you would like to use for your rates
:type base: str
:param symbols: A list of currencies you will like to see the rates for. You can refer to a list all supported currencies here
:type symbols: str
:param api_key: Account -> Account Details -> API KEY (use as password in external tools)
:type api_key: str
:return: Latest data of base currency
:rtype: pandas.DataFrame
"""
params = {"base": base, "symbols": symbols, "api_key": api_key}
url = "https://api.currencyscoop.com/v1/latest"
r = requests.get(url, params=params)
temp_df = pd.DataFrame.from_dict(r.json()["response"])
temp_df["date"] = pd.to_datetime(temp_df["date"])
temp_df.reset_index(inplace=True)
temp_df.rename(columns={"index": "currency"}, inplace=True)
return temp_df
def currency_history(
base: str = "USD", date: str = "2023-02-03", symbols: str = "", api_key: str = ""
) -> pd.DataFrame:
"""
Latest data from currencyscoop.com
https://currencyscoop.com/api-documentation
:param base: The base currency you would like to use for your rates
:type base: str
:param date: Specific date, e.g., "2020-02-03"
:type date: str
:param symbols: A list of currencies you will like to see the rates for. You can refer to a list all supported currencies here
:type symbols: str
:param api_key: Account -> Account Details -> API KEY (use as password in external tools)
:type api_key: str
:return: Latest data of base currency
:rtype: pandas.DataFrame
"""
params = {"base": base, "date": date, "symbols": symbols, "api_key": api_key}
url = "https://api.currencyscoop.com/v1/historical"
r = requests.get(url, params=params)
temp_df = pd.DataFrame.from_dict(r.json()["response"])
temp_df["date"] = pd.to_datetime(temp_df["date"]).dt.date
temp_df.reset_index(inplace=True)
temp_df.rename(columns={"index": "currency"}, inplace=True)
return temp_df
def currency_time_series(
base: str = "USD",
start_date: str = "2023-02-03",
end_date: str = "2023-03-04",
symbols: str = "",
api_key: str = "",
) -> pd.DataFrame:
"""
Time-series data from currencyscoop.com
P.S. need special authority
https://currencyscoop.com/api-documentation
:param base: The base currency you would like to use for your rates
:type base: str
:param start_date: Specific date, e.g., "2020-02-03"
:type start_date: str
:param end_date: Specific date, e.g., "2020-02-03"
:type end_date: str
:param symbols: A list of currencies you will like to see the rates for. You can refer to a list all supported currencies here
:type symbols: str
:param api_key: Account -> Account Details -> API KEY (use as password in external tools)
:type api_key: str
:return: Latest data of base currency
:rtype: pandas.DataFrame
"""
params = {
"base": base,
"api_key": api_key,
"start_date": start_date,
"end_date": end_date,
"symbols": symbols,
}
url = "https://api.currencyscoop.com/v1/timeseries"
r = requests.get(url, params=params)
temp_df = pd.DataFrame.from_dict(r.json()["response"])
temp_df = temp_df.T
temp_df.reset_index(inplace=True)
temp_df.rename(columns={"index": "date"}, inplace=True)
temp_df["date"] = pd.to_datetime(temp_df["date"]).dt.date
return temp_df
def currency_currencies(c_type: str = "fiat", api_key: str = "") -> pd.DataFrame:
"""
currencies data from currencyscoop.com
https://currencyscoop.com/api-documentation
:param c_type: now only "fiat" can return data
:type c_type: str
:param api_key: Account -> Account Details -> API KEY (use as password in external tools)
:type api_key: str
:return: Latest data of base currency
:rtype: pandas.DataFrame
"""
params = {"type": c_type, "api_key": api_key}
url = "https://api.currencyscoop.com/v1/currencies"
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["response"])
return temp_df
def currency_convert(
base: str = "USD",
to: str = "CNY",
amount: str = "10000",
api_key: str = "",
) -> pd.DataFrame:
"""
currencies data from currencyscoop.com
https://currencyscoop.com/api-documentation
:param base: The base currency you would like to use for your rates
:type base: str
:param to: The currency you would like to use for your rates
:type to: str
:param amount: The amount of base currency
:type amount: str
:param api_key: Account -> Account Details -> API KEY (use as password in external tools)
:type api_key: str
:return: Latest data of base currency
:rtype: pandas.Series
"""
params = {
"from": base,
"to": to,
"amount": amount,
"api_key": api_key,
}
url = "https://api.currencyscoop.com/v1/convert"
r = requests.get(url, params=params)
temp_se = pd.Series(r.json()["response"])
temp_se["timestamp"] = pd.to_datetime(temp_se["timestamp"], unit="s")
temp_df = temp_se.to_frame()
temp_df.reset_index(inplace=True)
temp_df.columns = ["item", "value"]
return temp_df
if __name__ == "__main__":
currency_latest_df = currency_latest(base="USD", api_key="")
print(currency_latest_df)
currency_history_df = currency_history(base="USD", date="2023-02-03", api_key="")
print(currency_history_df)
currency_time_series_df = currency_time_series(
base="USD",
start_date="2023-02-03",
end_date="2023-03-04",
symbols="",
api_key="",
)
print(currency_time_series_df)
currency_currencies_df = currency_currencies(c_type="fiat", api_key="")
print(currency_currencies_df)
currency_convert_se = currency_convert(
base="USD", to="CNY", amount="10000", api_key=""
)
print(currency_convert_se)
@@ -0,0 +1,117 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/12/8 17:20
Desc: 新浪财经-中行人民币牌价历史数据查询
https://biz.finance.sina.com.cn/forex/forex.php?startdate=2012-01-01&enddate=2021-06-14&money_code=EUR&type=0
"""
from functools import lru_cache
from io import StringIO
import pandas as pd
import requests
from bs4 import BeautifulSoup
from tqdm import tqdm
@lru_cache()
def _currency_boc_sina_map(
start_date: str = "20210614", end_date: str = "20230810"
) -> dict:
"""
外汇 symbol 和代码映射
https://biz.finance.sina.com.cn/forex/forex.php?startdate=2012-01-01&enddate=2021-06-14&money_code=EUR&type=0
:param start_date: 开始交易日
:type start_date: str
:param end_date: 结束交易日
:type end_date: str
:return: 外汇 symbol 和代码映射
:rtype: dict
"""
url = "http://biz.finance.sina.com.cn/forex/forex.php"
params = {
"startdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"enddate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
"money_code": "EUR",
"type": "0",
}
r = requests.get(url, params=params)
r.encoding = "gbk"
soup = BeautifulSoup(r.text, "lxml")
data_dict = dict(
zip(
[
item.text
for item in soup.find(attrs={"id": "money_code"}).find_all("option")
],
[
item["value"]
for item in soup.find(attrs={"id": "money_code"}).find_all("option")
],
)
)
return data_dict
def currency_boc_sina(
symbol: str = "美元", start_date: str = "20230304", end_date: str = "20231110"
) -> pd.DataFrame:
"""
新浪财经-中行人民币牌价历史数据查询
https://biz.finance.sina.com.cn/forex/forex.php?startdate=2012-01-01&enddate=2021-06-14&money_code=EUR&type=0
:param symbol: choice of {'美元', '英镑', '欧元', '澳门元', '泰国铢', '菲律宾比索', '港币', '瑞士法郎', '新加坡元', '瑞典克朗', '丹麦克朗', '挪威克朗', '日元', '加拿大元', '澳大利亚元', '新西兰元', '韩国元'}
:type symbol: str
:param start_date: 开始交易日
:type start_date: str
:param end_date: 结束交易日
:type end_date: str
:return: 中行人民币牌价历史数据查询
:rtype: pandas.DataFrame
"""
data_dict = _currency_boc_sina_map(start_date=start_date, end_date=end_date)
url = "http://biz.finance.sina.com.cn/forex/forex.php"
params = {
"money_code": data_dict[symbol],
"type": "0",
"startdate": "-".join([start_date[:4], start_date[4:6], start_date[6:]]),
"enddate": "-".join([end_date[:4], end_date[4:6], end_date[6:]]),
"page": "1",
"call_type": "ajax",
}
r = requests.get(url, params=params)
soup = BeautifulSoup(r.text, features="lxml")
soup.find(attrs={"id": "money_code"})
page_element_list = soup.find_all("a", attrs={"class": "page"})
page_num = int(page_element_list[-2].text) if len(page_element_list) != 0 else 1
big_df = pd.DataFrame()
for page in tqdm(range(1, page_num + 1), leave=False):
params.update({"page": page})
r = requests.get(url, params=params)
temp_df = pd.read_html(StringIO(r.text), header=0)[0]
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.columns = [
"日期",
"中行汇买价",
"中行钞买价",
"中行钞卖价/汇卖价",
"央行中间价",
"中行折算价",
]
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce").dt.date
big_df["中行汇买价"] = pd.to_numeric(big_df["中行汇买价"], errors="coerce")
big_df["中行钞买价"] = pd.to_numeric(big_df["中行钞买价"], errors="coerce")
big_df["中行钞卖价/汇卖价"] = pd.to_numeric(
big_df["中行钞卖价/汇卖价"], errors="coerce"
)
big_df["央行中间价"] = pd.to_numeric(big_df["央行中间价"], errors="coerce")
big_df["中行折算价"] = pd.to_numeric(big_df["中行折算价"], errors="coerce")
big_df.sort_values(by=["日期"], inplace=True, ignore_index=True)
return big_df
if __name__ == "__main__":
currency_boc_sina_df = currency_boc_sina(
symbol="美元", start_date="20230304", end_date="20231110"
)
print(currency_boc_sina_df)
@@ -0,0 +1,60 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2024/4/29 17:00
Desc: 人民币汇率中间价
https://www.safe.gov.cn/safe/rmbhlzjj/index.html
"""
import re
from datetime import datetime
from io import StringIO
import pandas as pd
import requests
from bs4 import BeautifulSoup
def currency_boc_safe() -> pd.DataFrame:
"""
人民币汇率中间价
https://www.safe.gov.cn/safe/rmbhlzjj/index.html
:return: 人民币汇率中间价
:rtype: pandas.DataFrame
"""
url = "https://www.safe.gov.cn/safe/2020/1218/17833.html"
r = requests.get(url)
r.encoding = "utf8"
soup = BeautifulSoup(r.text, features="lxml")
content = soup.find(name="a", string=re.compile("人民币汇率"))["href"]
url = f"https://www.safe.gov.cn{content}"
temp_df = pd.read_excel(url)
temp_df.sort_values(by=["日期"], inplace=True)
temp_df.reset_index(inplace=True, drop=True)
start_date = (
(pd.Timestamp(temp_df["日期"].tolist()[-1]) + pd.Timedelta(days=1))
.isoformat()
.split("T")[0]
)
end_date = datetime.now().isoformat().split("T")[0]
url = "https://www.safe.gov.cn/AppStructured/hlw/RMBQuery.do"
payload = {
"startDate": start_date,
"endDate": end_date,
"queryYN": "true",
}
r = requests.post(url, data=payload)
current_temp_df = pd.read_html(StringIO(r.text))[-1]
current_temp_df.sort_values(by=["日期"], inplace=True)
current_temp_df.reset_index(inplace=True, drop=True)
big_df = pd.concat(objs=[temp_df, current_temp_df], ignore_index=True)
column_name_list = big_df.columns[1:]
for item in column_name_list:
big_df[item] = pd.to_numeric(big_df[item], errors="coerce")
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce").dt.date
return big_df
if __name__ == "__main__":
currency_boc_safe_df = currency_boc_safe()
print(currency_boc_safe_df)
@@ -0,0 +1,6 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2022/5/9 18:08
Desc:
"""
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,989 @@
var TOKEN_SERVER_TIME = 1572845499.629;
function v_cookie (r, n, t, e, a) {
var u = n[0],
c = n[1],
v = a[0],
s = t[0],
f = t[1],
l = r[0],
d = hr(a[1], e[0], t[2]),
p = t[3],
h = e[1],
g = yr(a[2], a[3], e[2]),
m = yr(a[4], r[1], t[4]),
w = r[2],
I = a[5],
_ = a[6],
y = a[7],
E = hr(n[2], r[3], r[4]),
A = t[5],
C = e[3],
b = e[4],
B = t[6],
R = a[8],
T = a[9],
S = n[3],
k = t[7],
x = t[8],
O = a[10],
L = n[4],
M = n[5],
N = a[11],
P = e[5],
j = hr(n[6], e[6], t[9], r[5]),
D = t[10],
W = e[7],
$ = r[6],
F = yr(r[7], t[11], e[8], n[7]),
X = r[8],
H = t[12],
K = r[9],
U = n[8],
V = e[9],
Y = r[10],
J = e[10],
q = r[11],
Q = a[12],
Z = n[9],
G = t[13],
z = t[14],
rr = t[15],
nr = n[10],
tr = a[13],
er = a[14],
ar = e[11],
or = r[12],
ir = yr(t[16], r[13], r[14], r[15]),
ur = t[17],
cr = t[18];
function vr () {
var r = arguments[n[11]];
return r.split(n[12]).reverse().join(e[12])
}
var sr = [new e[13](hr(a[15], n[13], a[16])), new e[13](a[17])];
function fr () {
var n = arguments[a[18]];
if (!n) return a[19];
for (var o = t[19], i = e[14], u = e[15]; u < n.length; u++)
{
var c = n.charCodeAt(u),
v = c ^ i;
i = c,
o += r[16].fromCharCode(v)
}
return o
}
var lr = '',
dr; !
function (o) {
var i = e[18],
c = e[19];
o[e[20]] = a[21];
function v (t, a, o, i, u) {
var c, v, s;
c = v = s = r;
var f, l, d;
f = l = d = n;
var p, h, g;
p = h = g = e;
var m = t + g[21] + a;
i && (m += l[15] + i),
u && (m += h[22] + u),
o && (m += v[17] + o),
l[14][g[23]] = m
}
o[e[24]] = l;
function s (t, e, a) {
var o = n[16];
this.setCookie(t, r[18], i + o + c, e, a)
}
o[t[22]] = f;
function f (o) {
var i = vr(e[25], a[22]),
c = a[23][n[17]],
v = u + i + o + t[23],
s = '';
if (s == -r[19])
{
if (v = o + t[23], c.substr(a[24], v.length) != v) return;
s = a[24]
}
var f = s + v[r[20]],
l = '';
return l == -e[26] && (l = c[t[24]])
}
o[e[27]] = v;
function l () {
var r, t, a;
r = t = a = e;
var i, u, c;
i = u = c = n;
var v = u[18];
this.setCookie(v, a[28]),
this.getCookie(v) || (o[i[19]] = u[20]),
this.delCookie(v)
}
o[n[21]] = s
}(dr || (dr = {}));
var pr;
function hr () {
var r = arguments[a[25]];
if (!r) return a[19];
for (var e = a[19], o = t[25], i = n[22], u = t[18]; u < r.length; u++)
{
var c = r.charCodeAt(u);
i = (i + t[26]) % o.length,
c ^= o.charCodeAt(i),
e += String.fromCharCode(c)
}
return e
} !
function (o) {
var i, u, d;
i = u = d = a;
var p, h, g;
p = h = g = t;
var m, w, I;
m = w = I = r;
var _, y, E;
_ = y = E = n;
var b, B, R;
b = B = R = e;
var T = B[29],
S = y[23],
k = m[22],
x = w[0],
O = E[24],
L = (C, Ar, R[30]),
M = b[31],
N = T + S,
P = p[28],
j,
W = m[23][y[25]],
$,
F;
function X (r) {
return function () {
F.appendChild(j),
j.addBehavior(u[26]),
j.load(N);
var n = r();
return F.removeChild(j),
n
}
}
function H () {
var r = A;
r = D;
try
{
return !!(N in B[32] && b[32][N])
} catch (n)
{
return void B[15]
}
}
function K (r) {
return P ? G(r) : j ? Y(r) : void _[26]
}
function U () {
if (P = H(), P) j = _[27][N];
else if (W[k + c][I[24]]) try
{
$ = new ActiveXObject(vr(I[25], y[28], w[26])),
$.open(),
$.write(y[29]),
$.close(),
F = $.w[B[33]][I[27]][_[30]],
j = F.createElement(I[28])
} catch (r)
{
j = W.createElement(N),
F = W[vr(I[29], d[27])] || W.getElementsByTagName(b[17])[I[27]] || W[m[30]]
}
}
o[w[31]] = U;
function V (r, n) {
var t = J;
if (void 0 === n) return Z(r);
if (t = sr, P) z(r, n);
else
{
if (!j) return void B[15];
Q(r, n)
}
}
o[v + x] = V;
function Y (r) {
X(function () {
return r = J(r),
j.getAttribute(r)
})()
}
function J (r) {
var n = z;
n = v;
var t = vr(Ir, w[32]),
e = new y[31](t + O + s + L, b[31]);
return r.replace(new B[13](d[28]), b[34]).replace(e, p[29])
}
function q (r) {
try
{
j.removeItem(r)
} catch (n) { }
}
o[M + f + l] = K;
function Q (r, n) {
var t = G;
t = cr,
X(function () {
var t = M;
r = J(r),
t = K;
try
{
j.setAttribute(r, n),
j.save(N)
} catch (e) { }
})()
}
function Z (r) {
var n, t, e;
if (n = t = e = g, P) q(r);
else
{
if (!j) return void t[18];
rr(r)
}
}
function G (r) {
try
{
return j.getItem(r)
} catch (n)
{
return y[20]
}
}
o[fr(w[33], p[30], R[35])] = Z;
function z (r, n) {
try
{
j.setItem(r, n)
} catch (t) { }
}
function rr (r) {
X(function () {
r = J(r),
j.removeAttribute(r),
j.save(N)
})()
}
}(pr || (pr = {}));
var gr = function () {
var o, i, u;
o = i = u = e;
var c, v, s;
c = v = s = a;
var f, l, g;
f = l = g = n;
var m, w, I;
m = w = I = t;
var _, E, A;
_ = E = A = r;
var C = yr(Cr, U, _[34]),
b = vr(A[35], m[31]),
R = hr(g[32], c[29], i[36]),
T = hr(l[33], g[34], i[37], tr);
function S (r) {
this[m[32]] = r;
for (var n = o[15], t = r[i[38]]; t > n; n++) this[n] = i[15]
}
return S[d + p + C][b + h] = function () {
for (var r = this[vr(h, E[36], E[37])], n = [], t = -I[26], e = o[15], a = r[A[20]]; a > e; e++) for (var u = this[e], f = r[e], d = t += f; n[d] = u & parseInt(v[30], l[35]), --f != s[24];)--d,
u >>= parseInt(i[39], c[31]);
return n
},
S[vr(w[33], v[32])][_[38]] = function (r) {
var n = dr,
t = this[vr(y, l[36], A[39])],
e = f[26];
n = B;
for (var a = v[24], o = t[l[37]]; o > a; a++)
{
var i = t[a],
u = l[26];
do u = (u << parseInt(R + T, g[35])) + r[e++];
while (--i > w[18]);
this[a] = u >>> w[18]
}
},
S
}(),
mr; !
function (o) {
var i, u, c;
i = u = c = n;
var v, s, f;
v = s = f = e;
var l, d, p;
l = d = p = a;
var h, w, I;
h = w = I = r;
var _, y, E;
_ = y = E = t;
var A = y[34],
C = (nr, U, h[40]),
b = p[25];
function B (r) {
for (var n = y[35], t = f[15], e = r[vr(c[38], I[41], H)], a = []; e > t;)
{
var o = k[r.charAt(t++)] << parseInt(g + A, d[31]) | k[r.charAt(t++)] << parseInt(n + m, h[42]) | k[r.charAt(t++)] << parseInt(I[43], i[35]) | k[r.charAt(t++)];
a.push(o >> parseInt(_[36], h[42]), o >> l[31] & parseInt(u[39], i[40]), o & parseInt(d[30], c[35]))
}
return a
}
function T (r) {
for (var n = (O, R, p[24]), t = I[27], e = r[E[24]]; e > t; t++) n = (n << E[37]) - n + r[t];
return n & parseInt(E[38], p[33])
}
for (var S = s[40], k = {},
x = s[15]; x < parseInt(I[44], l[34]); x++) k[S.charAt(x)] = x;
function L (r) {
var n = B(r),
t = n[u[26]];
if (t != b) return error = yr(V, u[41], s[41], v[42]),
void 0;
var e = n[s[26]],
a = [];
return P(n, +_[39], a, +_[18], e),
T(a) == e ? a : void 0
}
function M (r) {
var n = T(r),
t = [b, n];
return P(r, +l[24], t, +p[25], n),
N(t)
}
function N (r) {
var n, t, e;
n = t = e = f;
var a, o, u;
a = o = u = y;
var c, v, s;
c = v = s = h;
var d, p, g;
d = p = g = l;
var m, w, I;
m = w = I = i;
for (var _ = m[42], E = d[24], A = r[c[20]], b = []; A > E;)
{
var B = r[E++] << parseInt(fr(Z, d[35]), o[39]) | r[E++] << g[31] | r[E++];
b.push(S.charAt(B >> parseInt(m[43], t[43])), S.charAt(B >> parseInt(p[36], o[40]) & parseInt(I[44], I[45])), S.charAt(B >> n[44] & parseInt(_ + C, n[42])), S.charAt(B & parseInt(fr(d[37], c[45], or), a[41])))
}
return b.join(o[19])
}
function P (r, n, t, e, a) {
var o, i, u;
o = i = u = w;
var c, v, s;
c = v = s = E;
for (var f = r[v[24]]; f > n;) t[e++] = r[n++] ^ a & parseInt(u[46], s[42]),
a = ~(a * parseInt(v[43], v[40]))
}
o[E[44]] = N,
o[_[45]] = B,
o[v[45]] = M,
o[y[46]] = L
}(mr || (mr = {}));
var wr; !
function (o) {
var i = a[38],
u = r[47],
c = t[47],
v = vr(n[46], a[39], a[40]),
s = e[46],
f = e[47],
l = a[41],
d = a[42];
function p (o) {
var i = a[43],
u = vr(n[47], e[48], n[48]),
c = {},
v = function (o, c) {
var s, f, l, d;
for (c = c.replace(n[49], n[12]), c = c.substring(e[26], c[e[38]] - e[26]), s = c.split(e[49]), l = a[24]; l < s[yr(v, sr, t[48])]; l++) if (f = s[l].split(n[50]), f && !(f[a[44]] < t[39]))
{
for (d = n[35]; d < f[r[20]]; d++) f[n[11]] = f[n[11]] + r[48] + f[d];
f[n[26]] = new a[45](r[49]).test(f[n[26]]) ? f[e[15]].substring(r[19], f[e[15]][a[44]] - n[11]) : f[n[26]],
f[n[11]] = new r[50](i + u + w).test(f[n[11]]) ? f[e[26]].substring(t[26], f[r[19]][n[37]] - t[26]) : f[a[18]],
o[f[r[27]]] = f[n[11]]
}
return o
};
return new a[45](I + _).test(o) && (c = v(c, o)),
c
}
function h (n) {
for (var t = [], e = a[24]; e < n[r[20]]; e++) t.push(n.charCodeAt(e));
return t
}
function g (o) {
var u = a[46];
if (typeof o === vr(O, a[47], or) && o[a[48]]) try
{
var c = parseInt(o[a[48]]);
switch (c)
{
case parseInt(i + u, t[42]): break;
case parseInt(yr(t[49], r[51], e[50]), e[43]): top[t[50]][n[51]] = o[e[51]];
break;
case parseInt(yr(a[25], j, e[52]), n[52]): top[n[53]][t[51]] = o[t[52]]
}
} catch (v) { }
}
function m (r, n, t) {
}
function L () {
var e, a, o;
e = a = o = r;
var i, u, c;
i = u = c = n;
var v, s, f;
v = s = f = t;
var l = f[53],
d = c[54],
p = new e[52];
return typeof TOKEN_SERVER_TIME == y + l + d ? s[18] : (time = parseInt(TOKEN_SERVER_TIME), time)
}
function M () {
var o = new t[54];
try
{
return time = n[2].now(),
time / parseInt(fr(a[50], a[51], r[53]), t[40]) >>> e[15]
} catch (i)
{
return time = o.getTime(),
time / parseInt(e[53], a[25]) >>> r[27]
}
}
function N (r) {
for (var a = t[18], o = r[t[24]] - n[11]; o >= e[15]; o--) a = a << e[26] | +r[o];
return a
}
function P (a) {
var o = new r[50](n[55]);
if (K(a)) return a;
var i = o.test(a) ? -e[54] : -t[39],
u = a.split(r[54]);
return u.slice(i).join(fr(n[56], t[55], E))
}
function j (t) {
for (var o = n[26], i = e[15], u = t[vr(r[55], a[52], D)]; u > i; i++) o = (o << r[56]) - o + t.charCodeAt(i),
o >>>= n[26];
return o
}
function W (n, o) {
var i = new a[45](t[56], yr(r[57], $, t[57], r[58])),
u = new a[45](t[58]);
if (n)
{
var c = n.match(i);
if (c)
{
var v = c[e[26]];
return o && u.test(v) && (v = v.split(t[59]).pop().split(r[48])[e[15]]),
v
}
}
}
function $ (o) {
var i = n[57],
u = vr(e[55], e[56]),
f = e[4];
if (!(o > t[60]))
{
o = o || a[24];
var l = parseInt(E + c + A, r[42]),
d = n[14].createElement(e[57]);
d[r[59]] = n[58] + parseInt((new a[53]).getTime() / l) + r[60],
d[r[61]] = function () {
var n = a[46];
cr = r[19],
setTimeout(function () {
$(++o)
},
o * parseInt(C + n, a[33]))
},
d[t[61]] = d[hr(a[54], a[55], t[62])] = function () {
var a = n[59];
this[i + v + u + b] && this[e[58]] !== n[60] && this[s + B + a + f] !== e[59] && this[t[63]] !== n[61] || (cr = e[15], d[hr(N, r[62], n[62], e[25])] = d[t[64]] = r[63])
},
e[60][e[61]].appendChild(d)
}
}
function F () {
var r = a[56];
return Math.random() * parseInt(R + T + f + r, t[42]) >>> n[26]
}
function X (r) {
var e = new n[31](fr(t[65], t[66], a[57]), yr(c, n[63], t[57]));
if (r)
{
var o = r.match(e);
return o
}
}
o[S + k] = p,
o[r[64]] = $,
o[t[67]] = g,
o[t[68]] = h,
o[t[69]] = j,
o[t[70]] = F,
o[r[65]] = K,
o[x + l] = P,
o[t[71]] = W,
o[t[72]] = X,
o[hr(r[66], t[73], r[67], C)] = N,
o[t[74]] = M,
o[d + O] = L;
function K (n) {
return new r[50](t[75]).test(n)
}
o[r[68]] = m
}(wr || (wr = {}));
var Ir; !
function (o) {
var i = t[76],
u = t[77],
c = n[65],
v = t[78],
s = a[24],
f = n[26],
l = t[18],
d = t[18],
p = e[15],
h = a[24],
g = r[69],
m = '';
wr.eventBind(e[60], n[67], E),
wr.eventBind(r[71], t[79], E),
wr.eventBind(t[20], hr(e[64], A, a[59]), b),
wr.eventBind(e[60], r[72], y);
function w () {
return f
}
function I (r) {
f++
}
function _ () {
return {
x: p,
y: h,
trusted: g
}
}
function y (r) {
d++
}
function E (r) {
s++
}
function C () {
return l
}
function b (r) {
var o, i, u;
o = i = u = n;
var c, s, f;
c = s = f = t;
var d, m, w;
d = m = w = e;
var I, _, y;
I = _ = y = a;
var E = I[60],
A = d[65];
l++ ,
g = void 0 == r[E + A + v] || r[yr(f[80], s[81], i[68])],
p = r[s[82]],
h = r[c[83]]
}
function B () {
return d
}
function R () {
return s
}
o[r[73]] = R,
o[a[61]] = w,
o[fr(a[62], n[69])] = C,
o[n[70]] = B,
o[r[74]] = _
}(Ir || (Ir = {}));
var _r; !
function (u) {
var v = fr(n[71], t[84]),
s = r[75],
f = yr(dr, n[72], e[66], $),
l = r[76],
d = e[67],
p = r[77],
h = hr(dr, r[78], a[63], n[73]),
g = r[79],
m = n[74];
BROWSER_LIST = {
};
function w () {
var t, e, a;
t = e = a = r;
var o, i, u;
o = i = u = n;
return wr.booleanToDecimal(c)
}
function I (t) {
for (var o = n[26]; o < y[e[38]]; o++)
{
var i = y[o][r[94]];
if (t.test(i)) return !a[24]
}
return !a[18]
}
function E (t) {
}
function A () {
return a[73]
}
function B () {
return n[20]
}
function T () {
return I(new t[93](r[96]))
}
function S () {
return I(new a[45](t[98], r[97]))
}
function k () {
for (var r in BROWSER_LIST) if (BROWSER_LIST.hasOwnProperty(r))
{
var n = BROWSER_LIST[r];
if (n()) return + r.substr(a[18])
}
return e[15]
}
function x () {
var n, a, o;
n = a = o = r;
var i, u, c;
i = u = c = t;
var v, s, f;
v = s = f = e;
var l = s[75],
d = s[76];
return I(new u[93](o[98], v[71])) || E(l + F + d + X)
}
function O () {
}
function L () {
var r, n, t;
r = n = t = a;
var o, i, u;
o = i = u = e;
var c = l;
return c = p
}
function M () {
var r, n, a;
r = n = a = t;
var o, i, u;
o = i = u = e;
var c;
try
{
c = i[60].createElement(a[99]).getContext(i[78])
} catch (v) { }
return !!c
}
function J () {
var t, e, o;
t = e = o = n;
var i, u, c;
i = u = c = a;
var v, s, f;
return v = s = f = r,
-parseInt(s[100], c[31]) === (new e[2]).getTimezoneOffset()
}
function Q () {
try
{
} catch (e)
{
return r[101]
}
}
function Z () {
var n, a, o;
n = a = o = e;
var i, u, c;
i = u = c = r;
var v, s, f;
return v = s = f = t,
plugin_num = s[18],
plugin_num
}
var z = [R, x, S, T, L, Q, b, V, O, J, M, q, Y, B, tr, A];
var nr = [new e[13](n[85]), new n[31](e[82]), new r[50](e[83]), new r[50](t[102]), new n[31](e[84]), new a[45](a[78]), new a[45](e[85]), new e[13](t[103]), new a[45](r[103]), new t[93](r[104]), new a[45](r[105])];
function tr () {
return e[86]
}
u[e[87]] = rr,
u[a[79]] = k,
u[yr(c, e[88], r[106])] = Z,
u[K + U + m] = w
}(_r || (_r = {}));
function yr () {
var o = arguments[a[25]];
if (!o) return t[19];
for (var i = a[19], u = e[14], c = r[27]; c < o.length; c++)
{
var v = o.charCodeAt(c),
s = v ^ u;
u = u * c % a[80] + e[89],
i += n[86].fromCharCode(s)
}
return i
}
var Er; !
function (o) {
var i = a[81],
u = t[35],
c = r[107],
v = vr(S, a[56]),
f = r[27],
l = r[19],
d = a[25],
p = n[87],
h = parseInt(e[90], r[108]),
g = a[82],
m = parseInt(vr(s, t[104]), t[39]),
w = r[109],
I = t[40],
_ = parseInt(i + V, n[45]),
y = parseInt(u + c, n[52]),
E = parseInt(t[105], r[42]),
A = e[91],
C = parseInt(Y + v, r[42]),
b = parseInt(e[92], e[93]),
B = t[106],
R = parseInt(vr(e[94], e[95]), t[41]),
T = parseInt(a[83], e[93]),
k;
function x () {
var r = M();
return r
}
function O () {
var r = t[26],
a = n[35],
o = e[54],
i = n[88];
k = new gr([i, i, i, i, r, r, r, o, a, a, a, a, a, a, a, i, a, r]),
k[l] = wr.serverTimeNow(),
L(),
k[B] = cr,
k[T] = ur,
k[R] = e[15],
k[C] = _r.getBrowserFeature(),
k[g] = _r.getBrowserIndex(),
k[m] = _r.getPluginNum()
}
function L () {
var a = dr.getCookie(tr) || pr.get(ar);
if (a && a[r[20]] == parseInt(e[96], n[52]))
{
var o = mr.decode(a);
if (o && (k.decodeBuffer(o), k[f] != t[18])) return
}
k[f] = wr.random()
}
o[a[84]] = O;
function M () {
k[R]++ ,
k[l] = wr.serverTimeNow(),
k[d] = wr.timeNow(),
k[B] = cr,
k[w] = Ir.getMouseMove(),
k[I] = Ir.getMouseClick(),
k[_] = Ir.getMouseWhell(),
k[y] = Ir.getKeyDown(),
k[E] = Ir.getClickPos().x,
k[A] = Ir.getClickPos().y;
var r = k.toBuffer();
return mr.encode(r)
}
o[yr(r[3], n[89], e[97])] = x
}(Er || (Er = {}));
var Ar; !
function (o) {
var i = n[90],
u = a[85],
v = r[110],
s = a[86],
f = t[107],
p,
h,
m,
w,
I,
_;
function E (r) {
return N(r) && dr[a[87]]
}
function A (o) {
var i = wr.getOriginFromUrl(o);
return i ? !new n[31](yr(r[42], c, t[110]) + w).test(i[r[108]]) || !new e[13](I).test(i[a[18]]) : t[111]
}
function C (e) {
var o = (_r, g, Er.update());
return e + (new r[50](vr(a[88], a[89])).test(e) ? n[91] : vr(P, a[90], t[112])) + er + t[23] + r[111](o)
}
function b (o, i, u) {
if (r[112] in i) return i.apply(o, u);
switch (u[n[37]])
{
case n[26]:
return i();
case a[18]:
return i(u[n[26]]);
case r[108]:
return i(u[e[15]], u[r[19]]);
default:
return i(u[n[26]], u[r[108]], u[t[17]])
}
}
function B () {
var r = Er.update();
return r
}
function k (r, e, o) {
if (!r) return n[20];
var i = r[e];
if (!i) return t[111];
var u = o(i);
return d || (u[a[97]] = i + t[19]),
u[n[97]] = i,
r[e] = u,
a[21]
}
function M (o) {
var i, u, c;
i = u = c = n;
var v, s, l;
v = s = l = r;
var d, p, h;
d = p = h = e;
var g, m, w;
g = m = w = a;
var I, _, y;
I = _ = y = t;
var R = hr(I[121], w[106], d[109]),
T;
k(o, _[122],
function (r) {
var n = w[107];
return function () {
var t, e, a;
t = e = a = _;
var o, i, u;
o = i = u = l;
var c, v, s;
c = v = s = w;
var f = s[108];
try
{
A(arguments[s[18]]) && !E(arguments[o[19]]) ? arguments[a[26]] = C(arguments[s[18]]) : T = B(),
r.apply(this, arguments),
A(arguments[i[19]]) || this.setRequestHeader(ar, T)
} catch (d)
{
return n + f
}
}
}),
k(o, g[109],
function (r) {
var n = b;
n = M;
var t = vr(_[123], u[107]);
return function () {
var n = fr(f, c[108], I[124]),
e = s[122];
try
{
if (parseInt(this.status) === parseInt(h[110], v[123]))
{
for (var a = r.apply(this, arguments), o = new p[13](i[109], n + R), u, l, d = {}; u = o.exec(a);) d[u[m[18]].toLowerCase()] = u[v[108]];
wr.analysisRst(wr.parse(d[ir.toLowerCase()]))
}
} catch (g)
{
return e + t
}
return r.apply(this, arguments)
}
})
}
function N (r) {
var n = wr.getHostFromUrl(r, e[28]);
return n ? _.test(n) : e[28]
}
function j () {
var cookie_v;
cookie_v = B()
return cookie_v
}
o[n[111]] = j
}(Ar || (Ar = {}));
var Cr;
var cookie = (function (a) {
function _ () {
var cookie_v;
Er.Init();
cookie_v = Ar.Init();
return cookie_v
}
return function y () {
try
{
return _()
} catch (r)
{
return r
}
}
})()
return cookie()
}
function v () {
var v;
v = v_cookie(
["t", 34, '"$', 36, "\fb", 55, "ure", "lJ#K", "Flash", "getBro", "1", "analys", "CHAMELEON_CALLBACK", 30, "\u256f\u0930\u097b\u09ff\u09a4\u0934\u099d\u09c1\u099d\u09d9\u09a7\u09c3\u0995\u09f0\u09d3\u0a62\u0a6f\u09bc\u09ad\u0934", "F,sp-", String, "; expires=", "", 1, "length", "; ", '', '', "addBehavior", ";^l", ">*]+", 0, "div", "&~!", "", "Init", "('&%$#\"![", ">NJ", "\u254e\u096d\u095f", "W$R", "sdelif_esab", "Or)E", "decodeBuffer", 84, "f", "htgnel", 8, "110", "40", "\u2504\u2562", "255", "o", ":", '^".*"$', RegExp, 40, Date, "e9", ".", 19, 5, "t8JOi", "}B", "src", ".js", "onerror", "*q:", null, "getServerTime", "isIPAddr", "8-", "ZX9Y]V8aWs3VQZ7Y", "eventBind", !0, "wheel", '', "keydown", "getMouseMove", "getClickPos", "vent", "me", "MSG", 41, "th", "safari", "ActiveXObject", "maxHeight", "head", "Google Inc.", "vendor", "sgAppName", "opr", 94, "tugw`pj", "chrome", "2345Explorer", "ome", "TheWorld", "name", "\u2553\u253c\u2572\u251d\u2569\u253d\u254f\u252e\u254d\u2526", "Native Client", "i", "Shockwave", "systemLanguage", "740", !1, "plugins", "^ARM", "^iPod", "^BlackBerry", "\u2550\u0978\u094e\u09c1\u09bc\u0928\u0989\u09d8\u099a\u09f3\u09b7\u09dc", "0", 2, 7, "c", encodeURIComponent, "apply", "headers", "8S:+", "\u2560\u2509\u2567\u2503\u256c\u251b", "\u255e\u2530\u2543\u2526\u2554\u2520\u2562\u2507\u2561\u250e\u257c\u2519", "a", 14, ":dB2", "href", "click", "err", 16, "hostname", "`60w", "\fbf", "&X "],
[";", "Element", Date, "par", "i", "DOMMous", 21, "xmT", "wserFe", "h", !0, 1, "", Boolean, '', "; domain=", "n 1970 00:", "cookie", "checkcookie", "allow", !1, "delCookie", 2333, "torage", ")*+,/\\\\:;", '', 0, '', "eliflmth", '', "ducument", RegExp, "W", "qsU", 61, 2, "sdelif_esab", "length", "I", "ff", 16, 45, "3", "10010", "77", 8, "6e%d", "DT{e", "$", / /g, ":", "href", 10, "location", "ned", "\\.com\\.cn$|\\.com\\.hk$", 63, "rea", "https://s.thsi.cn/js/chameleon/time.1", "tat", "loaded", "interactive", "WY:ZYS", "E?`a", "addEventListener", "eScroll", "onmousewheel", "mousemove", "\u255e\u096e\u096e\u09e3\u09a5\u092e\u099a\u09d4\u0990", "\u2550\u2535\u2541\u250c\u2563\u2516\u2565\u2500\u2543\u252f\u2546\u2525\u254e", "getKeyDown", "H69<J", "v~g-", "", "ature", "callPhantom", "ActiveXObject", "Uint8Array", "WeakMap", "JX%<", "chrome", "@L:!", "20", "language", "localStorage", "^Win32", String, 3, 4, "=XAE", "hea", "&", "/", "\\R$", '^R"VP', "s", "include", "_raw", "x.", "isRst", "SCRIPT", "ta", "base", "$?", "^_self$", "#", "unload", "ro", "\u2550", "^(.*?):[ \\t]*([^\\r\\n]*)\\r?$", "g", "Init", "t6?x}", "\u2574\u0955\u097b\u09dc\u0995\u0911\u09ab\u09fe\u09ba\u09e2\u098e\u09fe\u09f9\u09f9\u09f3\u0a55", "=d' "],
["<=>?@[\\]^", "e", "HE9", "tot", "\u2503", "0", "dyS", "se", "getRoot", "NR", "nd", 60, "ng", "s", "get", "mit", 13, 3, 0, "", '', "\u255f\u253a\u255b\u253f", "getCookie", "=", "length", "V587", 1, String, !0, "___", "\u2553\u2536\u255a", "uBot", "base_fileds", 32, "2", "1", "20", 5, "255", 2, 8, 16, 10, "203", "base64Encode", "base64Decode", "decode", "760", "\u255b\u0978\u0954\u09f6\u09a4\u0935", 70, "location", "href", "redirect_url", "efi", Date, "\u2519", "^\\s*(?:https?:)?\\/{2,}([^\\/\\?\\#\\\\]+)", "\u255e", "[@:]", "@", 7, "onload", 'WY$PYS/FLV"P[_7[_R', "readyState", "onreadystatechange", '"^w', "\u2569\u2535\u2546\u256c\u2544\u257b\u2541\u2569\u2501\u2575\u2501\u2571\u2502\u253d\u2507\u252e\u2507\u2538\u2564\u254b\u2530\u2502\u252e\u2553\u257b\u2520\u257e\u2522\u250d\u2551\u256e\u2532\u2511\u254d\u2511\u254c\u2567\u254e", "analysisRst", "strToBytes", "strhash", "random", "getHostFromUrl", "getOriginFromUrl", 83, "timeNow", "^(\\d+\\.)+\\d+$", "d", "v", "ted", "touchmove", 85, "F(K9i", "clientX", "clientY", "\u257a\u2515\u256f\u253c", "postMessage", '', "ActiveXObject", "Apple Computer, Inc.", "Q", "chr", "\u2558\u2535\u2550", "BIDUBrowser", RegExp, "QQBrowser", "ro", "aef", "msDoNotTrack", "PDF|Acrobat", "canvas", "yE", "\u255b\u253a\u2554\u2533\u2546\u2527\u2540\u2525\u2556", "^Android", "^Linux [ix]\\d+", "011", "13", 15, "sub", "addEventListener", "jsonp_ignore", "\u2569", !1, 'L"', "Sj", "T{_,", "q*", "i", "tagName", "et", "{'K", "Pp<", "#x'", "open", "rS", "KN3", "#", "protocol", "\\.", "DEDAOL_NOELEMAHC"],
[83, "ffer", "\u2505", "20", "e", "ngsE", Error, "est", "\u2552\u095b\u0956\u09f0\u09a3\u0935\u09c0\u09e2", "1", "sr", "hexin-v", "", RegExp, 9527, 0, "**l>", "head", "Thu, 01 Ja", "00:00 GMT", "allow", "=", "; path=", "cookie", "Init", 33, 1, "setCookie", !0, "localS", "`{|}~]", "g", '', "frames", "___$&", 56, " ", "\b", "length", "10", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_", "\u2552\u096f\u0948\u09fe\u09a2", 16, 2, 6, "encode", "rea", "729", "*.", ",", "\u2506\u092c\u090b\u09a0\u09e1\u096d\u09df\u0981\u09c4\u098c", "redirect_url", "\u2506\u092d\u090a\u09a3", "1111101000", 3, 47, "tat", "script", "readyState", "complete", '', "body", "onwheel", "mousewheel", 37, "rus", "\u2554\u0975", "chr", "ActiveXObject", "WeakMap", "aT1Kg", "i", 24, "\u2554\u253c\u254e\u2521\u254c\u2529", "\u2547\u0971\u094f\u09f6\u09b9\u0933\u099d", "Shockwav", "hockwave", "$cdc_asdjflasutopfhvcZLmcfl_", "webgl2", "2>n|", "plugins", "platform", "^Win64", "^Linux armv|Android", "^iPhone", "^MacIntel", !1, "getPlatform", "6Y,", 2333, "100", 12, "14", 10, 36, "01", "60", "\u2542\u096d\u095e\u09f0\u09a4\u0938", "j", 17, "Request", "prototype", "`z}lc", "error", "s", "r", "target", "\u255e", "A", "U", "193", "host", "$"],
["se", "g@g?", Array, "*Y", Number, "^{.", "*}$", "und", "429", "496", "imeNow", "etti", "rg", "v", "hexin-v", Error, "L_%\\T8", ".baidu.", 1, "", Function, !0, " ", '', 0, 2, "#default#userData", "ydob", "^d", 89, "11111111", 8, "epytotorp", 10, 16, "\u2506\u2536\u2506\u2536\u2506", "14", 13, "10", "Syd", 44, "Domain", "serverT", '^"', "length", RegExp, "00", "tcejbo", "status_code", "n", 66, "\u2506\u2531\u2504\u2534", "htgnel", Date, "L%", 67, "5", "?)'", '', "[[?VS", "isT", "getMouseWhell", "}}", "TR", "ActiveXObject", "WE", "python", "Maxthon", 97, "chrome", "Ryp", "UBrowser", 54, !1, "ontouchstart", "\u254d\u0975\u0917\u09f2\u09be", "iso-8859-1", "defaultCharset", "^iPad", "getBrowserIndex", 256, "1", 5, "17", "Init", "XMLHttp", "tar", "allow", "@*", "?\\", "?", "\u2571\u2503\u256a\u2546\u2566\u2556\u2567\u2547\u2501\u2564\u2506\u2526\u2514\u2524\u2511\u2521\u2501\u2531\u2501\u253b\u250b\u253b\u2501\u2531\u2501\u2521\u2566\u252b\u257f", "den", "tia", 94, "ls", "\u2554\u2526\u2543", "_str", 37, "append", "Child", "\u255f", "\u2569\u0975\u094e\u09e5\u09a0\u092e\u09d1\u09ed\u09ce", "srcElement", "parentNode", "\u2543\u2522\u2545\u250b\u256a\u2507\u2562", "}*", "err", "or", "getAllResponseHeaders", "\\.?", "\\."]
);
return v
}
@@ -0,0 +1,39 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2024/12/30 15:30
Desc: 导入文件工具,可以正确处理路径问题
"""
import pathlib
from importlib import resources
def get_ths_js(file: str = "ths.js") -> pathlib.Path:
"""
get path to data "ths.js" text file.
:return: 文件路径
:rtype: pathlib.Path
"""
with resources.path("akshare.data", file) as f:
data_file_path = f
return data_file_path
def get_crypto_info_csv(file: str = "crypto_info.zip") -> pathlib.Path:
"""
get path to data "ths.js" text file.
:return: 文件路径
:rtype: pathlib.Path
"""
with resources.path("akshare.data", file) as f:
data_file_path = f
return data_file_path
if __name__ == "__main__":
get_ths_js_path = get_ths_js(file="ths.js")
print(get_ths_js_path)
get_crypto_info_csv_path = get_crypto_info_csv(file="crypto_info.zip")
print(get_crypto_info_csv_path)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/10/21 12:08
Desc:
"""
@@ -0,0 +1,233 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/10/21 21:11
Desc: 宏观经济配置文件
"""
# urls-china
JS_CHINA_CPI_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_cpi_yoy_all.js?v={}&_={}"
)
JS_CHINA_CPI_MONTHLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_cpi_mom_all.js?v={}&_={}"
)
JS_CHINA_M2_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_m2_money_supply_yoy_all.js?v={}&_={}"
)
JS_CHINA_PPI_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_ppi_yoy_all.js?v={}&_={}"
)
JS_CHINA_PMI_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_manufacturing_pmi_all.js?v={}&_={}"
)
JS_CHINA_GDP_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_gdp_yoy_all.js?v={}&_={}"
)
JS_CHINA_CX_PMI_YEARLY_URL = "https://cdn.jin10.com/dc/reports/dc_chinese_caixin_manufacturing_pmi_all.js?v={}&_={}"
JS_CHINA_CX_SERVICE_PMI_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_caixin_services_pmi_all.js?v={}&_={}"
)
JS_CHINA_FX_RESERVES_YEARLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_fx_reserves_all.js?v={}&_={}"
)
JS_CHINA_ENERGY_DAILY_URL = (
"https://cdn.jin10.com/dc/reports/dc_qihuo_energy_report_all.js?v={}&_={}"
)
JS_CHINA_NON_MAN_PMI_MONTHLY_URL = (
"https://cdn.jin10.com/dc/reports/dc_chinese_non_manufacturing_pmi_all.js?v={}&_={}"
)
JS_CHINA_RMB_DAILY_URL = "https://cdn.jin10.com/dc/reports/dc_rmb_data_all.js?v={}&_={}"
JS_CHINA_MARKET_MARGIN_SZ_URL = (
"https://cdn.jin10.com/dc/reports/dc_market_margin_sz_all.js?v={}&_={}"
)
JS_CHINA_MARKET_MARGIN_SH_URL = (
"https://cdn.jin10.com/dc/reports/dc_market_margin_sse_all.js?v={}&_={}"
)
JS_CHINA_REPORT_URL = "https://cdn.jin10.com/dc/reports/dc_sge_report_all.js?v={}&_={}"
# urls-usa
JS_USA_INTEREST_RATE_URL = (
"https://cdn.jin10.com/dc/reports/dc_usa_interest_rate_decision_all.js?v={}&_={}"
)
JS_USA_NON_FARM_URL = (
"https://cdn.jin10.com/dc/reports/dc_nonfarm_payrolls_all.js?v={}&_={}"
)
JS_USA_UNEMPLOYMENT_RATE_URL = (
"https://cdn.jin10.com/dc/reports/dc_usa_unemployment_rate_all.js??v={}&_={}"
)
JS_USA_EIA_CRUDE_URL = (
"https://cdn.jin10.com/dc/reports/dc_eia_crude_oil_all.js?v={}&_={}"
)
JS_USA_INITIAL_JOBLESS_URL = (
"https://cdn.jin10.com/dc/reports/dc_initial_jobless_all.js?v={}&_={}"
)
JS_USA_CORE_PCE_PRICE_URL = (
"https://cdn.jin10.com/dc/reports/dc_usa_core_pce_price_all.js?v={}&_={}"
)
JS_USA_CPI_MONTHLY_URL = "https://cdn.jin10.com/dc/reports/dc_usa_cpi_all.js?v={}&_={}"
JS_USA_LMCI_URL = "https://cdn.jin10.com/dc/reports/dc_usa_lmci_all.js?v={}&_={}"
JS_USA_ADP_NONFARM_URL = (
"https://cdn.jin10.com/dc/reports/dc_adp_nonfarm_employment_all.js?v={}&_={}"
)
JS_USA_GDP_MONTHLY_URL = "https://cdn.jin10.com/dc/reports/dc_usa_gdp_all.js?v={}&_={}"
JS_USA_EIA_CRUDE_PRODUCE_URL = (
"https://cdn.jin10.com/dc/reports/dc_eia_crude_oil_produce_all.js?v={}&_={}"
)
# urls-euro
JS_EURO_RATE_DECISION_URL = (
"https://cdn.jin10.com/dc/reports/dc_interest_rate_decision_all.js?v={}&_={}"
)
# urls-constitute
JS_CONS_GOLD_ETF_URL = "https://cdn.jin10.com/dc/reports/dc_etf_gold_all.js?v={}&_={}"
JS_CONS_SLIVER_ETF_URL = (
"https://cdn.jin10.com/dc/reports/dc_etf_sliver_all.js?v={}&_={}"
)
JS_CONS_OPEC_URL = "https://cdn.jin10.com/dc/reports/dc_opec_report_all.js??v={}&_={}"
usa_name_url_map = {
"美联储决议报告": "//datacenter.jin10.com/reportType/dc_usa_interest_rate_decision",
"美国非农就业人数报告": "//datacenter.jin10.com/reportType/dc_nonfarm_payrolls",
"美国失业率报告": "//datacenter.jin10.com/reportType/dc_usa_unemployment_rate",
"美国CPI月率报告": "//datacenter.jin10.com/reportType/dc_usa_cpi",
"美国初请失业金人数报告": "//datacenter.jin10.com/reportType/dc_initial_jobless",
"美国核心PCE物价指数年率报告": "//datacenter.jin10.com/reportType/dc_usa_core_pce_price",
"美国EIA原油库存报告": "//datacenter.jin10.com/reportType/dc_eia_crude_oil",
"美联储劳动力市场状况指数报告": "//datacenter.jin10.com/reportType/dc_usa_lmci",
"美国ADP就业人数报告": "//datacenter.jin10.com/reportType/dc_adp_nonfarm_employment",
"美国国内生产总值(GDP)报告": "//datacenter.jin10.com/reportType/dc_usa_gdp",
"美国原油产量报告": "//datacenter.jin10.com/reportType/dc_eia_crude_oil_produce",
"美国零售销售月率报告": "//datacenter.jin10.com/reportType/dc_usa_retail_sales",
"美国商品期货交易委员会CFTC外汇类非商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_nc_report",
"美国NFIB小型企业信心指数报告": "//datacenter.jin10.com/reportType/dc_usa_nfib_small_business",
"贝克休斯钻井报告": "//datacenter.jin10.com/reportType/dc_rig_count_summary",
"美国谘商会消费者信心指数报告": "//datacenter.jin10.com/reportType/dc_usa_cb_consumer_confidence",
"美国FHFA房价指数月率报告": "//datacenter.jin10.com/reportType/dc_usa_house_price_index",
"美国个人支出月率报告": "//datacenter.jin10.com/reportType/dc_usa_personal_spending",
"美国生产者物价指数(PPI)报告": "//datacenter.jin10.com/reportType/dc_usa_ppi",
"美国成屋销售总数年化报告": "//datacenter.jin10.com/reportType/dc_usa_exist_home_sales",
"美国成屋签约销售指数月率报告": "//datacenter.jin10.com/reportType/dc_usa_pending_home_sales",
"美国S&P/CS20座大城市房价指数年率报告": "//datacenter.jin10.com/reportType/dc_usa_spcs20",
"美国进口物价指数报告": "//datacenter.jin10.com/reportType/dc_usa_import_price",
"美国营建许可总数报告": "//datacenter.jin10.com/reportType/dc_usa_building_permits",
"美国商品期货交易委员会CFTC商品类非商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_c_report",
"美国挑战者企业裁员人数报告": "//datacenter.jin10.com/reportType/dc_usa_job_cuts",
"美国实际个人消费支出季率初值报告": "//datacenter.jin10.com/reportType/dc_usa_real_consumer_spending",
"美国贸易帐报告": "//datacenter.jin10.com/reportType/dc_usa_trade_balance",
"美国经常帐报告": "//datacenter.jin10.com/reportType/dc_usa_current_account",
"美国API原油库存报告": "//datacenter.jin10.com/reportType/dc_usa_api_crude_stock",
"美国工业产出月率报告": "//datacenter.jin10.com/reportType/dc_usa_industrial_production",
"美国耐用品订单月率报告": "//datacenter.jin10.com/reportType/dc_usa_durable_goods_orders",
"美国工厂订单月率报告": "//datacenter.jin10.com/reportType/dc_usa_factory_orders",
"Markit服务业PMI终值": "//datacenter.jin10.com/reportType/dc_usa_services_pmi",
"商业库存月率": "//datacenter.jin10.com/reportType/dc_usa_business_inventories",
"美国ISM非制造业PMI": "//datacenter.jin10.com/reportType/dc_usa_ism_non_pmi",
"NAHB房产市场指数": "//datacenter.jin10.com/reportType/dc_usa_nahb_house_market_index",
"新屋开工总数年化": "//datacenter.jin10.com/reportType/dc_usa_house_starts",
"美国新屋销售总数年化": "//datacenter.jin10.com/reportType/dc_usa_new_home_sales",
"美国Markit制造业PMI初值报告": "//datacenter.jin10.com/reportType/dc_usa_pmi",
"美国ISM制造业PMI报告": "//datacenter.jin10.com/reportType/dc_usa_ism_pmi",
"美国密歇根大学消费者信心指数初值报告": "//datacenter.jin10.com/reportType/dc_usa_michigan_consumer_sentiment",
"美国出口价格指数报告": "//datacenter.jin10.com/reportType/dc_usa_export_price",
"美国核心生产者物价指数(PPI)报告": "//datacenter.jin10.com/reportType/dc_usa_core_ppi",
"美国核心CPI月率报告": "//datacenter.jin10.com/reportType/dc_usa_core_cpi",
"美国EIA俄克拉荷马州库欣原油库存报告": "//datacenter.jin10.com/reportType/dc_eia_cushing_oil",
"美国EIA精炼油库存报告": "//datacenter.jin10.com/reportType/dc_eia_distillates_stocks",
"美国EIA天然气库存报告": "//datacenter.jin10.com/reportType/dc_eia_natural_gas",
"美国EIA汽油库存报告": "//datacenter.jin10.com/reportType/dc_eia_gasoline",
}
china_name_url_map = {
"郑州商品交易所期货每日行情": "//datacenter.jin10.com/reportType/dc_czce_futures_data",
"中国CPI年率报告": "//datacenter.jin10.com/reportType/dc_chinese_cpi_yoy",
"中国PPI年率报告": "//datacenter.jin10.com/reportType/dc_chinese_ppi_yoy",
"中国以美元计算出口年率报告": "//datacenter.jin10.com/reportType/dc_chinese_exports_yoy",
"中国以美元计算进口年率报告": "//datacenter.jin10.com/reportType/dc_chinese_imports_yoy",
"中国以美元计算贸易帐报告": "//datacenter.jin10.com/reportType/dc_chinese_trade_balance",
"中国规模以上工业增加值年率报告": "//datacenter.jin10.com/reportType/dc_chinese_industrial_production_yoy",
"中国官方制造业PMI报告": "//datacenter.jin10.com/reportType/dc_chinese_manufacturing_pmi",
"中国财新制造业PMI终值报告": "//datacenter.jin10.com/reportType/dc_chinese_caixin_manufacturing_pmi",
"中国财新服务业PMI报告": "//datacenter.jin10.com/reportType/dc_chinese_caixin_services_pmi",
"中国外汇储备报告": "//datacenter.jin10.com/reportType/dc_chinese_fx_reserves",
"中国M2货币供应年率报告": "//datacenter.jin10.com/reportType/dc_chinese_m2_money_supply_yoy",
"中国GDP年率报告": "//datacenter.jin10.com/reportType/dc_chinese_gdp_yoy",
"人民币汇率中间价报告": "//datacenter.jin10.com/reportType/dc_rmb_data",
"在岸人民币成交量报告": "//datacenter.jin10.com/reportType/dc_dollar_rmb_report",
"上海期货交易所期货合约行情": "//datacenter.jin10.com/reportType/dc_shfe_futures_data",
"中国CPI月率报告": "//datacenter.jin10.com/reportType/dc_chinese_cpi_mom",
"大连商品交易所期货每日行情": "//datacenter.jin10.com/reportType/dc_dce_futures_data",
"中国金融期货交易所期货每日行情": "//datacenter.jin10.com/reportType/dc_cffex_futures_data",
"同业拆借报告": "//datacenter.jin10.com/reportType/dc_shibor",
"香港同业拆借报告": "//datacenter.jin10.com/reportType/dc_hk_market_info",
"深圳融资融券报告": "//datacenter.jin10.com/reportType/dc_market_margin_sz",
"上海融资融券报告": "//datacenter.jin10.com/reportType/dc_market_margin_sse",
"上海黄金交易所报告": "//datacenter.jin10.com/reportType/dc_sge_report",
"上海期货交易所仓单日报": "//datacenter.jin10.com/reportType/dc_shfe_daily_stock",
"大连商品交易所仓单日报": "//datacenter.jin10.com/reportType/dc_dce_daily_stock",
"郑州商品交易所仓单日报": "//datacenter.jin10.com/reportType/dc_czce_daily_stock",
"上海期货交易所指定交割仓库库存周报": "//datacenter.jin10.com/reportType/dc_shfe_weekly_stock",
"CCI指数5500大卡动力煤价格报告": "//datacenter.jin10.com/reportType/dc_cci_report",
"沿海六大电厂库存动态报告": "//datacenter.jin10.com/reportType/dc_qihuo_energy_report",
"国内期货市场实施热度报告": "//datacenter.jin10.com/reportType/dc_futures_market_realtime",
"中国官方非制造业PMI报告": "//datacenter.jin10.com/reportType/dc_chinese_non_manufacturing_pmi",
}
euro_name_url_map = {
"欧元区未季调贸易帐报告": "//datacenter.jin10.com/reportType/dc_eurozone_trade_balance_mom",
"欧元区季度GDP年率报告": "//datacenter.jin10.com/reportType/dc_eurozone_gdp_yoy",
"欧元区CPI年率报告": "//datacenter.jin10.com/reportType/dc_eurozone_cpi_yoy",
"欧元区PPI月率报告": "//datacenter.jin10.com/reportType/dc_eurozone_ppi_mom",
"欧元区零售销售月率报告": "//datacenter.jin10.com/reportType/dc_eurozone_retail_sales_mom",
"欧元区季调后就业人数季率报告": "//datacenter.jin10.com/reportType/dc_eurozone_employment_change_qoq",
"欧元区失业率报告": "//datacenter.jin10.com/reportType/dc_eurozone_unemployment_rate_mom",
"欧元区CPI月率报告": "//datacenter.jin10.com/reportType/dc_eurozone_cpi_mom",
"欧元区经常帐报告": "//datacenter.jin10.com/reportType/dc_eurozone_current_account_mom",
"欧元区工业产出月率报告": "//datacenter.jin10.com/reportType/dc_eurozone_industrial_production_mom",
"欧元区制造业PMI初值报告": "//datacenter.jin10.com/reportType/dc_eurozone_manufacturing_pmi",
"欧元区服务业PMI终值报告": "//datacenter.jin10.com/reportType/dc_eurozone_services_pmi",
"欧元区ZEW经济景气指数报告": "//datacenter.jin10.com/reportType/dc_eurozone_zew_economic_sentiment",
"欧元区Sentix投资者信心指数报告": "//datacenter.jin10.com/reportType/dc_eurozone_sentix_investor_confidence",
}
world_central_bank_map = {
"美联储决议报告": "//datacenter.jin10.com/reportType/dc_usa_interest_rate_decision",
"欧洲央行决议报告": "//datacenter.jin10.com/reportType/dc_interest_rate_decision",
"新西兰联储决议报告": "//datacenter.jin10.com/reportType/dc_newzealand_interest_rate_decision",
"中国央行决议报告": "//datacenter.jin10.com/reportType/dc_china_interest_rate_decision",
"瑞士央行决议报告": "//datacenter.jin10.com/reportType/dc_switzerland_interest_rate_decision",
"英国央行决议报告": "//datacenter.jin10.com/reportType/dc_english_interest_rate_decision",
"澳洲联储决议报告": "//datacenter.jin10.com/reportType/dc_australia_interest_rate_decision",
"日本央行决议报告": "//datacenter.jin10.com/reportType/dc_japan_interest_rate_decision",
"印度央行决议报告": "//datacenter.jin10.com/reportType/dc_india_interest_rate_decision",
"俄罗斯央行决议报告": "//datacenter.jin10.com/reportType/dc_russia_interest_rate_decision",
"巴西央行决议报告": "//datacenter.jin10.com/reportType/dc_brazil_interest_rate_decision",
}
constitute_report_map = {
"全球最大黄金ETF—SPDR Gold Trust持仓报告": "//datacenter.jin10.com/reportType/dc_etf_gold",
"全球最大白银ETF--iShares Silver Trust持仓报告": "//datacenter.jin10.com/reportType/dc_etf_sliver",
"芝加哥商业交易所(CME)能源类商品成交量报告": "//datacenter.jin10.com/reportType/dc_cme_energy_report",
"美国商品期货交易委员会CFTC外汇类非商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_nc_report",
"美国商品期货交易委员会CFTC商品类非商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_c_report",
"芝加哥商业交易所(CME)金属类商品成交量报告": "//datacenter.jin10.com/reportType/dc_cme_report",
"芝加哥商业交易所(CME)外汇类商品成交量报告": "//datacenter.jin10.com/reportType/dc_cme_fx_report",
"伦敦金属交易所(LME)库存报告": "//datacenter.jin10.com/reportType/dc_lme_report",
"伦敦金属交易所(LME)持仓报告": "//datacenter.jin10.com/reportType/dc_lme_traders_report",
"美国商品期货交易委员会CFTC商品类商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_merchant_goods",
"美国商品期货交易委员会CFTC外汇类商业持仓报告": "//datacenter.jin10.com/reportType/dc_cftc_merchant_currency",
}
other_map = {
"投机情绪报告": "//datacenter.jin10.com/reportType/dc_ssi_trends",
"外汇实时波动监控": "//datacenter.jin10.com/reportType/dc_myFxBook_heat_map",
"外汇相关性报告": "//datacenter.jin10.com/reportType/dc_myFxBook_correlation",
"加密货币实时行情": "//datacenter.jin10.com/reportType/dc_bitcoin_current",
}
main_map = {
"全球最大黄金ETF—SPDR Gold Trust持仓报告": "//datacenter.jin10.com/reportType/dc_etf_gold",
"全球最大白银ETF--iShares Silver Trust持仓报告": "//datacenter.jin10.com/reportType/dc_etf_sliver",
"美国非农就业人数报告": "//datacenter.jin10.com/reportType/dc_nonfarm_payrolls",
"投机情绪报告": "//datacenter.jin10.com/reportType/dc_ssi_trends",
"数据达人 — 复合报告": "//datacenter.jin10.com/reportType/dc_complex_report?complexType=1",
"投行订单": "//datacenter.jin10.com/banks_orders",
"行情报价": "//datacenter.jin10.com/price_wall",
"美国EIA原油库存报告": "//datacenter.jin10.com/reportType/dc_eia_crude_oil",
"欧佩克报告": "//datacenter.jin10.com/reportType/dc_opec_report",
}
@@ -0,0 +1,390 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/1/17 15:30
Desc: 东方财富-经济数据-澳大利亚
https://data.eastmoney.com/cjsj/foreign_5_0.html
"""
import pandas as pd
import requests
# 零售销售月率
def macro_australia_retail_rate_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-零售销售月率
https://data.eastmoney.com/cjsj/foreign_5_0.html
:return: 零售销售月率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00152903")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 贸易帐
def macro_australia_trade() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-贸易帐
https://data.eastmoney.com/cjsj/foreign_5_1.html
:return: 贸易帐
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00152793")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 失业率
def macro_australia_unemployment_rate() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-失业率
https://data.eastmoney.com/cjsj/foreign_5_2.html
:return: 失业率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00101141")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 生产者物价指数季率
def macro_australia_ppi_quarterly() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-生产者物价指数季率
https://data.eastmoney.com/cjsj/foreign_5_3.html
:return: 生产者物价指数季率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00152722")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 消费者物价指数季率
def macro_australia_cpi_quarterly() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-消费者物价指数季率
https://data.eastmoney.com/cjsj/foreign_5_4.html
:return: 消费者物价指数季率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00101104")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 消费者物价指数年率
def macro_australia_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_5_5.html
:return: 消费者物价指数年率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00101093")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
# 央行公布利率决议
def macro_australia_bank_rate() -> pd.DataFrame:
"""
东方财富-经济数据-澳大利亚-央行公布利率决议
https://data.eastmoney.com/cjsj/foreign_5_6.html
:return: 央行公布利率决议
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_AUSTRALIA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00342255")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(by="发布日期", ignore_index=True, inplace=True)
return temp_df
if __name__ == "__main__":
macro_australia_retail_rate_monthly_df = macro_australia_retail_rate_monthly()
print(macro_australia_retail_rate_monthly_df)
macro_australia_trade_df = macro_australia_trade()
print(macro_australia_trade_df)
macro_australia_unemployment_rate_df = macro_australia_unemployment_rate()
print(macro_australia_unemployment_rate_df)
macro_australia_ppi_quarterly_df = macro_australia_ppi_quarterly()
print(macro_australia_ppi_quarterly_df)
macro_australia_cpi_quarterly_df = macro_australia_cpi_quarterly()
print(macro_australia_cpi_quarterly_df)
macro_australia_cpi_yearly_df = macro_australia_cpi_yearly()
print(macro_australia_cpi_yearly_df)
macro_australia_bank_rate_df = macro_australia_bank_rate()
print(macro_australia_bank_rate_df)
@@ -0,0 +1,274 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/11/5 17:11
Desc: 金十数据中心-经济指标-央行利率-主要央行利率
https://datacenter.jin10.com/economic
输出数据格式为 float64
美联储利率决议报告
欧洲央行决议报告
新西兰联储决议报告
中国央行决议报告
瑞士央行决议报告
英国央行决议报告
澳洲联储决议报告
日本央行决议报告
俄罗斯央行决议报告
印度央行决议报告
巴西央行决议报告
"""
import datetime
import time
import pandas as pd
import requests
def __get_interest_rate_data(attr_id: str, name: str = "利率") -> pd.DataFrame:
"""
利率决议报告公共函数
https://datacenter.jin10.com/reportType/dc_usa_interest_rate_decision
:param attr_id: 内置属性
:type attr_id: str
:param name: 利率报告名称
:type name: str
:return: 利率决议报告数据
:rtype: pandas.Series
"""
t = time.time()
headers = {
"Accept": "*/*",
"Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/120.0.0.0 Safari/537.36",
"Origin": "https://datacenter.jin10.com",
"Referer": "https://datacenter.jin10.com/",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-version": "1.0.0",
}
base_url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": "",
"category": "ec",
"attr_id": attr_id,
"_": str(int(round(t * 1000))),
}
interest_rate_data = []
try:
while True:
response = requests.get(
url=base_url, params=params, headers=headers, timeout=10
)
data = response.json()
if not data.get("data", {}).get("values"):
break
interest_rate_data.extend(data["data"]["values"])
# Update max_date for pagination
last_date = data["data"]["values"][-1][0]
next_date = (
datetime.datetime.strptime(last_date, "%Y-%m-%d").date()
- datetime.timedelta(days=1)
).isoformat()
params["max_date"] = next_date
except requests.exceptions.RequestException as e:
print(f"Error fetching data: {e}")
return pd.DataFrame()
# Convert to DataFrame
big_df = pd.DataFrame(interest_rate_data)
if big_df.empty:
return pd.DataFrame()
# Process DataFrame
big_df["商品"] = name
big_df.columns = ["日期", "今值", "预测值", "前值", "商品"]
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
# Convert data types
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
numeric_columns = ["今值", "预测值", "前值"]
for col in numeric_columns:
big_df[col] = pd.to_numeric(big_df[col], errors="coerce")
return big_df.sort_values("日期").reset_index(drop=True)
# 金十数据中心-经济指标-央行利率-主要央行利率-美联储利率决议报告
def macro_bank_usa_interest_rate() -> pd.DataFrame:
"""
美联储利率决议报告, 数据区间从 19820927-至今
https://datacenter.jin10.com/reportType/dc_usa_interest_rate_decision
:return: 美联储利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="24", name="美联储利率决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-欧洲央行决议报告
def macro_bank_euro_interest_rate() -> pd.DataFrame:
"""
欧洲央行决议报告, 数据区间从 19990101-至今
https://datacenter.jin10.com/reportType/dc_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_interest_rate_decision_all.js?v=1578581663
:return: 欧洲央行决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="21", name="欧洲央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-新西兰联储决议报告
def macro_bank_newzealand_interest_rate() -> pd.DataFrame:
"""
新西兰联储决议报告, 数据区间从 19990401-至今
https://datacenter.jin10.com/reportType/dc_newzealand_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_newzealand_interest_rate_decision_all.js?v=1578582075
:return: 新西兰联储决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="23", name="新西兰利率决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-中国央行决议报告
def macro_bank_china_interest_rate() -> pd.DataFrame:
"""
中国央行决议报告, 数据区间从 19990105-至今
https://datacenter.jin10.com/reportType/dc_newzealand_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_newzealand_interest_rate_decision_all.js?v=1578582075
:return: 新西兰联储决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="91", name="中国央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-瑞士央行决议报告
def macro_bank_switzerland_interest_rate() -> pd.DataFrame:
"""
瑞士央行利率决议报告, 数据区间从 20080313-至今
https://datacenter.jin10.com/reportType/dc_switzerland_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_switzerland_interest_rate_decision_all.js?v=1578582240
:return: 瑞士央行利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="25", name="瑞士央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-英国央行决议报告
def macro_bank_english_interest_rate() -> pd.DataFrame:
"""
英国央行决议报告, 数据区间从 19700101-至今
https://datacenter.jin10.com/reportType/dc_english_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_english_interest_rate_decision_all.js?v=1578582331
:return: 英国央行决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="26", name="英国央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-澳洲联储决议报告
def macro_bank_australia_interest_rate() -> pd.DataFrame:
"""
澳洲联储决议报告, 数据区间从 19800201-至今
https://datacenter.jin10.com/reportType/dc_australia_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_australia_interest_rate_decision_all.js?v=1578582414
:return: 澳洲联储决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="27", name="澳洲联储决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-日本央行决议报告
def macro_bank_japan_interest_rate() -> pd.DataFrame:
"""
日本利率决议报告, 数据区间从 20080214-至今
https://datacenter.jin10.com/reportType/dc_japan_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_japan_interest_rate_decision_all.js?v=1578582485
:return: 日本利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="22", name="日本央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-俄罗斯央行决议报告
def macro_bank_russia_interest_rate() -> pd.DataFrame:
"""
俄罗斯利率决议报告, 数据区间从 20030601-至今
https://datacenter.jin10.com/reportType/dc_russia_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_russia_interest_rate_decision_all.js?v=1578582572
:return: 俄罗斯利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="64", name="俄罗斯央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-印度央行决议报告
def macro_bank_india_interest_rate() -> pd.DataFrame:
"""
印度利率决议报告, 数据区间从 20000801-至今
https://datacenter.jin10.com/reportType/dc_india_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_india_interest_rate_decision_all.js?v=1578582645
:return: 印度利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="68", name="印度央行决议报告")
# 金十数据中心-经济指标-央行利率-主要央行利率-巴西央行决议报告
def macro_bank_brazil_interest_rate() -> pd.DataFrame:
"""
巴西利率决议报告, 数据区间从 20080201-至今
https://datacenter.jin10.com/reportType/dc_brazil_interest_rate_decision
https://cdn.jin10.com/dc/reports/dc_brazil_interest_rate_decision_all.js?v=1578582718
:return: 巴西利率决议报告-今值(%)
:rtype: pandas.Series
"""
return __get_interest_rate_data(attr_id="55", name="巴西央行决议报告")
if __name__ == "__main__":
# 金十数据中心-经济指标-央行利率-主要央行利率-美联储利率决议报告
macro_bank_usa_interest_rate_df = macro_bank_usa_interest_rate()
print(macro_bank_usa_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-欧洲央行决议报告
macro_bank_euro_interest_rate_df = macro_bank_euro_interest_rate()
print(macro_bank_euro_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-新西兰联储决议报告
macro_bank_newzealand_interest_rate_df = macro_bank_newzealand_interest_rate()
print(macro_bank_newzealand_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-中国央行决议报告
macro_bank_china_interest_rate_df = macro_bank_china_interest_rate()
print(macro_bank_china_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-瑞士央行决议报告
macro_bank_switzerland_interest_rate_df = macro_bank_switzerland_interest_rate()
print(macro_bank_switzerland_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-英国央行决议报告
macro_bank_english_interest_rate_df = macro_bank_english_interest_rate()
print(macro_bank_english_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-澳洲联储决议报告
macro_bank_australia_interest_rate_df = macro_bank_australia_interest_rate()
print(macro_bank_australia_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-日本央行决议报告
macro_bank_japan_interest_rate_df = macro_bank_japan_interest_rate()
print(macro_bank_japan_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-俄罗斯央行决议报告
macro_bank_russia_interest_rate_df = macro_bank_russia_interest_rate()
print(macro_bank_russia_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-印度央行决议报告
macro_bank_india_interest_rate_df = macro_bank_india_interest_rate()
print(macro_bank_india_interest_rate_df)
# 金十数据中心-经济指标-央行利率-主要央行利率-巴西央行决议报告
macro_bank_brazil_interest_rate_df = macro_bank_brazil_interest_rate()
print(macro_bank_brazil_interest_rate_df)
@@ -0,0 +1,552 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/11/27 20:30
Desc: 东方财富-经济数据-加拿大
https://data.eastmoney.com/cjsj/foreign_5_0.html
"""
import pandas as pd
import requests
# 新屋开工
def macro_canada_new_house_rate() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-新屋开工
https://data.eastmoney.com/cjsj/foreign_7_0.html
:return: 新屋开工
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00342247")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 失业率
def macro_canada_unemployment_rate() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-失业率
https://data.eastmoney.com/cjsj/foreign_7_1.html
:return: 失业率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00157746")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 贸易帐
def macro_canada_trade() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-贸易帐
https://data.eastmoney.com/cjsj/foreign_7_2.html
:return: 贸易帐
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00102022")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 零售销售月率
def macro_canada_retail_rate_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-零售销售月率
https://data.eastmoney.com/cjsj/foreign_7_3.html
:return: 零售销售月率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG01337094")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 央行公布利率决议
def macro_canada_bank_rate() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-央行公布利率决议
https://data.eastmoney.com/cjsj/foreign_7_4.html
:return: 央行公布利率决议
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00342248")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 核心消费者物价指数年率
def macro_canada_core_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-核心消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_7_5.html
:return: 核心消费者物价指数年率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00102030")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 核心消费者物价指数月率
def macro_canada_core_cpi_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-核心消费者物价指数月率
https://data.eastmoney.com/cjsj/foreign_7_6.html
:return: 核心消费者物价指数月率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00102044")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 消费者物价指数年率
def macro_canada_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_7_7.html
:return: 消费者物价指数年率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00102029")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# 消费者物价指数月率
def macro_canada_cpi_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-消费者物价指数月率
https://data.eastmoney.com/cjsj/foreign_7_8.html
:return: 消费者物价指数月率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00158719")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
# GDP 月率
def macro_canada_gdp_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-加拿大-GDP 月率
https://data.eastmoney.com/cjsj/foreign_7_9.html
:return: GDP 月率
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CA",
"columns": "ALL",
"filter": '(INDICATOR_ID="EMG00159259")',
"pageNumber": "1",
"pageSize": "2000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = [
"-",
"-",
"-",
"-",
"时间",
"-",
"发布日期",
"现值",
"前值",
]
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
return temp_df
if __name__ == "__main__":
macro_canada_new_house_rate_df = macro_canada_new_house_rate()
print(macro_canada_new_house_rate_df)
macro_canada_unemployment_rate_df = macro_canada_unemployment_rate()
print(macro_canada_unemployment_rate_df)
macro_canada_trade_df = macro_canada_trade()
print(macro_canada_trade_df)
macro_canada_retail_rate_monthly_df = macro_canada_retail_rate_monthly()
print(macro_canada_retail_rate_monthly_df)
macro_canada_bank_rate_df = macro_canada_bank_rate()
print(macro_canada_bank_rate_df)
macro_canada_core_cpi_yearly_df = macro_canada_core_cpi_yearly()
print(macro_canada_core_cpi_yearly_df)
macro_canada_core_cpi_monthly_df = macro_canada_core_cpi_monthly()
print(macro_canada_core_cpi_monthly_df)
macro_canada_cpi_yearly_df = macro_canada_cpi_yearly()
print(macro_canada_cpi_yearly_df)
macro_canada_cpi_monthly_df = macro_canada_cpi_monthly()
print(macro_canada_cpi_monthly_df)
macro_canada_gdp_monthly_df = macro_canada_gdp_monthly()
print(macro_canada_gdp_monthly_df)
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,194 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/3 16:21
Desc: 中国-香港-宏观指标
https://data.eastmoney.com/cjsj/foreign_8_0.html
"""
import pandas as pd
import requests
def macro_china_hk_core(symbol: str = "EMG00341602") -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-宏观经济-日本-核心代码
https://data.eastmoney.com/cjsj/foreign_1_0.html
:param symbol: 代码
:type symbol: str
:return: 指定 symbol 的数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_HK",
"columns": "ALL",
"filter": f'(INDICATOR_ID="{symbol}")',
"pageNumber": "1",
"pageSize": "5000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.rename(
columns={
"COUNTRY": "-",
"INDICATOR_ID": "-",
"INDICATOR_NAME": "-",
"REPORT_DATE_CH": "时间",
"REPORT_DATE": "-",
"PUBLISH_DATE": "发布日期",
"VALUE": "现值",
"PRE_VALUE": "前值",
"INDICATOR_IDOLD": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(["发布日期"], inplace=True, ignore_index=True)
return temp_df
def macro_china_hk_cpi() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-消费者物价指数
https://data.eastmoney.com/cjsj/foreign_8_0.html
:return: 消费者物价指数
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG01336996")
return temp_df
def macro_china_hk_cpi_ratio() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_8_1.html
:return: 消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00059282")
return temp_df
def macro_china_hk_rate_of_unemployment() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-失业率
https://data.eastmoney.com/cjsj/foreign_8_2.html
:return: 失业率
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00059647")
return temp_df
def macro_china_hk_gbp() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港 GDP
https://data.eastmoney.com/cjsj/foreign_8_3.html
:return: 香港 GDP
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG01337008")
return temp_df
def macro_china_hk_gbp_ratio() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港 GDP 同比
https://data.eastmoney.com/cjsj/foreign_8_4.html
:return: 香港 GDP 同比
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG01337009")
return temp_df
def macro_china_hk_building_volume() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港楼宇买卖合约数量
https://data.eastmoney.com/cjsj/foreign_8_5.html
:return: 香港楼宇买卖合约数量
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00158055")
return temp_df
def macro_china_hk_building_amount() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港楼宇买卖合约成交金额
https://data.eastmoney.com/cjsj/foreign_8_6.html
:return: 香港楼宇买卖合约成交金额
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00158066")
return temp_df
def macro_china_hk_trade_diff_ratio() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港商品贸易差额年率
https://data.eastmoney.com/cjsj/foreign_8_7.html
:return: 香港商品贸易差额年率
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00157898")
return temp_df
def macro_china_hk_ppi() -> pd.DataFrame:
"""
东方财富-经济数据一览-中国香港-香港制造业 PPI 年率
https://data.eastmoney.com/cjsj/foreign_8_8.html
:return: 香港制造业 PPI 年率
:rtype: pandas.DataFrame
"""
temp_df = macro_china_hk_core(symbol="EMG00157818")
return temp_df
if __name__ == "__main__":
macro_china_hk_cpi_df = macro_china_hk_cpi()
print(macro_china_hk_cpi_df)
macro_china_hk_cpi_ratio_df = macro_china_hk_cpi_ratio()
print(macro_china_hk_cpi_ratio_df)
macro_china_hk_rate_of_unemployment_df = macro_china_hk_rate_of_unemployment()
print(macro_china_hk_rate_of_unemployment_df)
macro_china_hk_gbp_df = macro_china_hk_gbp()
print(macro_china_hk_gbp_df)
macro_china_hk_gbp_ratio_df = macro_china_hk_gbp_ratio()
print(macro_china_hk_gbp_ratio_df)
marco_china_hk_building_volume_df = macro_china_hk_building_volume()
print(marco_china_hk_building_volume_df)
macro_china_hk_building_amount_df = macro_china_hk_building_amount()
print(macro_china_hk_building_amount_df)
macro_china_hk_trade_diff_ratio_df = macro_china_hk_trade_diff_ratio()
print(macro_china_hk_trade_diff_ratio_df)
macro_china_hk_ppi_df = macro_china_hk_ppi()
print(macro_china_hk_ppi_df)
@@ -0,0 +1,293 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/6/30 22:00
Desc: 中国-国家统计局-宏观数据
https://data.stats.gov.cn/easyquery.htm
"""
import time
from functools import lru_cache
from typing import Union, Literal, List, Dict
import jsonpath as jp
import numpy as np
import pandas as pd
import requests
import urllib3
from urllib3.exceptions import InsecureRequestWarning
# 忽略InsecureRequestWarning警告
urllib3.disable_warnings(InsecureRequestWarning)
@lru_cache
def _get_nbs_tree(idcode: str, dbcode: str) -> List[Dict]:
"""
获取指标目录树
:param idcode: 指标编码
:param dbcode: 库编码
:return: json数据
"""
url = "https://data.stats.gov.cn/easyquery.htm"
params = {"id": idcode, "dbcode": dbcode, "wdcode": "zb", "m": "getTree"}
r = requests.post(url, params=params, verify=False, allow_redirects=True)
data_json = r.json()
return data_json
@lru_cache
def _get_nbs_wds_tree(idcode: str, dbcode: str, rowcode: str) -> List[Dict]:
"""
获取地区数据的可选指标目录树
:param idcode: 指标编码
:param dbcode: 库编码
:param rowcode: 值为zb是返回地区的编码值为reg时返回可选指标的编码
:return: json数据
"""
url = "https://data.stats.gov.cn/easyquery.htm"
params = {
"m": "getOtherWds",
"dbcode": dbcode,
"rowcode": rowcode,
"colcode": "sj",
"wds": '[{"wdcode":"zb","valuecode":"%s"}]' % idcode,
"k1": str(time.time_ns())[:13],
}
r = requests.post(url, params=params, verify=False, allow_redirects=True)
data_json = r.json()
data_json = data_json["returndata"][0]["nodes"]
return data_json
def _get_code_from_nbs_tree(tree: List[Dict], name: str, target: str = "id") -> str:
"""
根据指标名称从目录树中获取target编码
:param tree: 目录树
:param name: 指标名称
:param target: 指标编码属性名
:return: 指标编码
"""
expr = f'$[?(@.name == "{name}")].{target}'
ret = jp.jsonpath(tree, expr)
if ret is False:
raise ValueError("Please check if the data path or indicator is correct.")
return ret[0]
def macro_china_nbs_nation(
kind: Literal["月度数据", "季度数据", "年度数据"], path: str, period: str = "LAST10"
) -> pd.DataFrame:
"""
国家统计局全国数据通用接口
https://data.stats.gov.cn/easyquery.htm
:param kind: 数据类别
:param path: 数据路径
:param period: 时间区间例如'LAST10', '2016-2023', '2016-'
:return: 国家统计局统计数据
:rtype: pandas.DataFrame
"""
# 获取dbcode
kind_code = {"月度数据": "hgyd", "季度数据": "hgjd", "年度数据": "hgnd"}
dbcode = kind_code[kind]
# 获取最终id
parent_tree = _get_nbs_tree("zb", dbcode)
path_split = path.replace(" ", "").split(">")
indicator_id = _get_code_from_nbs_tree(parent_tree, path_split[0])
path_split.pop(0)
while path_split:
temp_tree = _get_nbs_tree(indicator_id, dbcode)
indicator_id = _get_code_from_nbs_tree(temp_tree, path_split[0])
path_split.pop(0)
# 请求数据
url = "https://data.stats.gov.cn/easyquery.htm"
params = {
"m": "QueryData",
"dbcode": dbcode,
"rowcode": "zb",
"colcode": "sj",
"wds": "[]",
"dfwds": '[{"wdcode":"zb","valuecode":"%s"}, '
'{"wdcode":"sj","valuecode":"%s"}]' % (indicator_id, period),
"k1": str(time.time_ns())[:13],
}
r = requests.get(url, params=params, verify=False, allow_redirects=True)
data_json = r.json()
# 整理为dataframe
temp_df = pd.DataFrame(data_json["returndata"]["datanodes"])
temp_df["data"] = temp_df["data"].apply(
lambda x: x["data"] if x["hasdata"] else None
)
wdnodes = data_json["returndata"]["wdnodes"]
wn_df_list = []
for wn in wdnodes:
wn_df_list.append(
pd.DataFrame(wn["nodes"])
.assign(
funit=lambda df: df["unit"].apply(lambda x: "(" + x + ")" if x else x)
)
.assign(fname=lambda df: df["cname"] + df["funit"]),
)
row_name, column_name = (
wn_df_list[0]["fname"],
wn_df_list[1]["fname"],
)
data_ndarray = np.reshape(temp_df["data"], (len(row_name), len(column_name)))
data_df = pd.DataFrame(data=data_ndarray, columns=column_name, index=row_name)
data_df.index.name = None
data_df.columns.name = None
return data_df
def macro_china_nbs_region(
kind: Literal[
"分省月度数据",
"分省季度数据",
"分省年度数据",
"主要城市月度价格",
"主要城市年度数据",
"港澳台月度数据",
"港澳台年度数据",
],
path: str,
indicator: Union[str, None],
region: Union[str, None] = None,
period: str = "LAST10",
) -> pd.DataFrame:
"""
国家统计局地区数据通用接口
https://data.stats.gov.cn/easyquery.htm
:param kind: 数据类别
:param path: 数据路径
:param indicator: 指定指标
:param region: 指定地区 当指定region时将symbol设为None可以同时获得所有可选指标的值
:param period: 时间区间例如'LAST10', '2016-2023', '2016-'
:return: 国家统计局统计数据
:rtype: pandas.DataFrame
"""
if indicator is None and region is None:
raise AssertionError("The indicator and region parameters cannot both be None.")
# 获取dbcode
kind_dict = {
"分省月度数据": "fsyd",
"分省季度数据": "fsjd",
"分省年度数据": "fsnd",
"主要城市月度价格": "csyd",
"主要城市年度数据": "csnd",
"港澳台月度数据": "gatyd",
"港澳台年度数据": "gatnd",
}
dbcode = kind_dict[kind]
# 获取最终id
parent_tree = _get_nbs_tree("zb", dbcode)
path_split = path.replace(" ", "").split(">")
indicator_id = _get_code_from_nbs_tree(parent_tree, path_split[0])
path_split.pop(0)
while path_split:
temp_tree = _get_nbs_tree(indicator_id, dbcode)
indicator_id = _get_code_from_nbs_tree(temp_tree, path_split[0])
path_split.pop(0)
# 参数设定
if region is None:
indicator_tree = _get_nbs_wds_tree(indicator_id, dbcode, "reg")
indicator_id = _get_code_from_nbs_tree(indicator_tree, indicator, target="code")
rowcode = "reg"
colcode = "sj"
wds = '[{"wdcode":"zb","valuecode":"%s"}]' % indicator_id
dfwds = '[{"wdcode":"sj","valuecode":"%s"}]' % period
else:
if indicator is not None:
indicator_tree = _get_nbs_wds_tree(indicator_id, dbcode, "reg")
indicator_id = _get_code_from_nbs_tree(
indicator_tree, indicator, target="code"
)
region_tree = _get_nbs_wds_tree(indicator_id, dbcode, "zb")
region_id = _get_code_from_nbs_tree(region_tree, region, target="code")
rowcode = "zb"
colcode = "sj"
wds = '[{"wdcode":"reg","valuecode":"%s"}]' % region_id
dfwds = (
'[{"wdcode":"zb","valuecode":"%s"}, '
'{"wdcode":"sj","valuecode":"%s"}]' % (indicator_id, period)
)
# 请求数据
url = "https://data.stats.gov.cn/easyquery.htm"
params = {
"m": "QueryData",
"dbcode": dbcode,
"rowcode": rowcode,
"colcode": colcode,
"wds": wds,
"dfwds": dfwds,
"k1": str(time.time_ns())[:13],
}
r = requests.get(url, params=params, verify=False, allow_redirects=True)
data_json = r.json()
# 整理为dataframe
temp_df = pd.DataFrame(data_json["returndata"]["datanodes"])
temp_df["data"] = temp_df["data"].apply(
lambda x: x["data"] if x["hasdata"] else None
)
wdnodes = data_json["returndata"]["wdnodes"]
wn_df_list = []
for wn in wdnodes:
wn_df_list.append(
pd.DataFrame(wn["nodes"])
.assign(
funit=lambda df: df["unit"].apply(lambda x: "(" + x + ")" if x else x)
)
.assign(fname=lambda df: df["cname"] + df["funit"]),
)
if region is None:
row_name, column_name = wn_df_list[1]["fname"], wn_df_list[2]["fname"]
title_name = wn_df_list[0]["fname"][0]
else:
row_name, column_name = wn_df_list[0]["fname"], wn_df_list[2]["fname"]
title_name = wn_df_list[1]["fname"][0]
data_ndarray = np.reshape(temp_df["data"], (len(row_name), len(column_name)))
data_df = pd.DataFrame(data=data_ndarray, columns=column_name, index=row_name)
data_df.index.name = None
data_df.columns.name = title_name
return data_df
if __name__ == "__main__":
macro_china_nbs_nation_df = macro_china_nbs_nation(
kind="月度数据",
path="工业 > 工业分大类行业出口交货值(2018-至今) > 废弃资源综合利用业",
period="LAST5",
)
print(macro_china_nbs_nation_df)
macro_china_nbs_region_df = macro_china_nbs_region(
kind="分省季度数据",
path="人民生活 > 居民人均可支配收入",
period="2018-2022",
indicator=None,
region="北京市",
)
print(macro_china_nbs_region_df)
macro_china_nbs_region_df = macro_china_nbs_region(
kind="分省季度数据",
path="国民经济核算 > 地区生产总值",
period="2018-",
indicator="地区生产总值_累计值(亿元)",
)
print(macro_china_nbs_region_df)
@@ -0,0 +1,246 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/3 16:08
Desc: 金十数据-数据中心-主要机构-宏观经济
https://datacenter.jin10.com/
"""
import datetime
import time
import pandas as pd
import requests
from tqdm import tqdm
def macro_cons_gold() -> pd.DataFrame:
"""
全球最大黄金 ETFSPDR Gold Trust 持仓报告, 数据区间从 20041118-至今
https://datacenter.jin10.com/reportType/dc_etf_gold
:return: 持仓报告
:rtype: pandas.DataFrame
"""
t = time.time()
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"category": "etf",
"attr_id": "1",
"max_date": "",
"_": str(int(round(t * 1000))),
}
big_df = pd.DataFrame()
while True:
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
if not data_json["data"]["values"]:
break
temp_df = pd.DataFrame(data_json["data"]["values"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
last_date_str = temp_df.iat[-1, 0]
last_date_str = (
(
datetime.datetime.strptime(last_date_str, "%Y-%m-%d")
- datetime.timedelta(days=1)
)
.date()
.isoformat()
)
params.update({"max_date": f"{last_date_str}"})
big_df.columns = [
"日期",
"总库存",
"增持/减持",
"总价值",
]
big_df["商品"] = "黄金"
big_df = big_df[
[
"商品",
"日期",
"总库存",
"增持/减持",
"总价值",
]
]
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce").dt.date
big_df["总库存"] = pd.to_numeric(big_df["总库存"], errors="coerce")
big_df["增持/减持"] = pd.to_numeric(big_df["增持/减持"], errors="coerce")
big_df["总价值"] = pd.to_numeric(big_df["总价值"], errors="coerce")
big_df.sort_values(["日期"], inplace=True)
big_df.reset_index(inplace=True, drop=True)
return big_df
def macro_cons_silver() -> pd.DataFrame:
"""
全球最大白银 ETFSPDR Gold Trust 持仓报告, 数据区间从 20041118-至今
https://datacenter.jin10.com/reportType/dc_etf_sliver
:return: 持仓报告
:rtype: pandas.DataFrame
"""
t = time.time()
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"category": "etf",
"attr_id": "2",
"max_date": "",
"_": str(int(round(t * 1000))),
}
big_df = pd.DataFrame()
while True:
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
if not data_json["data"]["values"]:
break
temp_df = pd.DataFrame(data_json["data"]["values"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
last_date_str = temp_df.iat[-1, 0]
last_date_str = (
(
datetime.datetime.strptime(last_date_str, "%Y-%m-%d")
- datetime.timedelta(days=1)
)
.date()
.isoformat()
)
params.update({"max_date": f"{last_date_str}"})
big_df.columns = [
"日期",
"总库存",
"增持/减持",
"总价值",
]
big_df["商品"] = "白银"
big_df = big_df[
[
"商品",
"日期",
"总库存",
"增持/减持",
"总价值",
]
]
big_df["日期"] = pd.to_datetime(big_df["日期"], errors="coerce").dt.date
big_df["总库存"] = pd.to_numeric(big_df["总库存"], errors="coerce")
big_df["增持/减持"] = pd.to_numeric(big_df["增持/减持"], errors="coerce")
big_df["总价值"] = pd.to_numeric(big_df["总价值"], errors="coerce")
big_df.sort_values(["日期"], inplace=True)
big_df.reset_index(inplace=True, drop=True)
return big_df
def macro_cons_opec_month() -> pd.DataFrame:
"""
欧佩克报告-月度, 数据区间从 20170118-至今
这里返回的具体索引日期的数据为上一个月的数据, 由于某些国家的数据有缺失
只选择有数据的国家返回
20200312:fix:由于 厄瓜多尔 已经有几个月没有更新数据在这里加以剔除
https://datacenter.jin10.com/reportType/dc_opec_report
:return: 欧佩克报告-月度
:rtype: pandas.DataFrame
"""
t = time.time()
big_df = pd.DataFrame()
headers = {
"accept": "*/*",
"accept-encoding": "gzip, deflate, br",
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8",
"cache-control": "no-cache",
"origin": "https://datacenter.jin10.com",
"pragma": "no-cache",
"referer": "https://datacenter.jin10.com/reportType/dc_opec_report",
"sec-fetch-mode": "cors",
"sec-fetch-site": "same-site",
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/79.0.3945.117 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "",
"x-version": "1.0.0",
}
res = requests.get(
url=f"https://datacenter-api.jin10.com/reports/dates?category=opec&_={str(int(round(t * 1000)))}",
headers=headers,
) # 日期序列
all_date_list = res.json()["data"]
bar = tqdm(reversed(all_date_list))
for item in bar:
bar.set_description(f"Please wait for a moment, now downloading {item}'s data")
res = requests.get(
url=f"https://datacenter-api.jin10.com/reports/list?"
f"category=opec&date={item}&_={str(int(round(t * 1000)))}",
headers=headers,
)
temp_df = pd.DataFrame(
res.json()["data"]["values"],
columns=pd.DataFrame(res.json()["data"]["keys"])["name"].tolist(),
).T
temp_df.columns = temp_df.iloc[0, :]
temp_df = temp_df.iloc[1:, :]
try:
temp_df = temp_df[
[
"阿尔及利亚",
"安哥拉",
"加蓬",
"伊朗",
"伊拉克",
"科威特",
"利比亚",
"尼日利亚",
"沙特",
"阿联酋",
"委内瑞拉",
"欧佩克产量",
]
].iloc[-2, :]
except: # noqa: E722
temp_df = temp_df[
[
"阿尔及利亚",
"安哥拉",
"加蓬",
"伊朗",
"伊拉克",
"科威特",
"利比亚",
"尼日利亚",
"沙特",
"阿联酋",
"委内瑞拉",
"欧佩克产量",
]
].iloc[-1, :]
temp_df.dropna(inplace=True)
big_df[temp_df.name] = temp_df
big_df = big_df.T
big_df = big_df.astype(float)
big_df.reset_index(inplace=True)
big_df.rename(columns={"index": "日期"}, inplace=True)
big_df.columns.name = None
return big_df
if __name__ == "__main__":
macro_cons_gold_df = macro_cons_gold()
print(macro_cons_gold_df)
macro_cons_silver_df = macro_cons_silver()
print(macro_cons_silver_df)
macro_cons_opec_month_df = macro_cons_opec_month()
print(macro_cons_opec_month_df)
@@ -0,0 +1,959 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/3 17:08
Desc: 金十数据中心-经济指标-欧元区
金十数据中心-经济指标-欧元区-国民经济运行状况-经济状况
金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平
金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场
金十数据中心-经济指标-欧元区-贸易状况
金十数据中心-经济指标-欧元区-产业指标
金十数据中心-经济指标-欧元区-领先指标
"""
import time
import pandas as pd
import requests
from tqdm import tqdm
# 金十数据中心-经济指标-欧元区-国民经济运行状况
# 金十数据中心-经济指标-欧元区-国民经济运行状况-经济状况
# 金十数据中心-经济指标-欧元区-国民经济运行状况-经济状况-欧元区季度GDP年率报告
def macro_euro_gdp_yoy() -> pd.DataFrame:
"""
欧元区季度 GDP 年率报告, 数据区间从 20131114-至今
https://datacenter.jin10.com/reportType/dc_eurozone_gdp_yoy
:return: 欧元区季度 GDP 年率报告
:rtype: pandas.DataFrame
"""
ec = 84
url = "https://datacenter-api.jin10.com/reports/dates"
params = {"category": "ec", "attr_id": ec}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区季度GDP年率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区CPI月率报告
def macro_euro_cpi_mom() -> pd.DataFrame:
"""
欧元区 CPI 月率报告, 数据区间从 19900301-至今
https://datacenter.jin10.com/reportType/dc_eurozone_cpi_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_cpi_mom_all.js?v=1578578318
:return: 欧元区CPI月率报告
:rtype: pandas.Series
"""
ec = 84
url = "https://datacenter-api.jin10.com/reports/dates"
params = {"category": "ec", "attr_id": ec}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区CPI月率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区CPI年率报告
def macro_euro_cpi_yoy() -> pd.DataFrame:
"""
欧元区CPI年率报告, 数据区间从19910201-至今
https://datacenter.jin10.com/reportType/dc_eurozone_cpi_yoy
https://cdn.jin10.com/dc/reports/dc_eurozone_cpi_yoy_all.js?v=1578578404
:return: 欧元区CPI年率报告-今值(%)
:rtype: pandas.Series
"""
ec = 8
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区CPI年率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区PPI月率报告
def macro_euro_ppi_mom() -> pd.DataFrame:
"""
欧元区PPI月率报告, 数据区间从19810301-至今
https://datacenter.jin10.com/reportType/dc_eurozone_ppi_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_ppi_mom_all.js?v=1578578493
:return: 欧元区PPI月率报告-今值(%)
:rtype: pandas.Series
"""
ec = 36
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区PPI月率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区零售销售月率报告
def macro_euro_retail_sales_mom() -> pd.DataFrame:
"""
欧元区零售销售月率报告, 数据区间从20000301-至今
https://datacenter.jin10.com/reportType/dc_eurozone_retail_sales_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_retail_sales_mom_all.js?v=1578578576
:return: 欧元区零售销售月率报告-今值(%)
:rtype: pandas.Series
"""
ec = 38
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区零售销售月率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场-欧元区季调后就业人数季率报告
def macro_euro_employment_change_qoq() -> pd.DataFrame:
"""
欧元区季调后就业人数季率报告, 数据区间从20083017-至今
https://datacenter.jin10.com/reportType/dc_eurozone_employment_change_qoq
https://cdn.jin10.com/dc/reports/dc_eurozone_employment_change_qoq_all.js?v=1578578699
:return: 欧元区季调后就业人数季率报告-今值(%)
:rtype: pandas.Series
"""
ec = 14
url = "https://datacenter-api.jin10.com/reports/dates"
params = {"category": "ec", "attr_id": ec}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区季调后就业人数季率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场-欧元区失业率报告
def macro_euro_unemployment_rate_mom() -> pd.DataFrame:
"""
欧元区失业率报告, 数据区间从19980501-至今
https://datacenter.jin10.com/reportType/dc_eurozone_unemployment_rate_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_unemployment_rate_mom_all.js?v=1578578767
:return: 欧元区失业率报告-今值(%)
:rtype: pandas.Series
"""
ec = 46
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区失业率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-贸易状况-欧元区未季调贸易帐报告
def macro_euro_trade_balance() -> pd.DataFrame:
"""
欧元区未季调贸易帐报告, 数据区间从19990201-至今
https://datacenter.jin10.com/reportType/dc_eurozone_trade_balance_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_trade_balance_mom_all.js?v=1578577862
:return: 欧元区未季调贸易帐报告-今值(亿欧元)
:rtype: pandas.Series
"""
ec = 43
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区未季调贸易帐"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-贸易状况-欧元区经常帐报告
def macro_euro_current_account_mom() -> pd.DataFrame:
"""
欧元区经常帐报告, 数据区间从20080221-至今, 前两个值需要去掉
https://datacenter.jin10.com/reportType/dc_eurozone_current_account_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_current_account_mom_all.js?v=1578577976
:return: 欧元区经常帐报告-今值(亿欧元)
:rtype: pandas.Series
"""
ec = 11
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区经常帐"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-产业指标-欧元区工业产出月率报告
def macro_euro_industrial_production_mom() -> pd.DataFrame:
"""
欧元区工业产出月率报告, 数据区间从19910301-至今
https://datacenter.jin10.com/reportType/dc_eurozone_industrial_production_mom
https://cdn.jin10.com/dc/reports/dc_eurozone_industrial_production_mom_all.js?v=1578577377
:return: 欧元区工业产出月率报告-今值(%)
:rtype: pandas.Series
"""
ec = 19
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区工业产出月率"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-产业指标-欧元区制造业PMI初值报告
def macro_euro_manufacturing_pmi() -> pd.DataFrame:
"""
欧元区制造业PMI初值报告, 数据区间从20080222-至今
https://datacenter.jin10.com/reportType/dc_eurozone_manufacturing_pmi
https://cdn.jin10.com/dc/reports/dc_eurozone_manufacturing_pmi_all.js?v=1578577537
:return: 欧元区制造业PMI初值报告-今值
:rtype: pandas.Series
"""
ec = 30
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区制造业PMI初值"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-产业指标-欧元区服务业PMI终值报告
def macro_euro_services_pmi() -> pd.DataFrame:
"""
欧元区服务业PMI终值报告, 数据区间从 20080222-至今
https://datacenter.jin10.com/reportType/dc_eurozone_services_pmi
https://cdn.jin10.com/dc/reports/dc_eurozone_services_pmi_all.js?v=1578577639
:return: 欧元区服务业PMI终值报告-今值
:rtype: pandas.Series
"""
ec = 41
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区服务业PMI终值"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-领先指标-欧元区ZEW经济景气指数报告
def macro_euro_zew_economic_sentiment() -> pd.DataFrame:
"""
欧元区ZEW经济景气指数报告, 数据区间从20080212-至今
https://datacenter.jin10.com/reportType/dc_eurozone_zew_economic_sentiment
https://cdn.jin10.com/dc/reports/dc_eurozone_zew_economic_sentiment_all.js?v=1578577013
:return: 欧元区ZEW经济景气指数报告-今值
:rtype: pandas.Series
"""
ec = 48
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区ZEW经济景气指数"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-经济指标-欧元区-领先指标-欧元区Sentix投资者信心指数报告
def macro_euro_sentix_investor_confidence() -> pd.DataFrame:
"""
欧元区Sentix投资者信心指数报告, 数据区间从20020801-至今
https://datacenter.jin10.com/reportType/dc_eurozone_sentix_investor_confidence
https://cdn.jin10.com/dc/reports/dc_eurozone_sentix_investor_confidence_all.js?v=1578577195
:return: 欧元区Sentix投资者信心指数报告-今值
:rtype: pandas.Series
"""
ec = 40
url = "https://datacenter-api.jin10.com/reports/dates"
params = {
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
date_list = data_json["data"]
date_point_list = [item for num, item in enumerate(date_list) if num % 20 == 0]
big_df = pd.DataFrame()
for date in tqdm(date_point_list, leave=False):
url = "https://datacenter-api.jin10.com/reports/list_v2"
params = {
"max_date": f"{date}",
"category": "ec",
"attr_id": ec,
}
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
data_json["data"]["values"],
columns=[item["name"] for item in data_json["data"]["keys"]],
)
big_df = pd.concat([big_df, temp_df], ignore_index=True)
big_df["商品"] = "欧元区Sentix投资者信心指数"
big_df = big_df[["商品", "日期", "今值", "预测值", "前值"]]
big_df["今值"] = pd.to_numeric(big_df["今值"])
big_df["预测值"] = pd.to_numeric(big_df["预测值"])
big_df["前值"] = pd.to_numeric(big_df["前值"])
big_df["日期"] = pd.to_datetime(big_df["日期"]).dt.date
big_df.sort_values(["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-伦敦金属交易所(LME)-持仓报告
def macro_euro_lme_holding() -> pd.DataFrame:
"""
伦敦金属交易所(LME)-持仓报告, 数据区间从 20151022-至今
https://datacenter.jin10.com/reportType/dc_lme_traders_report
https://cdn.jin10.com/data_center/reports/lme_position.json?_=1591533934658
:return: 伦敦金属交易所(LME)-持仓报告
:rtype: pandas.DataFrame
"""
t = time.time()
params = {"_": str(int(round(t * 1000)))}
r = requests.get(
url="https://cdn.jin10.com/data_center/reports/lme_position.json", params=params
)
json_data = r.json()
temp_df = pd.DataFrame(json_data["values"]).T
temp_df.fillna(value="[0, 0, 0]", inplace=True)
big_df = pd.DataFrame()
for item in temp_df.columns:
for i in range(3):
inner_temp_df = temp_df.loc[:, item].apply(lambda x: eval(str(x))[i])
inner_temp_df.name = inner_temp_df.name + "-" + json_data["keys"][i]["name"]
big_df = pd.concat(objs=[big_df, inner_temp_df], axis=1)
big_df = big_df.astype("float")
big_df = big_df.iloc[:-1, :].copy()
big_df.reset_index(inplace=True)
big_df.rename(columns={"index": "日期"}, inplace=True)
big_df.sort_values(by=["日期"], ignore_index=True, inplace=True)
return big_df
# 金十数据中心-伦敦金属交易所(LME)-库存报告
def macro_euro_lme_stock() -> pd.DataFrame:
"""
伦敦金属交易所(LME)-库存报告, 数据区间从 20140702-至今
https://datacenter.jin10.com/reportType/dc_lme_report
https://cdn.jin10.com/data_center/reports/lme_stock.json?_=1591535304783
:return: 伦敦金属交易所(LME)-库存报告
:rtype: pandas.DataFrame
"""
t = time.time()
params = {"_": str(int(round(t * 1000)))}
r = requests.get(
url="https://cdn.jin10.com/data_center/reports/lme_stock.json", params=params
)
json_data = r.json()
temp_df = pd.DataFrame(json_data["values"]).T
big_df = pd.DataFrame()
for item in temp_df.columns:
for i in range(3):
inner_temp_df = temp_df.loc[:, item].apply(lambda x: eval(str(x))[i])
inner_temp_df.name = inner_temp_df.name + "-" + json_data["keys"][i]["name"]
big_df = pd.concat(objs=[big_df, inner_temp_df], axis=1)
big_df.sort_index(inplace=True)
big_df.reset_index(inplace=True)
big_df.rename(columns={"index": "日期"}, inplace=True)
return big_df
if __name__ == "__main__":
# 金十数据中心-经济指标-欧元区-国民经济运行状况
# 金十数据中心-经济指标-欧元区-国民经济运行状况-经济状况
# 金十数据中心-经济指标-欧元区-国民经济运行状况-经济状况-欧元区季度GDP年率报告
macro_euro_gdp_yoy_df = macro_euro_gdp_yoy()
print(macro_euro_gdp_yoy_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区CPI月率报告
macro_euro_cpi_mom_df = macro_euro_cpi_mom()
print(macro_euro_cpi_mom_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区CPI年率报告
macro_euro_cpi_yoy_df = macro_euro_cpi_yoy()
print(macro_euro_cpi_yoy_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区PPI月率报告
macro_euro_ppi_mom_df = macro_euro_ppi_mom()
print(macro_euro_ppi_mom_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-物价水平-欧元区零售销售月率报告
macro_euro_retail_sales_mom_df = macro_euro_retail_sales_mom()
print(macro_euro_retail_sales_mom_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场
# 金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场-欧元区季调后就业人数季率报告
macro_euro_employment_change_qoq_df = macro_euro_employment_change_qoq()
print(macro_euro_employment_change_qoq_df)
# 金十数据中心-经济指标-欧元区-国民经济运行状况-劳动力市场-欧元区失业率报告
macro_euro_unemployment_rate_mom_df = macro_euro_unemployment_rate_mom()
print(macro_euro_unemployment_rate_mom_df)
# 金十数据中心-经济指标-欧元区-贸易状况
# 金十数据中心-经济指标-欧元区-贸易状况-欧元区未季调贸易帐报告
macro_euro_trade_balance_df = macro_euro_trade_balance()
print(macro_euro_trade_balance_df)
# 金十数据中心-经济指标-欧元区-贸易状况-欧元区经常帐报告
macro_euro_current_account_mom_df = macro_euro_current_account_mom()
print(macro_euro_current_account_mom_df)
# 金十数据中心-经济指标-欧元区-产业指标
# 金十数据中心-经济指标-欧元区-产业指标-欧元区工业产出月率报告
macro_euro_industrial_production_mom_df = macro_euro_industrial_production_mom()
print(macro_euro_industrial_production_mom_df)
# 金十数据中心-经济指标-欧元区-产业指标-欧元区制造业PMI初值报告
macro_euro_manufacturing_pmi_df = macro_euro_manufacturing_pmi()
print(macro_euro_manufacturing_pmi_df)
# 金十数据中心-经济指标-欧元区-产业指标-欧元区服务业PMI终值报告
macro_euro_services_pmi_df = macro_euro_services_pmi()
print(macro_euro_services_pmi_df)
# 金十数据中心-经济指标-欧元区-领先指标
# 金十数据中心-经济指标-欧元区-领先指标-欧元区ZEW经济景气指数报告
macro_euro_zew_economic_sentiment_df = macro_euro_zew_economic_sentiment()
print(macro_euro_zew_economic_sentiment_df)
# 金十数据中心-经济指标-欧元区-领先指标-欧元区Sentix投资者信心指数报告
macro_euro_sentix_investor_confidence_df = macro_euro_sentix_investor_confidence()
print(macro_euro_sentix_investor_confidence_df)
# 金十数据中心-伦敦金属交易所(LME)-持仓报告
macro_euro_lme_holding_df = macro_euro_lme_holding()
print(macro_euro_lme_holding_df)
# 金十数据中心-伦敦金属交易所(LME)-库存报告
macro_euro_lme_stock_df = macro_euro_lme_stock()
print(macro_euro_lme_stock_df)
@@ -0,0 +1,136 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/10/21 20:00
Desc: 同花顺-数据中心-宏观数据-股票筹资
https://data.10jqka.com.cn/macro/finance/
"""
from io import StringIO
import pandas as pd
import requests
def macro_stock_finance() -> pd.DataFrame:
"""
同花顺-数据中心-宏观数据-股票筹资
https://data.10jqka.com.cn/macro/finance/
:return: 股票筹资
:rtype: pandas.DataFrame
"""
url = "https://data.10jqka.com.cn/macro/finance/"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 "
"(KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36"
}
r = requests.get(url, headers=headers)
temp_df = pd.read_html(StringIO(r.text))[0]
temp_df.rename(
columns={
"月份": "月份",
"募集资金(亿元)": "募集资金",
"首发募集资金(亿元)": "首发募集资金",
"增发募集资金(亿元)": "增发募集资金",
"配股募集资金(亿元)": "配股募集资金",
},
inplace=True,
)
temp_df = temp_df[
["月份", "募集资金", "首发募集资金", "增发募集资金", "配股募集资金"]
]
temp_df["募集资金"] = pd.to_numeric(temp_df["募集资金"], errors="coerce")
temp_df["首发募集资金"] = pd.to_numeric(temp_df["首发募集资金"], errors="coerce")
temp_df["增发募集资金"] = pd.to_numeric(temp_df["增发募集资金"], errors="coerce")
temp_df["配股募集资金"] = pd.to_numeric(temp_df["配股募集资金"], errors="coerce")
temp_df.sort_values(by=["月份"], inplace=True, ignore_index=True)
return temp_df
def macro_rmb_loan() -> pd.DataFrame:
"""
同花顺-数据中心-宏观数据-新增人民币贷款
https://data.10jqka.com.cn/macro/loan/
:return: 新增人民币贷款
:rtype: pandas.DataFrame
"""
url = "https://data.10jqka.com.cn/macro/loan/"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 "
"(KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36"
}
r = requests.get(url, headers=headers)
temp_df = pd.read_html(StringIO(r.text), skiprows=0)[0]
temp_df.columns = [
"月份",
"新增人民币贷款-总额",
"新增人民币贷款-同比",
"新增人民币贷款-环比",
"累计人民币贷款-总额",
"累计人民币贷款-同比",
]
temp_df["新增人民币贷款-总额"] = pd.to_numeric(
temp_df["新增人民币贷款-总额"], errors="coerce"
)
temp_df["累计人民币贷款-总额"] = pd.to_numeric(
temp_df["累计人民币贷款-总额"], errors="coerce"
)
temp_df.sort_values(by=["月份"], inplace=True, ignore_index=True)
return temp_df
def macro_rmb_deposit() -> pd.DataFrame:
"""
同花顺-数据中心-宏观数据-人民币存款余额
https://data.10jqka.com.cn/macro/rmb/
:return: 人民币存款余额
:rtype: pandas.DataFrame
"""
url = "https://data.10jqka.com.cn/macro/rmb/"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 "
"(KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36"
}
r = requests.get(url, headers=headers)
temp_df = pd.read_html(StringIO(r.text), skiprows=0)[0]
temp_df.columns = [
"月份",
"新增存款-数量",
"新增存款-同比",
"新增存款-环比",
"新增企业存款-数量",
"新增企业存款-同比",
"新增企业存款-环比",
"新增储蓄存款-数量",
"新增储蓄存款-同比",
"新增储蓄存款-环比",
"新增其他存款-数量",
"新增其他存款-同比",
"新增其他存款-环比",
]
temp_df["新增存款-数量"] = pd.to_numeric(temp_df["新增存款-数量"], errors="coerce")
temp_df["新增企业存款-数量"] = pd.to_numeric(
temp_df["新增企业存款-数量"], errors="coerce"
)
temp_df["新增企业存款-数量"] = pd.to_numeric(
temp_df["新增企业存款-数量"], errors="coerce"
)
temp_df["新增储蓄存款-数量"] = pd.to_numeric(
temp_df["新增储蓄存款-数量"], errors="coerce"
)
temp_df["新增其他存款-数量"] = pd.to_numeric(
temp_df["新增其他存款-数量"], errors="coerce"
)
temp_df.sort_values(by=["月份"], inplace=True, ignore_index=True)
return temp_df
if __name__ == "__main__":
macro_stock_finance_df = macro_stock_finance()
print(macro_stock_finance_df)
macro_rmb_loan_df = macro_rmb_loan()
print(macro_rmb_loan_df)
macro_rmb_deposit_df = macro_rmb_deposit()
print(macro_rmb_deposit_df)
@@ -0,0 +1,187 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/11/5 17:08
Desc: 东方财富-德国-经济数据
"""
import pandas as pd
import requests
def macro_germany_core(symbol: str = "EMG00179154") -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-宏观经济-德国-核心代码
https://data.eastmoney.com/cjsj/foreign_1_0.html
:param symbol: 代码
:type symbol: str
:return: 指定 symbol 的数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_GER",
"columns": "ALL",
"filter": f'(INDICATOR_ID="{symbol}")',
"pageNumber": "1",
"pageSize": "5000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.rename(
columns={
"COUNTRY": "-",
"INDICATOR_ID": "-",
"INDICATOR_NAME": "-",
"REPORT_DATE_CH": "时间",
"REPORT_DATE": "-",
"PUBLISH_DATE": "发布日期",
"VALUE": "现值",
"PRE_VALUE": "前值",
"INDICATOR_IDOLD": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"])
temp_df["现值"] = pd.to_numeric(temp_df["现值"])
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
temp_df.sort_values(["发布日期"], inplace=True, ignore_index=True)
return temp_df
# 东方财富-德国-经济数据-IFO商业景气指数
def macro_germany_ifo() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-IFO商业景气指数
https://data.eastmoney.com/cjsj/foreign_1_0.html
:return: IFO商业景气指数
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00179154")
return temp_df
# 东方财富-德国-经济数据-消费者物价指数月率终值
def macro_germany_cpi_monthly() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-消费者物价指数月率终值
https://data.eastmoney.com/cjsj/foreign_1_1.html
:return: 消费者物价指数月率终值
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00009758")
return temp_df
# 东方财富-德国-经济数据-消费者物价指数年率终值
def macro_germany_cpi_yearly() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-消费者物价指数年率终值
https://data.eastmoney.com/cjsj/foreign_1_2.html
:return: 消费者物价指数年率终值
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00009756")
return temp_df
# 东方财富-德国-经济数据-贸易帐(季调后)
def macro_germany_trade_adjusted() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-贸易帐(季调后)
https://data.eastmoney.com/cjsj/foreign_1_3.html
:return: 贸易帐(季调后)
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00009753")
return temp_df
# 东方财富-德国-经济数据-GDP
def macro_germany_gdp() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-GDP
https://data.eastmoney.com/cjsj/foreign_1_4.html
:return: GDP
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00009720")
return temp_df
# 东方财富-德国-经济数据-实际零售销售月率
def macro_germany_retail_sale_monthly() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-实际零售销售月率
https://data.eastmoney.com/cjsj/foreign_1_5.html
:return: 实际零售销售月率
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG01333186")
return temp_df
# 东方财富-德国-经济数据-实际零售销售年率
def macro_germany_retail_sale_yearly() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-实际零售销售年率
https://data.eastmoney.com/cjsj/foreign_1_6.html
:return: 实际零售销售年率
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG01333192")
return temp_df
# 东方财富-德国-经济数据-ZEW 经济景气指数
def macro_germany_zew() -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-德国-ZEW 经济景气指数
https://data.eastmoney.com/cjsj/foreign_1_7.html
:return: ZEW 经济景气指数
:rtype: pandas.DataFrame
"""
temp_df = macro_germany_core(symbol="EMG00172577")
return temp_df
if __name__ == "__main__":
macro_germany_ifo_df = macro_germany_ifo()
print(macro_germany_ifo_df)
macro_germany_cpi_monthly_df = macro_germany_cpi_monthly()
print(macro_germany_cpi_monthly_df)
macro_germany_cpi_yearly_df = macro_germany_cpi_yearly()
print(macro_germany_cpi_yearly_df)
macro_germany_trade_adjusted_df = macro_germany_trade_adjusted()
print(macro_germany_trade_adjusted_df)
macro_germany_gdp_df = macro_germany_gdp()
print(macro_germany_gdp_df)
macro_germany_retail_sale_monthly_df = macro_germany_retail_sale_monthly()
print(macro_germany_retail_sale_monthly_df)
macro_germany_retail_sale_yearly_df = macro_germany_retail_sale_yearly()
print(macro_germany_retail_sale_yearly_df)
macro_germany_zew_df = macro_germany_zew()
print(macro_germany_zew_df)
@@ -0,0 +1,100 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/5/15 18:20
Desc: 华尔街见闻-日历-宏观
https://wallstreetcn.com/calendar
"""
from datetime import datetime, timedelta
import numpy as np
import pandas as pd
import requests
def __convert_date_format(date: str) -> str:
"""
将日期字符串从格式'%Y%m%d'转换为格式'%Y-%m-%d %H:%M:%S'
:param date: 日期字符串,格式为'%Y%m%d'
:return: 转换后的日期字符串,格式为'%Y-%m-%d %H:%M:%S'
"""
datetime_obj = datetime.strptime(date, "%Y%m%d")
return datetime_obj.strftime("%Y-%m-%d %H:%M:%S")
def __format_date(date: str) -> int:
"""
将日期字符串转换为Unix时间戳
:param date: 日期字符串,格式为'%Y-%m-%d %H:%M:%S'
:return: Unix时间戳
"""
datetime_obj = datetime.strptime(date, "%Y-%m-%d %H:%M:%S")
return int(datetime_obj.timestamp())
def macro_info_ws(date: str = "20240514") -> pd.DataFrame:
"""
华尔街见闻-日历-宏观
https://wallstreetcn.com/calendar
:param date: 日期
:type date: str
:return: 日历-宏观
:rtype: pandas.DataFrame
"""
date = __convert_date_format(date)
url = "https://api-one-wscn.awtmt.com/apiv1/finance/macrodatas"
datetime_obj = datetime.strptime(date, "%Y-%m-%d %H:%M:%S")
one_day = timedelta(days=1)
new_datetime = datetime_obj + one_day
date_str = new_datetime.strftime("%Y-%m-%d %H:%M:%S")
params = {"start": __format_date(date), "end": __format_date(date_str)}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["items"])
temp_df["public_date"] = pd.to_datetime(
temp_df["public_date"], errors="coerce", unit="s", utc=True
).dt.tz_convert("Asia/Shanghai")
temp_df["public_date"] = temp_df["public_date"].dt.strftime("%Y-%m-%d %H:%M:%S")
temp_df = temp_df.rename(
columns={
"public_date": "时间",
"country": "地区",
"title": "事件",
"importance": "重要性",
"actual": "今值",
"forecast": "预期",
"previous": "前值",
"revised": "修正",
"uri": "链接",
}
)
temp_df = temp_df[
[
"时间",
"地区",
"事件",
"重要性",
"今值",
"预期",
"前值",
"修正",
"链接",
]
]
temp_df["今值"] = pd.to_numeric(temp_df["今值"], errors="coerce")
temp_df["预期"] = pd.to_numeric(temp_df["预期"], errors="coerce")
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["修正"] = pd.to_numeric(temp_df["修正"], errors="coerce")
temp_df["前值"] = np.where(
temp_df["修正"].notnull(), temp_df["修正"], temp_df["前值"]
)
del temp_df["修正"]
return temp_df
if __name__ == "__main__":
macro_info_ws_df = macro_info_ws(date="20240514")
print(macro_info_ws_df)
@@ -0,0 +1,143 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/3 16:00
Desc: 东方财富-经济数据-日本
https://data.eastmoney.com/cjsj/foreign_3_0.html
"""
import pandas as pd
import requests
def macro_japan_core(symbol: str = "EMG00341602") -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-宏观经济-日本-核心代码
https://data.eastmoney.com/cjsj/foreign_1_0.html
:param symbol: 代码
:type symbol: str
:return: 指定 symbol 的数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_JPAN",
"columns": "ALL",
"filter": f'(INDICATOR_ID="{symbol}")',
"pageNumber": "1",
"pageSize": "5000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.rename(
columns={
"COUNTRY": "-",
"INDICATOR_ID": "-",
"INDICATOR_NAME": "-",
"REPORT_DATE_CH": "时间",
"REPORT_DATE": "-",
"PUBLISH_DATE": "发布日期",
"VALUE": "现值",
"PRE_VALUE": "前值",
"INDICATOR_IDOLD": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"], errors="coerce")
temp_df["现值"] = pd.to_numeric(temp_df["现值"], errors="coerce")
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"], errors="coerce").dt.date
temp_df.sort_values(["发布日期"], inplace=True, ignore_index=True)
return temp_df
# 央行公布利率决议
def macro_japan_bank_rate() -> pd.DataFrame:
"""
东方财富-经济数据-日本-央行公布利率决议
https://data.eastmoney.com/cjsj/foreign_3_0.html
:return: 央行公布利率决议
:rtype: pandas.DataFrame
"""
temp_df = macro_japan_core(symbol="EMG00342252")
return temp_df
# 全国消费者物价指数年率
def macro_japan_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-日本-全国消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_3_1.html
:return: 全国消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_japan_core(symbol="EMG00005004")
return temp_df
# 全国核心消费者物价指数年率
def macro_japan_core_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-日本-全国核心消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_2_2.html
:return: 全国核心消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_japan_core(symbol="EMG00158099")
return temp_df
# 失业率
def macro_japan_unemployment_rate() -> pd.DataFrame:
"""
东方财富-经济数据-日本-失业率
https://data.eastmoney.com/cjsj/foreign_2_3.html
:return: 失业率
:rtype: pandas.DataFrame
"""
temp_df = macro_japan_core(symbol="EMG00005047")
return temp_df
# 领先指标终值
def macro_japan_head_indicator() -> pd.DataFrame:
"""
东方财富-经济数据-日本-领先指标终值
https://data.eastmoney.com/cjsj/foreign_3_4.html
:return: 领先指标终值
:rtype: pandas.DataFrame
"""
temp_df = macro_japan_core(symbol="EMG00005117")
return temp_df
if __name__ == "__main__":
macro_japan_bank_rate_df = macro_japan_bank_rate()
print(macro_japan_bank_rate_df)
macro_japan_cpi_yearly_df = macro_japan_cpi_yearly()
print(macro_japan_cpi_yearly_df)
macro_japan_core_cpi_yearly_df = macro_japan_core_cpi_yearly()
print(macro_japan_core_cpi_yearly_df)
macro_japan_unemployment_rate_df = macro_japan_unemployment_rate()
print(macro_japan_unemployment_rate_df)
macro_japan_head_indicator_df = macro_japan_head_indicator()
print(macro_japan_head_indicator_df)
@@ -0,0 +1,112 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/3 16:36
Desc: 金十数据-其他-加密货币实时行情
"""
from datetime import datetime
import pandas as pd
import requests
def crypto_js_spot() -> pd.DataFrame:
"""
主流加密货币的实时行情数据, 一次请求返回具体某一时刻行情数据
https://datacenter.jin10.com/reportType/dc_bitcoin_current
:return: pandas.DataFrame
"""
url = "https://datacenter-api.jin10.com/crypto_currency/list"
headers = {
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/107.0.0.0 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "x-csrf-token",
"x-version": "1.0.0",
}
r = requests.get(url, headers=headers)
data_json = r.json()
data_df = pd.DataFrame(data_json["data"])
data_df["reported_at"] = pd.to_datetime(data_df["reported_at"])
data_df.columns = [
"市场",
"交易品种",
"最近报价",
"涨跌额",
"涨跌幅",
"24小时最高",
"24小时最低",
"24小时成交量",
"更新时间",
]
data_df["最近报价"] = pd.to_numeric(data_df["最近报价"], errors="coerce")
data_df["涨跌额"] = pd.to_numeric(data_df["涨跌额"], errors="coerce")
data_df["涨跌幅"] = pd.to_numeric(data_df["涨跌幅"], errors="coerce")
data_df["24小时最高"] = pd.to_numeric(data_df["24小时最高"], errors="coerce")
data_df["24小时最低"] = pd.to_numeric(data_df["24小时最低"], errors="coerce")
data_df["24小时成交量"] = pd.to_numeric(data_df["24小时成交量"], errors="coerce")
data_df["更新时间"] = data_df["更新时间"].astype(str)
return data_df
def macro_fx_sentiment(
start_date: str = "20221011", end_date: str = "20221017"
) -> pd.DataFrame:
"""
金十数据-外汇-投机情绪报告
外汇投机情绪报告显示当前市场多空仓位比例数据由8家交易平台提供涵盖11个主要货币对和1个黄金品种
报告内容: 品种: 澳元兑日元澳元兑美元欧元兑美元欧元兑澳元欧元兑日元英镑兑美元英镑兑日元纽元兑美元美元兑加元美元兑瑞郎美元兑日元以及现货黄金兑美元
数据: 由Shark - fx整合全球8家交易平台 包括 Oanda FXCM Insta Dukas MyFxBook以及FiboGroup 的多空投机仓位数据而成
名词释义: 外汇投机情绪报告显示当前市场多空仓位比例数据由8家交易平台提供涵盖11个主要货币对和1个黄金品种
工具使用策略: Shark-fx声明表示基于主流通常都是错误的的事实当空头头寸超过60%交易者就应该建立多头仓位 同理当市场多头头寸超过60%交易者则应该建立空头仓位此外当多空仓位比例接近50%的情况下我们则倾向于建议交易者不要进场保持观望
https://datacenter.jin10.com/reportType/dc_ssi_trends
:param start_date: 具体交易日
:type start_date: str
:param end_date: 具体交易日, end_date 相同
:type end_date: str
:return: 投机情绪报告
:rtype: pandas.DataFrame
"""
start_date = "-".join([start_date[:4], start_date[4:6], start_date[6:]])
end_date = "-".join([end_date[:4], end_date[4:6], end_date[6:]])
url = "https://datacenter-api.jin10.com/sentiment/datas"
params = {
"start_date": start_date,
"end_date": end_date,
"currency_pair": "",
}
headers = {
"accept": "*/*",
"accept-encoding": "",
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8",
"cache-control": "no-cache",
"origin": "https://datacenter.jin10.com",
"pragma": "no-cache",
"referer": "https://datacenter.jin10.com/reportType/dc_ssi_trends",
"sec-fetch-mode": "cors",
"sec-fetch-site": "same-site",
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/79.0.3945.130 Safari/537.36",
"x-app-id": "rU6QIu7JHe2gOUeR",
"x-csrf-token": "",
"x-version": "1.0.0",
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["data"]["values"]).T
temp_df.reset_index(inplace=True)
temp_df.rename(columns={"index": "date"}, inplace=True)
for col in temp_df.columns[1:]:
temp_df[col] = pd.to_numeric(temp_df[col], errors="coerce")
return temp_df
if __name__ == "__main__":
crypto_js_spot_df = crypto_js_spot()
print(crypto_js_spot_df)
test_date = datetime.now().date().isoformat().replace("-", "")
macro_fx_sentiment_df = macro_fx_sentiment(start_date=test_date, end_date=test_date)
print(macro_fx_sentiment_df)
@@ -0,0 +1,158 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/11/8 10:00
Desc: 东方财富-经济数据-瑞士
http://data.eastmoney.com/cjsj/foreign_2_0.html
"""
import pandas as pd
import requests
def macro_swiss_core(symbol: str = "EMG00341602") -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-宏观经济-瑞士-核心代码
https://data.eastmoney.com/cjsj/foreign_1_0.html
:param symbol: 代码
:type symbol: str
:return: 指定 symbol 的数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_CH",
"columns": "ALL",
"filter": f'(INDICATOR_ID="{symbol}")',
"pageNumber": "1",
"pageSize": "5000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.rename(
columns={
"COUNTRY": "-",
"INDICATOR_ID": "-",
"INDICATOR_NAME": "-",
"REPORT_DATE_CH": "时间",
"REPORT_DATE": "-",
"PUBLISH_DATE": "发布日期",
"VALUE": "现值",
"PRE_VALUE": "前值",
"INDICATOR_IDOLD": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"])
temp_df["现值"] = pd.to_numeric(temp_df["现值"])
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
temp_df.sort_values(["发布日期"], inplace=True, ignore_index=True)
return temp_df
# SVME采购经理人指数
def macro_swiss_svme():
"""
东方财富-经济数据-瑞士-SVME采购经理人指数
http://data.eastmoney.com/cjsj/foreign_2_0.html
:return: SVME采购经理人指数
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341602")
return temp_df
# 贸易帐
def macro_swiss_trade():
"""
东方财富-经济数据-瑞士-贸易帐
http://data.eastmoney.com/cjsj/foreign_2_1.html
:return: 贸易帐
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341603")
return temp_df
# 消费者物价指数年率
def macro_swiss_cpi_yearly():
"""
东方财富-经济数据-瑞士-消费者物价指数年率
http://data.eastmoney.com/cjsj/foreign_2_2.html
:return: 消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341604")
return temp_df
# GDP季率
def macro_swiss_gdp_quarterly():
"""
东方财富-经济数据-瑞士-GDP季率
http://data.eastmoney.com/cjsj/foreign_2_3.html
:return: GDP季率
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341600")
return temp_df
# GDP年率
def macro_swiss_gbd_yearly():
"""
东方财富-经济数据-瑞士-GDP 年率
http://data.eastmoney.com/cjsj/foreign_2_4.html
:return: GDP年率
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341601")
return temp_df
# 央行公布利率决议
def macro_swiss_gbd_bank_rate():
"""
东方财富-经济数据-瑞士-央行公布利率决议
http://data.eastmoney.com/cjsj/foreign_2_5.html
:return: 央行公布利率决议
:rtype: pandas.DataFrame
"""
temp_df = macro_swiss_core(symbol="EMG00341606")
return temp_df
if __name__ == "__main__":
macro_swiss_svme_df = macro_swiss_svme()
print(macro_swiss_svme_df)
macro_swiss_trade_df = macro_swiss_trade()
print(macro_swiss_trade_df)
macro_swiss_cpi_yearly_df = macro_swiss_cpi_yearly()
print(macro_swiss_cpi_yearly_df)
macro_swiss_gdp_quarterly_df = macro_swiss_gdp_quarterly()
print(macro_swiss_gdp_quarterly_df)
macro_swiss_gbd_yearly_df = macro_swiss_gbd_yearly()
print(macro_swiss_gbd_yearly_df)
macro_swiss_gbd_bank_rate_df = macro_swiss_gbd_bank_rate()
print(macro_swiss_gbd_bank_rate_df)
@@ -0,0 +1,293 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/11/12 17:14
Desc: 东方财富-经济数据-英国
https://data.eastmoney.com/cjsj/foreign_4_0.html
"""
import pandas as pd
import requests
def macro_uk_core(symbol: str = "EMG00010348") -> pd.DataFrame:
"""
东方财富-数据中心-经济数据一览-宏观经济-英国-核心代码
https://data.eastmoney.com/cjsj/foreign_4_0.html
:param symbol: 代码
:type symbol: str
:return: 指定 symbol 的数据
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPT_ECONOMICVALUE_BRITAIN",
"columns": "ALL",
"filter": f'(INDICATOR_ID="{symbol}")',
"pageNumber": "1",
"pageSize": "5000",
"sortColumns": "REPORT_DATE",
"sortTypes": "-1",
"source": "WEB",
"client": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.rename(
columns={
"COUNTRY": "-",
"INDICATOR_ID": "-",
"INDICATOR_NAME": "-",
"REPORT_DATE_CH": "时间",
"REPORT_DATE": "-",
"PUBLISH_DATE": "发布日期",
"VALUE": "现值",
"PRE_VALUE": "前值",
"INDICATOR_IDOLD": "-",
},
inplace=True,
)
temp_df = temp_df[
[
"时间",
"前值",
"现值",
"发布日期",
]
]
temp_df["前值"] = pd.to_numeric(temp_df["前值"])
temp_df["现值"] = pd.to_numeric(temp_df["现值"])
temp_df["发布日期"] = pd.to_datetime(temp_df["发布日期"]).dt.date
temp_df.sort_values(["发布日期"], inplace=True, ignore_index=True)
return temp_df
# Halifax房价指数月率
def macro_uk_halifax_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-Halifax 房价指数月率
https://data.eastmoney.com/cjsj/foreign_4_0.html
:return: Halifax 房价指数月率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00342256")
return temp_df
# Halifax 房价指数年率
def macro_uk_halifax_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-Halifax 房价指数年率
https://data.eastmoney.com/cjsj/foreign_4_1.html
:return: Halifax房价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010370")
return temp_df
# 贸易帐
def macro_uk_trade() -> pd.DataFrame:
"""
东方财富-经济数据-英国-贸易帐
https://data.eastmoney.com/cjsj/foreign_4_2.html
:return: 贸易帐
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00158309")
return temp_df
# 央行公布利率决议
def macro_uk_bank_rate() -> pd.DataFrame:
"""
东方财富-经济数据-英国-央行公布利率决议
https://data.eastmoney.com/cjsj/foreign_4_3.html
:return: 央行公布利率决议
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00342253")
return temp_df
# 核心消费者物价指数年率
def macro_uk_core_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-核心消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_4_4.html
:return: 核心消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010279")
return temp_df
# 核心消费者物价指数月率
def macro_uk_core_cpi_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-核心消费者物价指数月率
https://data.eastmoney.com/cjsj/foreign_4_5.html
:return: 核心消费者物价指数月率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010291")
return temp_df
# 消费者物价指数年率
def macro_uk_cpi_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-消费者物价指数年率
https://data.eastmoney.com/cjsj/foreign_4_6.html
:return: 消费者物价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010267")
return temp_df
# 消费者物价指数月率
def macro_uk_cpi_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-消费者物价指数月率
https://data.eastmoney.com/cjsj/foreign_4_7.html
:return: 消费者物价指数月率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010291")
return temp_df
# 零售销售月率
def macro_uk_retail_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-零售销售月率
https://data.eastmoney.com/cjsj/foreign_4_8.html
:return: 零售销售月率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00158298")
return temp_df
# 零售销售年率
def macro_uk_retail_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-零售销售年率
https://data.eastmoney.com/cjsj/foreign_4_9.html
:return: 零售销售年率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00158297")
return temp_df
# Rightmove 房价指数年率
def macro_uk_rightmove_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-Rightmove 房价指数年率
https://data.eastmoney.com/cjsj/foreign_4_10.html
:return: Rightmove 房价指数年率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00341608")
return temp_df
# Rightmove 房价指数月率
def macro_uk_rightmove_monthly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-Rightmove 房价指数月率
https://data.eastmoney.com/cjsj/foreign_4_11.html
:return: Rightmove 房价指数月率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00341607")
return temp_df
# GDP 季率初值
def macro_uk_gdp_quarterly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-GDP 季率初值
https://data.eastmoney.com/cjsj/foreign_4_12.html
:return: GDP 季率初值
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00158277")
return temp_df
# GDP 年率初值
def macro_uk_gdp_yearly() -> pd.DataFrame:
"""
东方财富-经济数据-英国-GDP 年率初值
https://data.eastmoney.com/cjsj/foreign_4_13.html
:return: GDP 年率初值
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00158276")
return temp_df
# 失业率
def macro_uk_unemployment_rate() -> pd.DataFrame:
"""
东方财富-经济数据-英国-失业率
https://data.eastmoney.com/cjsj/foreign_4_14.html
:return: 失业率
:rtype: pandas.DataFrame
"""
temp_df = macro_uk_core(symbol="EMG00010348")
return temp_df
if __name__ == "__main__":
macro_uk_halifax_monthly_df = macro_uk_halifax_monthly()
print(macro_uk_halifax_monthly_df)
macro_uk_halifax_yearly_df = macro_uk_halifax_yearly()
print(macro_uk_halifax_yearly_df)
macro_uk_trade_df = macro_uk_trade()
print(macro_uk_trade_df)
macro_uk_bank_rate_df = macro_uk_bank_rate()
print(macro_uk_bank_rate_df)
macro_uk_core_cpi_yearly_df = macro_uk_core_cpi_yearly()
print(macro_uk_core_cpi_yearly_df)
macro_uk_core_cpi_monthly_df = macro_uk_core_cpi_monthly()
print(macro_uk_core_cpi_monthly_df)
macro_uk_cpi_yearly_df = macro_uk_cpi_yearly()
print(macro_uk_cpi_yearly_df)
macro_uk_cpi_monthly_df = macro_uk_cpi_monthly()
print(macro_uk_cpi_monthly_df)
macro_uk_retail_monthly_df = macro_uk_retail_monthly()
print(macro_uk_retail_monthly_df)
macro_uk_retail_yearly_df = macro_uk_retail_yearly()
print(macro_uk_retail_yearly_df)
macro_uk_rightmove_yearly_df = macro_uk_rightmove_yearly()
print(macro_uk_rightmove_yearly_df)
macro_uk_rightmove_monthly_df = macro_uk_rightmove_monthly()
print(macro_uk_rightmove_monthly_df)
macro_uk_gdp_quarterly_df = macro_uk_gdp_quarterly()
print(macro_uk_gdp_quarterly_df)
macro_uk_gdp_yearly_df = macro_uk_gdp_yearly()
print(macro_uk_gdp_yearly_df)
macro_uk_unemployment_rate_df = macro_uk_unemployment_rate()
print(macro_uk_unemployment_rate_df)
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,73 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/8/14 11:10
Desc: 国家金融与发展实验室-中国宏观杠杆率数据
http://114.115.232.154:8080/
"""
import pandas as pd
def macro_cnbs() -> pd.DataFrame:
"""
国家金融与发展实验室-中国宏观杠杆率数据
http://114.115.232.154:8080/
:return: 中国宏观杠杆率数据
:rtype: pandas.DataFrame
"""
url = "http://114.115.232.154:8080/handler/download.ashx"
temp_df = pd.read_excel(
url, sheet_name="Data", header=0, skiprows=1, engine="openpyxl"
)
temp_df["Period"] = pd.to_datetime(temp_df["Period"]).dt.strftime("%Y-%m")
temp_df.dropna(axis=1, inplace=True)
temp_df.rename(
columns={
"Period": "年份",
"Household": "居民部门",
"Non-financial corporations": "非金融企业部门",
"Central government ": "中央政府",
"Local government": "地方政府",
"General government": "政府部门",
"Non financial sector": "实体经济部门",
"Financial sector(asset side)": "金融部门资产方",
"Financial sector(liability side)": "金融部门负债方",
},
inplace=True,
)
column_order = [
"年份",
"居民部门",
"非金融企业部门",
"政府部门",
"中央政府",
"地方政府",
"实体经济部门",
"金融部门资产方",
"金融部门负债方",
]
temp_df = temp_df.reindex(columns=column_order)
temp_df["居民部门"] = pd.to_numeric(temp_df["居民部门"], errors="coerce")
temp_df["非金融企业部门"] = pd.to_numeric(
temp_df["非金融企业部门"], errors="coerce"
)
temp_df["政府部门"] = pd.to_numeric(temp_df["政府部门"], errors="coerce")
temp_df["中央政府"] = pd.to_numeric(temp_df["中央政府"], errors="coerce")
temp_df["地方政府"] = pd.to_numeric(temp_df["地方政府"], errors="coerce")
temp_df["实体经济部门"] = pd.to_numeric(temp_df["实体经济部门"], errors="coerce")
temp_df["金融部门资产方"] = pd.to_numeric(
temp_df["金融部门资产方"], errors="coerce"
)
temp_df["金融部门负债方"] = pd.to_numeric(
temp_df["金融部门负债方"], errors="coerce"
)
return temp_df
if __name__ == "__main__":
macro_cnbs_df = macro_cnbs()
print(macro_cnbs_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/12/17 16:54
Desc:
"""
@@ -0,0 +1,306 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/6/25 15:00
Desc: 碳排放交易
北京市碳排放权电子交易平台-北京市碳排放权公开交易行情
https://www.bjets.com.cn/article/jyxx/
深圳碳排放交易所-国内碳情
http://www.cerx.cn/dailynewsCN/index.htm
深圳碳排放交易所-国际碳情
http://www.cerx.cn/dailynewsOuter/index.htm
湖北碳排放权交易中心-现货交易数据-配额-每日概况
http://www.cerx.cn/dailynewsOuter/index.htm
广州碳排放权交易中心-行情信息
http://www.cnemission.com/article/hqxx/
"""
from io import StringIO
import pandas as pd
import requests
from bs4 import BeautifulSoup
from tqdm import tqdm
from akshare.utils import demjson
from akshare.utils.cons import headers
def energy_carbon_domestic(symbol: str = "湖北") -> pd.DataFrame:
"""
碳交易网-行情信息
http://www.tanjiaoyi.com/
:param symbol: choice of {'湖北', '上海', '北京', '重庆', '广东', '天津', '深圳', '福建'}
:type symbol: str
:return: 行情信息
:rtype: pandas.DataFrame
"""
url = "http://k.tanjiaoyi.com:8080/KDataController/getHouseDatasInAverage.do"
params = {
"lcnK": "53f75bfcefff58e4046ccfa42171636c",
"brand": "TAN",
}
r = requests.get(url, params=params)
data_text = r.text
data_json = demjson.decode(data_text[data_text.find("(") + 1 : -1])
temp_df = pd.DataFrame(data_json[symbol])
temp_df.columns = [
"成交价",
"_",
"成交量",
"地点",
"成交额",
"日期",
"_",
]
temp_df = temp_df[
[
"日期",
"成交价",
"成交量",
"成交额",
"地点",
]
]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["成交价"] = pd.to_numeric(temp_df["成交价"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
return temp_df
def energy_carbon_bj() -> pd.DataFrame:
"""
北京市碳排放权电子交易平台-北京市碳排放权公开交易行情
https://www.bjets.com.cn/article/jyxx/
:return: 北京市碳排放权公开交易行情
:rtype: pandas.DataFrame
"""
url = "https://www.bjets.com.cn/article/jyxx/"
r = requests.get(url, verify=False, headers=headers)
soup = BeautifulSoup(r.text, features="lxml")
total_page = (
soup.find("table")
.find("script")
.string.split("=")[-1]
.strip()
.strip(";")
.strip('"')
)
temp_df = pd.DataFrame()
for i in tqdm(
range(1, int(total_page) + 1),
desc="Please wait for a moment",
leave=False,
):
if i == 1:
i = ""
url = f"https://www.bjets.com.cn/article/jyxx/?{i}"
r = requests.get(url, verify=False, headers=headers)
r.encoding = "utf-8"
df = pd.read_html(StringIO(r.text))[0]
temp_df = pd.concat(objs=[temp_df, df], ignore_index=True)
temp_df.columns = ["日期", "成交量", "成交均价", "成交额"]
temp_df["成交单位"] = (
temp_df["成交额"]
.str.split("(", expand=True)
.iloc[:, 1]
.str.split("", expand=True)
.iloc[:, 0]
.str.split(")", expand=True)
.iloc[:, 0]
)
temp_df["成交额"] = (
temp_df["成交额"]
.str.split("(", expand=True)
.iloc[:, 0]
.str.split("", expand=True)
.iloc[:, 0]
)
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交均价"] = pd.to_numeric(temp_df["成交均价"], errors="coerce")
temp_df["成交额"] = temp_df["成交额"].str.replace(",", "")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df.sort_values(by="日期", inplace=True)
temp_df.reset_index(inplace=True, drop=True)
return temp_df
def energy_carbon_sz() -> pd.DataFrame:
"""
深圳碳排放交易所-国内碳情
http://www.cerx.cn/dailynewsCN/index.htm
:return: 国内碳情每日行情数据
:rtype: pandas.DataFrame
"""
url = "http://www.cerx.cn/dailynewsCN/index.htm"
r = requests.get(url, headers=headers)
soup = BeautifulSoup(r.text, features="lxml")
page_num = int(soup.find(attrs={"class": "pagebar"}).find_all("option")[-1].text)
big_df = pd.read_html(StringIO(r.text), header=0)[0]
for page in tqdm(
range(2, page_num + 1), desc="Please wait for a moment", leave=False
):
url = f"http://www.cerx.cn/dailynewsCN/index_{page}.htm"
r = requests.get(url, headers=headers)
temp_df = pd.read_html(StringIO(r.text), header=0)[0]
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df["交易日期"] = pd.to_datetime(big_df["交易日期"], errors="coerce").dt.date
big_df["开盘价"] = pd.to_numeric(big_df["开盘价"], errors="coerce")
big_df["最高价"] = pd.to_numeric(big_df["最高价"], errors="coerce")
big_df["最低价"] = pd.to_numeric(big_df["最低价"], errors="coerce")
big_df["成交均价"] = pd.to_numeric(big_df["成交均价"], errors="coerce")
big_df["收盘价"] = pd.to_numeric(big_df["收盘价"], errors="coerce")
big_df["成交量"] = pd.to_numeric(big_df["成交量"], errors="coerce")
big_df["成交额"] = pd.to_numeric(big_df["成交额"], errors="coerce")
big_df.sort_values(by="交易日期", inplace=True)
big_df.reset_index(inplace=True, drop=True)
return big_df
def energy_carbon_eu() -> pd.DataFrame:
"""
深圳碳排放交易所-国际碳情
http://www.cerx.cn/dailynewsOuter/index.htm
:return: 国际碳情每日行情数据
:rtype: pandas.DataFrame
"""
url = "http://www.cerx.cn/dailynewsOuter/index.htm"
r = requests.get(url, headers=headers)
soup = BeautifulSoup(r.text, features="lxml")
page_num = int(soup.find(attrs={"class": "pagebar"}).find_all("option")[-1].text)
big_df = pd.read_html(StringIO(r.text), header=0)[0]
for page in tqdm(
range(2, page_num + 1), desc="Please wait for a moment", leave=False
):
url = f"http://www.cerx.cn/dailynewsOuter/index_{page}.htm"
r = requests.get(url)
temp_df = pd.read_html(StringIO(r.text), header=0)[0]
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df["交易日期"] = pd.to_datetime(big_df["交易日期"], errors="coerce").dt.date
big_df["开盘价"] = pd.to_numeric(big_df["开盘价"], errors="coerce")
big_df["最高价"] = pd.to_numeric(big_df["最高价"], errors="coerce")
big_df["最低价"] = pd.to_numeric(big_df["最低价"], errors="coerce")
big_df["成交均价"] = pd.to_numeric(big_df["成交均价"], errors="coerce")
big_df["收盘价"] = pd.to_numeric(big_df["收盘价"], errors="coerce")
big_df["成交量"] = pd.to_numeric(big_df["成交量"], errors="coerce")
big_df["成交额"] = pd.to_numeric(big_df["成交额"], errors="coerce")
big_df.sort_values(by="交易日期", inplace=True)
big_df.reset_index(inplace=True, drop=True)
return big_df
def energy_carbon_hb() -> pd.DataFrame:
"""
湖北碳排放权交易中心-现货交易数据-配额-每日概况
http://www.hbets.cn/list/13.html?page=42
:return: 现货交易数据-配额-每日概况行情数据
:rtype: pandas.DataFrame
"""
url = "https://www.hbets.cn/"
r = requests.get(url, headers=headers)
soup = BeautifulSoup(r.text, features="lxml")
data_text = (
soup.find(name="div", attrs={"class": "threeLeft"}).find_all("script")[1].text
)
start_pos = data_text.find("cjj = '[") + 7 # 找到 JSON 数组开始的位置
end_pos = data_text.rfind("cjj =") - 31 # 找到 JSON 数组结束的位置
data_json = demjson.decode(data_text[start_pos:end_pos])
temp_df = pd.DataFrame.from_dict(data_json)
temp_df.rename(
columns={
"riqi": "日期",
"cjj": "成交价",
"cjl": "成交量",
"zx": "最新",
"zd": "涨跌",
},
inplace=True,
)
temp_df = temp_df[
[
"日期",
"成交价",
"成交量",
"最新",
"涨跌",
]
]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["成交价"] = pd.to_numeric(temp_df["成交价"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["最新"] = pd.to_numeric(temp_df["最新"], errors="coerce")
temp_df["涨跌"] = pd.to_numeric(temp_df["涨跌"], errors="coerce")
return temp_df
def energy_carbon_gz() -> pd.DataFrame:
"""
广州碳排放权交易中心-行情信息
http://www.cnemission.com/article/hqxx/
:return: 行情信息数据
:rtype: pandas.DataFrame
"""
url = "http://ets.cnemission.com/carbon/portalIndex/markethistory"
params = {
"Top": "1",
"beginTime": "2010-01-01",
"endTime": "2030-09-12",
}
r = requests.get(url, params=params)
temp_df = pd.read_html(StringIO(r.text), header=0)[1]
temp_df.columns = [
"日期",
"品种",
"开盘价",
"收盘价",
"最高价",
"最低价",
"涨跌",
"涨跌幅",
"成交数量",
"成交金额",
]
temp_df["日期"] = pd.to_datetime(
temp_df["日期"], format="%Y%m%d", errors="coerce"
).dt.date
temp_df["开盘价"] = pd.to_numeric(temp_df["开盘价"], errors="coerce")
temp_df["收盘价"] = pd.to_numeric(temp_df["收盘价"], errors="coerce")
temp_df["最高价"] = pd.to_numeric(temp_df["最高价"], errors="coerce")
temp_df["最低价"] = pd.to_numeric(temp_df["最低价"], errors="coerce")
temp_df["涨跌"] = pd.to_numeric(temp_df["涨跌"], errors="coerce")
temp_df["涨跌幅"] = temp_df["涨跌幅"].str.strip("%")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["成交数量"] = pd.to_numeric(temp_df["成交数量"], errors="coerce")
temp_df["成交金额"] = pd.to_numeric(temp_df["成交金额"], errors="coerce")
temp_df.sort_values(by="日期", inplace=True)
temp_df.reset_index(inplace=True, drop=True)
return temp_df
if __name__ == "__main__":
energy_carbon_domestic_df = energy_carbon_domestic(symbol="湖北")
print(energy_carbon_domestic_df)
energy_carbon_domestic_df = energy_carbon_domestic(symbol="深圳")
print(energy_carbon_domestic_df)
energy_carbon_bj_df = energy_carbon_bj()
print(energy_carbon_bj_df)
energy_carbon_sz_df = energy_carbon_sz()
print(energy_carbon_sz_df)
energy_carbon_eu_df = energy_carbon_eu()
print(energy_carbon_eu_df)
energy_carbon_hb_df = energy_carbon_hb()
print(energy_carbon_hb_df)
energy_carbon_gz_df = energy_carbon_gz()
print(energy_carbon_gz_df)
@@ -0,0 +1,112 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/1/20 23:00
Desc: 东方财富-数据中心-中国油价
https://data.eastmoney.com/cjsj/oil_default.html
"""
import pandas as pd
import requests
def energy_oil_hist() -> pd.DataFrame:
"""
汽柴油历史调价信息
https://data.eastmoney.com/cjsj/oil_default.html
:return: 汽柴油历史调价信息
:rtype: pandas.DataFrame
"""
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPTA_WEB_YJ_BD",
"columns": "ALL",
"sortColumns": "dim_date",
"sortTypes": "-1",
"token": "894050c76af8597a853f5b408b759f5d",
"pageNumber": "1",
"pageSize": "1000",
"source": "WEB",
"p": "1",
"pageNo": "1",
"pageNum": "1",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"])
temp_df.columns = ["调整日期", "汽油价格", "柴油价格", "汽油涨跌", "柴油涨跌"]
temp_df["调整日期"] = pd.to_datetime(temp_df["调整日期"], errors="coerce").dt.date
temp_df["汽油价格"] = pd.to_numeric(temp_df["汽油价格"], errors="coerce")
temp_df["柴油价格"] = pd.to_numeric(temp_df["柴油价格"], errors="coerce")
temp_df["汽油涨跌"] = pd.to_numeric(temp_df["汽油涨跌"], errors="coerce")
temp_df["柴油涨跌"] = pd.to_numeric(temp_df["柴油涨跌"], errors="coerce")
temp_df.sort_values(by=["调整日期"], inplace=True)
temp_df.reset_index(inplace=True, drop=True)
return temp_df
def energy_oil_detail(date: str = "20220517") -> pd.DataFrame:
"""
全国各地区的汽油和柴油油价
https://data.eastmoney.com/cjsj/oil_default.html
:param date: 可以调用 ak.energy_oil_hist() 得到可以获取油价的调整时间
:type date: str
:return: oil price at specific date
:rtype: pandas.DataFrame
"""
date = "-".join([date[:4], date[4:6], date[6:]])
url = "https://datacenter-web.eastmoney.com/api/data/v1/get"
params = {
"reportName": "RPTA_WEB_YJ_JH",
"columns": "ALL",
"filter": f"(dim_date='{date}')",
"sortColumns": "cityname",
"sortTypes": "1",
"token": "894050c76af8597a853f5b408b759f5d",
"pageNumber": "1",
"pageSize": "1000",
"source": "WEB",
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"]["data"]).iloc[:, 1:]
temp_df.columns = [
"日期",
"地区",
"V_0",
"V_92",
"V_95",
"V_89",
"ZDE_0",
"ZDE_92",
"ZDE_95",
"ZDE_89",
"QE_0",
"QE_92",
"QE_95",
"QE_89",
"首字母",
]
del temp_df["首字母"]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["V_0"] = pd.to_numeric(temp_df["V_0"], errors="coerce")
temp_df["V_92"] = pd.to_numeric(temp_df["V_92"], errors="coerce")
temp_df["V_95"] = pd.to_numeric(temp_df["V_95"], errors="coerce")
temp_df["V_89"] = pd.to_numeric(temp_df["V_89"], errors="coerce")
temp_df["ZDE_0"] = pd.to_numeric(temp_df["ZDE_0"], errors="coerce")
temp_df["ZDE_92"] = pd.to_numeric(temp_df["ZDE_92"], errors="coerce")
temp_df["ZDE_95"] = pd.to_numeric(temp_df["ZDE_95"], errors="coerce")
temp_df["ZDE_89"] = pd.to_numeric(temp_df["ZDE_89"], errors="coerce")
temp_df["QE_0"] = pd.to_numeric(temp_df["QE_0"], errors="coerce")
temp_df["QE_92"] = pd.to_numeric(temp_df["QE_92"], errors="coerce")
temp_df["QE_95"] = pd.to_numeric(temp_df["QE_95"], errors="coerce")
temp_df["QE_89"] = pd.to_numeric(temp_df["QE_89"], errors="coerce")
return temp_df
if __name__ == "__main__":
energy_oil_hist_df = energy_oil_hist()
print(energy_oil_hist_df)
energy_oil_detail_df = energy_oil_detail(date="20240118")
print(energy_oil_detail_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2020/1/23 9:07
Desc:
"""
@@ -0,0 +1,435 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/9/24 15:22
Desc: 百度地图慧眼-迁徙城市代码映射
"""
province_dict = {
"820000": "澳门",
"810000": "香港",
"710000": "台湾省",
"650000": "新疆维吾尔自治区",
"640000": "宁夏回族自治区",
"630000": "青海省",
"620000": "甘肃省",
"610000": "陕西省",
"540000": "西藏自治区",
"530000": "云南省",
"520000": "贵州省",
"510000": "四川省",
"500000": "重庆市",
"460000": "海南省",
"450000": "广西壮族自治区",
"440000": "广东省",
"430000": "湖南省",
"420000": "湖北省",
"410000": "河南省",
"370000": "山东省",
"360000": "江西省",
"350000": "福建省",
"340000": "安徽省",
"330000": "浙江省",
"320000": "江苏省",
"310000": "上海市",
"230000": "黑龙江省",
"220000": "吉林省",
"210000": "辽宁省",
"150000": "内蒙古自治区",
"140000": "山西省",
"130000": "河北省",
"120000": "天津市",
"110000": "北京市",
}
city_dict = {
"520300": "遵义市",
"510300": "自贡市",
"370300": "淄博市",
"512000": "资阳市",
"411700": "驻马店市",
"430200": "株洲市",
"440400": "珠海市",
"411600": "周口市",
"330900": "舟山市",
"500100": "重庆市",
"500200": "重庆市",
"640500": "中卫市",
"442000": "中山市",
"410100": "郑州市",
"321100": "镇江市",
"441200": "肇庆市",
"530600": "昭通市",
"140400": "长治市",
"430100": "长沙市",
"220100": "长春市",
"350600": "漳州市",
"719007": "彰化县",
"620700": "张掖市",
"130700": "张家口市",
"430800": "张家界市",
"440800": "湛江市",
"370400": "枣庄市",
"140800": "运城市",
"719008": "云林县",
"445300": "云浮市",
"430600": "岳阳市",
"530400": "玉溪市",
"632700": "玉树藏族自治州",
"450900": "玉林市",
"610800": "榆林市",
"431100": "永州市",
"210800": "营口市",
"360600": "鹰潭市",
"640100": "银川市",
"430900": "益阳市",
"719005": "宜兰县",
"360900": "宜春市",
"420500": "宜昌市",
"511500": "宜宾市",
"654000": "伊犁哈萨克自治州",
"230700": "伊春市",
"140300": "阳泉市",
"441700": "阳江市",
"321000": "扬州市",
"320900": "盐城市",
"222400": "延边朝鲜族自治州",
"610600": "延安市",
"370600": "烟台市",
"511800": "雅安市",
"341800": "宣城市",
"411000": "许昌市",
"320300": "徐州市",
"341300": "宿州市",
"321300": "宿迁市",
"152200": "兴安盟",
"130500": "邢台市",
"411500": "信阳市",
"719004": "新竹县",
"719002": "新竹市",
"360500": "新余市",
"410700": "新乡市",
"710300": "新北市",
"140900": "忻州市",
"420900": "孝感市",
"420600": "襄阳市",
"433100": "湘西土家族苗族自治州",
"430300": "湘潭市",
"810000": "香港",
"610400": "咸阳市",
"421200": "咸宁市",
"429004": "仙桃市",
"152500": "锡林郭勒盟",
"532800": "西双版纳傣族自治州",
"630100": "西宁市",
"610100": "西安市",
"620600": "武威市",
"420100": "武汉市",
"469001": "五指山市",
"659004": "五家渠市",
"450400": "梧州市",
"640300": "吴忠市",
"340200": "芜湖市",
"320200": "无锡市",
"650100": "乌鲁木齐市",
"150900": "乌兰察布市",
"150300": "乌海市",
"532600": "文山壮族苗族自治州",
"469005": "文昌市",
"330300": "温州市",
"610500": "渭南市",
"370700": "潍坊市",
"371000": "威海市",
"469006": "万宁市",
"469022": "屯昌县",
"650400": "吐鲁番市",
"659003": "图木舒克市",
"520600": "铜仁市",
"340700": "铜陵市",
"610200": "铜川市",
"150500": "通辽市",
"220500": "通化市",
"659006": "铁门关市",
"211200": "铁岭市",
"620500": "天水市",
"429006": "天门市",
"120100": "天津市",
"710600": "桃园市",
"130200": "唐山市",
"321200": "泰州市",
"370900": "泰安市",
"140100": "太原市",
"331000": "台州市",
"710400": "台中市",
"710500": "台南市",
"719012": "台东县",
"710100": "台北市",
"654200": "塔城地区",
"510900": "遂宁市",
"421300": "随州市",
"231200": "绥化市",
"320500": "苏州市",
"220700": "松原市",
"220300": "四平市",
"140600": "朔州市",
"230500": "双鸭山市",
"659007": "双河市",
"640200": "石嘴山市",
"130100": "石家庄市",
"659001": "石河子市",
"420300": "十堰市",
"210100": "沈阳市",
"429021": "神农架林区",
"440300": "深圳市",
"330600": "绍兴市",
"430500": "邵阳市",
"440200": "韶关市",
"361100": "上饶市",
"310100": "上海市",
"411400": "商丘市",
"611000": "商洛市",
"441500": "汕尾市",
"440500": "汕头市",
"540500": "山南市",
"350200": "厦门市",
"460200": "三亚市",
"460300": "三沙市",
"350400": "三明市",
"411200": "三门峡市",
"371100": "日照市",
"540200": "日喀则市",
"350500": "泉州市",
"530300": "曲靖市",
"330800": "衢州市",
"469030": "琼中黎族苗族自治县",
"469002": "琼海市",
"621000": "庆阳市",
"441800": "清远市",
"370200": "青岛市",
"130300": "秦皇岛市",
"450700": "钦州市",
"522300": "黔西南布依族苗族自治州",
"522700": "黔南布依族苗族自治州",
"522600": "黔东南苗族侗族自治州",
"429005": "潜江市",
"230200": "齐齐哈尔市",
"230900": "七台河市",
"530800": "普洱市",
"410900": "濮阳市",
"350300": "莆田市",
"360300": "萍乡市",
"719011": "屏东县",
"620800": "平凉市",
"410400": "平顶山市",
"719014": "澎湖县",
"211100": "盘锦市",
"510400": "攀枝花市",
"533300": "怒江傈僳族自治州",
"350900": "宁德市",
"330200": "宁波市",
"511000": "内江市",
"411300": "南阳市",
"719009": "南投县",
"320600": "南通市",
"350700": "南平市",
"450100": "南宁市",
"320100": "南京市",
"511300": "南充市",
"360100": "南昌市",
"540600": "那曲市",
"231000": "牡丹江市",
"719006": "苗栗县",
"510700": "绵阳市",
"441400": "梅州市",
"511400": "眉山市",
"440900": "茂名市",
"340500": "马鞍山市",
"141100": "吕梁市",
"411100": "漯河市",
"410300": "洛阳市",
"510500": "泸州市",
"431300": "娄底市",
"621200": "陇南市",
"350800": "龙岩市",
"520200": "六盘水市",
"341500": "六安市",
"450200": "柳州市",
"469028": "陵水黎族自治县",
"371300": "临沂市",
"622900": "临夏回族自治州",
"469024": "临高县",
"141000": "临汾市",
"530900": "临沧市",
"540400": "林芝市",
"371500": "聊城市",
"220400": "辽源市",
"211000": "辽阳市",
"513400": "凉山彝族自治州",
"320700": "连云港市",
"331100": "丽水市",
"530700": "丽江市",
"511100": "乐山市",
"469027": "乐东黎族自治县",
"131000": "廊坊市",
"620100": "兰州市",
"451300": "来宾市",
"540100": "拉萨市",
"659009": "昆玉市",
"530100": "昆明市",
"653000": "克孜勒苏柯尔克孜自治州",
"650200": "克拉玛依市",
"659008": "可克达拉市",
"410200": "开封市",
"653100": "喀什地区",
"620900": "酒泉市",
"360400": "九江市",
"360200": "景德镇市",
"421000": "荆州市",
"420800": "荆门市",
"140700": "晋中市",
"140500": "晋城市",
"210700": "锦州市",
"330700": "金华市",
"620300": "金昌市",
"445200": "揭阳市",
"410800": "焦作市",
"440700": "江门市",
"620200": "嘉峪关市",
"719010": "嘉义县",
"719003": "嘉义市",
"330400": "嘉兴市",
"230800": "佳木斯市",
"419001": "济源市",
"370800": "济宁市",
"370100": "济南市",
"220200": "吉林市",
"360800": "吉安市",
"719001": "基隆市",
"230300": "鸡西市",
"441300": "惠州市",
"420200": "黄石市",
"341000": "黄山市",
"632300": "黄南藏族自治州",
"421100": "黄冈市",
"340400": "淮南市",
"340600": "淮北市",
"320800": "淮安市",
"431200": "怀化市",
"719013": "花莲县",
"330500": "湖州市",
"211400": "葫芦岛市",
"150700": "呼伦贝尔市",
"150100": "呼和浩特市",
"532500": "红河哈尼族彝族自治州",
"430400": "衡阳市",
"131100": "衡水市",
"231100": "黑河市",
"230400": "鹤岗市",
"410600": "鹤壁市",
"451100": "贺州市",
"371700": "菏泽市",
"441600": "河源市",
"451200": "河池市",
"653200": "和田地区",
"340100": "合肥市",
"330100": "杭州市",
"610700": "汉中市",
"130400": "邯郸市",
"632800": "海西蒙古族藏族自治州",
"632500": "海南藏族自治州",
"460100": "海口市",
"630200": "海东市",
"632200": "海北藏族自治州",
"650500": "哈密市",
"230100": "哈尔滨市",
"632600": "果洛藏族自治州",
"450300": "桂林市",
"520100": "贵阳市",
"450800": "贵港市",
"440100": "广州市",
"510800": "广元市",
"511600": "广安市",
"640400": "固原市",
"710200": "高雄市",
"360700": "赣州市",
"513300": "甘孜藏族自治州",
"623000": "甘南藏族自治州",
"341200": "阜阳市",
"210900": "阜新市",
"361000": "抚州市",
"210400": "抚顺市",
"350100": "福州市",
"440600": "佛山市",
"450600": "防城港市",
"422800": "恩施土家族苗族自治州",
"420700": "鄂州市",
"150600": "鄂尔多斯市",
"370500": "东营市",
"441900": "东莞市",
"469007": "东方市",
"621100": "定西市",
"469021": "定安县",
"533400": "迪庆藏族自治州",
"371400": "德州市",
"510600": "德阳市",
"533100": "德宏傣族景颇族自治州",
"460400": "儋州市",
"210600": "丹东市",
"232700": "大兴安岭地区",
"140200": "大同市",
"230600": "大庆市",
"210200": "大连市",
"532900": "大理白族自治州",
"511700": "达州市",
"532300": "楚雄彝族自治州",
"341100": "滁州市",
"451400": "崇左市",
"150400": "赤峰市",
"341700": "池州市",
"469023": "澄迈县",
"130800": "承德市",
"510100": "成都市",
"431000": "郴州市",
"445100": "潮州市",
"211300": "朝阳市",
"320400": "常州市",
"430700": "常德市",
"469026": "昌江黎族自治县",
"652300": "昌吉回族自治州",
"540300": "昌都市",
"130900": "沧州市",
"652700": "博尔塔拉蒙古自治州",
"341600": "亳州市",
"371600": "滨州市",
"520500": "毕节市",
"210500": "本溪市",
"659005": "北屯市",
"110100": "北京市",
"450500": "北海市",
"469029": "保亭黎族苗族自治县",
"530500": "保山市",
"130600": "保定市",
"610300": "宝鸡市",
"150200": "包头市",
"340300": "蚌埠市",
"451000": "百色市",
"620400": "白银市",
"220600": "白山市",
"469025": "白沙黎族自治县",
"220800": "白城市",
"511900": "巴中市",
"652800": "巴音郭楞蒙古自治州",
"150800": "巴彦淖尔市",
"820000": "澳门",
"210300": "鞍山市",
"410500": "安阳市",
"520400": "安顺市",
"340800": "安庆市",
"610900": "安康市",
"542500": "阿里地区",
"654300": "阿勒泰地区",
"152900": "阿拉善盟",
"659002": "阿拉尔市",
"652900": "阿克苏地区",
"513200": "阿坝藏族羌族自治州",
}
@@ -0,0 +1,104 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/5/12 22:30
Desc: 百度地图慧眼-百度迁徙数据
"""
import json
import pandas as pd
import requests
from akshare.event.cons import province_dict, city_dict
def migration_area_baidu(
area: str = "重庆市", indicator: str = "move_in", date: str = "20230922"
) -> pd.DataFrame:
"""
百度地图慧眼-百度迁徙-XXX迁入地详情
百度地图慧眼-百度迁徙-XXX迁出地详情
以上展示 top100 结果如不够 100 则展示全部
迁入来源地比例: xx 地迁入到当前区域的人数与当前区域迁入总人口的比值
迁出目的地比例: 从当前区域迁出到 xx 的人口与从当前区域迁出总人口的比值
https://qianxi.baidu.com/?from=shoubai#city=0
:param area: 可以输入 省份 或者 具体城市 但是需要用全称
:type area: str
:param indicator: move_in 迁入 move_out 迁出
:type indicator: str
:param date: 查询的日期 20200101 以后的时间
:type date: str
:return: 迁入地详情/迁出地详情的前 50
:rtype: pandas.DataFrame
"""
city_dict.update(province_dict)
inner_dict = dict(zip(city_dict.values(), city_dict.keys()))
if inner_dict[area] in province_dict.keys():
dt_flag = "province"
else:
dt_flag = "city"
url = "https://huiyan.baidu.com/migration/cityrank.jsonp"
params = {
"dt": dt_flag,
"id": inner_dict[area],
"type": indicator,
"date": date,
}
r = requests.get(url, params=params)
data_text = r.text[r.text.find("({") + 1 : r.text.rfind(");")]
data_json = json.loads(data_text)
temp_df = pd.DataFrame(data_json["data"]["list"])
temp_df["value"] = pd.to_numeric(temp_df["value"], errors="coerce")
return temp_df
def migration_scale_baidu(
area: str = "广州市",
indicator: str = "move_in",
) -> pd.DataFrame:
"""
百度地图慧眼-百度迁徙-迁徙规模
迁徙规模指数反映迁入或迁出人口规模城市间可横向对比城市迁徙边界采用该城市行政区划包含该城市管辖的区
https://qianxi.baidu.com/?from=shoubai#city=0
:param area: 可以输入 省份 或者 具体城市 但是需要用全称
:type area: str
:param indicator: move_in 迁入 move_out 迁出
:type indicator: str
:return: 时间序列的迁徙规模指数
:rtype: pandas.DataFrame
"""
city_dict.update(province_dict)
inner_dict = dict(zip(city_dict.values(), city_dict.keys()))
if inner_dict[area] in province_dict.keys():
dt_flag = "province"
else:
dt_flag = "city"
url = "https://huiyan.baidu.com/migration/historycurve.jsonp"
params = {
"dt": dt_flag,
"id": inner_dict[area],
"type": indicator,
}
r = requests.get(url, params=params)
json_data = json.loads(r.text[r.text.find("({") + 1 : r.text.rfind(");")])
temp_df = pd.DataFrame.from_dict(json_data["data"]["list"], orient="index")
temp_df.index = pd.to_datetime(temp_df.index)
temp_df.reset_index(inplace=True)
temp_df.columns = ["日期", "迁徙规模指数"]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["迁徙规模指数"] = pd.to_numeric(temp_df["迁徙规模指数"], errors="coerce")
return temp_df
if __name__ == "__main__":
migration_area_baidu_df = migration_area_baidu(
area="杭州市", indicator="move_out", date="20240401"
)
print(migration_area_baidu_df)
migration_scale_baidu_df = migration_scale_baidu(
area="广州市",
indicator="move_in",
)
print(migration_scale_baidu_df)
@@ -0,0 +1,43 @@
"""
AKShare 异常处理模块
"""
class AkshareException(Exception):
"""Base exception for akshare library"""
def __init__(self, message):
self.message = message
super().__init__(self.message)
class APIError(AkshareException):
"""Raised when API request fails"""
def __init__(self, message, status_code=None):
self.status_code = status_code
super().__init__(f"API Error: {message} (Status code: {status_code})")
class DataParsingError(AkshareException):
"""Raised when data parsing fails"""
pass
class InvalidParameterError(AkshareException):
"""Raised when an invalid parameter is provided"""
pass
class NetworkError(AkshareException):
"""Raised when network-related issues occur"""
pass
class RateLimitError(AkshareException):
"""Raised when API rate limit is exceeded"""
pass
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/9/30 13:58
Desc:
"""
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,192 @@
symbol_market_map = {
"EURCNYC": 120,
"JPYZAR": 119,
"NZDCNYC": 120,
"CNYRUBC": 120,
"AUDCNYC": 120,
"JPYGBP": 119,
"JPYSGD": 119,
"JPYCNH": 133,
"JPYAUD": 119,
"USDBRL": 119,
"JPYEUR": 119,
"JPYTRY": 119,
"JPYCAD": 119,
"CHFZAR": 119,
"JPYHKD": 119,
"SEKEUR": 119,
"JPYUSD": 119,
"GBPCNYC": 120,
"JPYNZD": 119,
"CHFGBP": 119,
"USDIDR": 119,
"CHFSGD": 119,
"USDPLN": 119,
"CHFCNH": 133,
"SEKUSD": 119,
"CHFAUD": 119,
"USDKRW": 119,
"EURPLN": 119,
"USDHUF": 119,
"CHFCAD": 119,
"USDTHB": 119,
"CHFEUR": 119,
"JPYCNYC": 120,
"EURHUF": 119,
"CHFHKD": 119,
"SGDCNYC": 120,
"CHFUSD": 119,
"USDINR": 119,
"USDCZK": 119,
"CHFNZD": 119,
"USDMXN": 119,
"GBPPLN": 119,
"USDZAR": 119,
"JPYCHF": 119,
"EURCZK": 119,
"EURZAR": 119,
"CADCNYC": 120,
"NOKEUR": 119,
"NZDGBP": 119,
"NOKUSD": 119,
"NZDSGD": 119,
"USDGBP": 119,
"HKDGBP": 119,
"NZDCNH": 133,
"NZDAUD": 119,
"HKDSGD": 119,
"CNYSARC": 120,
"USDSGD": 119,
"CNYAEDC": 120,
"EURGBP": 119,
"CADGBP": 119,
"USDCNH": 133,
"CNYTRYC": 120,
"CADSGD": 119,
"USDAUD": 119,
"GBPZAR": 119,
"EURSGD": 119,
"HKDCNH": 133,
"NZDCAD": 119,
"CADCNH": 133,
"HKDAUD": 119,
"NZDEUR": 119,
"EURCNH": 133,
"EURAUD": 119,
"NZDHKD": 119,
"CADAUD": 119,
"AUDGBP": 119,
"USDDKK": 119,
"HKDCAD": 119,
"USDCAD": 119,
"AUDSGD": 119,
"USDTRY": 119,
"EURTRY": 119,
"USDEUR": 119,
"NZDUSD": 119,
"SGDGBP": 119,
"USDHKD": 119,
"AUDCNH": 133,
"EURDKK": 119,
"USDARS": 119,
"USDSAR": 119,
"TRYUSD": 119,
"TRYEUR": 119,
"SARUSD": 119,
"INRUSD": 119,
"HUFUSD": 119,
"HUFEUR": 119,
"HKDUSD": 119,
"HKDEUR": 119,
"HKDCNYC": 120,
"EURCAD": 119,
"DKKUSD": 119,
"DKKEUR": 119,
"CNYMOPC": 120,
"CNHSGD": 133,
"CNHGBP": 133,
"CNHAUD": 133,
"CADEUR": 119,
"SGDCNH": 133,
"EURHKD": 119,
"CADHKD": 119,
"USDCNYC": 120,
"GBPSGD": 119,
"EURUSD": 119,
"SGDAUD": 119,
"HKDNZD": 119,
"USDNZD": 119,
"GBPCNH": 133,
"CADUSD": 119,
"AUDCAD": 119,
"CNYTHBC": 120,
"CNHEUR": 133,
"GBPAUD": 119,
"AUDEUR": 119,
"CADNZD": 119,
"EURNZD": 119,
"CNHCAD": 133,
"AUDHKD": 119,
"SGDCAD": 119,
"AUDUSD": 119,
"SGDEUR": 119,
"CNHHKD": 133,
"GBPCAD": 119,
"CNHUSD": 133,
"SGDHKD": 119,
"GBPEUR": 119,
"SGDUSD": 119,
"AUDNZD": 119,
"GBPHKD": 119,
"GBPUSD": 119,
"CNHNZD": 133,
"CHFCNYC": 120,
"SGDNZD": 119,
"ZARGBP": 119,
"USDNOK": 119,
"GBPNZD": 119,
"CZKEUR": 119,
"EURNOK": 119,
"CHFJPY": 119,
"NZDCHF": 119,
"PLNGBP": 119,
"HKDCHF": 119,
"ZARUSD": 119,
"USDCHF": 119,
"ZAREUR": 119,
"MXNUSD": 119,
"EURCHF": 119,
"CADCHF": 119,
"CZKUSD": 119,
"CNYKRWC": 120,
"CNHCHF": 133,
"AUDCHF": 119,
"PLNEUR": 119,
"CNYMXNC": 120,
"SGDCHF": 119,
"PLNUSD": 119,
"USDSEK": 119,
"GBPCHF": 119,
"EURSEK": 119,
"CNYMYRC": 120,
"NZDJPY": 119,
"ZARCHF": 119,
"USDJPY": 119,
"THBUSD": 119,
"HKDJPY": 119,
"EURJPY": 119,
"CADJPY": 119,
"AUDJPY": 119,
"TRYJPY": 119,
"CNHJPY": 133,
"SGDJPY": 119,
"GBPJPY": 119,
"CNYZARC": 120,
"ZARJPY": 119,
"USDRUB": 119,
"CNYDKKC": 120,
"CNYNOKC": 120,
"CNYHUFC": 120,
"CNYPLNC": 120,
"CNYSEKC": 120,
}
@@ -0,0 +1,149 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/6/23 15:00
Desc: 东方财富网-行情中心-外汇市场-所有汇率
https://quote.eastmoney.com/center/gridlist.html#forex_all
"""
import pandas as pd
import requests
from akshare.forex.cons import symbol_market_map
from akshare.utils.func import fetch_paginated_data
def forex_spot_em() -> pd.DataFrame:
"""
东方财富网-行情中心-外汇市场-所有汇率-实时行情数据
https://quote.eastmoney.com/center/gridlist.html#forex_all
:return: 实时行情数据
:rtype: pandas.DataFrame
"""
url = "https://push2.eastmoney.com/api/qt/clist/get"
params = {
"np": "1",
"fltt": "2",
"invt": "2",
"fs": "m:119,m:120,m:133",
"fields": "f12,f13,f14,f1,f2,f4,f3,f152,f17,f18,f15,f16",
"fid": "f3",
"pn": "1",
"pz": "100",
"po": "1",
"dect": "1",
"wbp2u": "|0|0|0|web",
}
temp_df = fetch_paginated_data(url, params)
temp_df.rename(
columns={
"index": "序号",
"f12": "代码",
"f14": "名称",
"f17": "今开",
"f4": "涨跌额",
"f3": "涨跌幅",
"f2": "最新价",
"f15": "最高",
"f16": "最低",
"f18": "昨收",
},
inplace=True,
)
temp_df = temp_df[
[
"序号",
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"今开",
"最高",
"最低",
"昨收",
]
]
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["今开"] = pd.to_numeric(temp_df["今开"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["昨收"] = pd.to_numeric(temp_df["昨收"], errors="coerce")
return temp_df
def forex_hist_em(symbol: str = "USDCNH") -> pd.DataFrame:
"""
东方财富网-行情中心-外汇市场-所有汇率-历史行情数据
https://quote.eastmoney.com/cnyrate/EURCNYC.html
:param symbol: 品种代码可以通过 ak.forex_spot_em() 来获取所有可获取历史行情数据的品种代码
:type symbol: str
:return: 历史行情数据
:rtype: pandas.DataFrame
"""
url = "https://push2his.eastmoney.com/api/qt/stock/kline/get"
market_code = symbol_market_map[symbol]
params = {
"secid": f"{market_code}.{symbol}",
"klt": "101",
"fqt": "1",
"lmt": "50000",
"end": "20500000",
"iscca": "1",
"fields1": "f1,f2,f3,f4,f5,f6,f7,f8",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58,f59,f60,f61,f62,f63,f64",
"ut": "f057cbcbce2a86e2866ab8877db1d059",
"forcect": 1,
}
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame([item.split(",") for item in data_json["data"]["klines"]])
temp_df["code"] = data_json["data"]["code"]
temp_df["name"] = data_json["data"]["name"]
temp_df.columns = [
"日期",
"今开",
"最新价",
"最高",
"最低",
"-",
"-",
"振幅",
"-",
"-",
"-",
"-",
"-",
"-",
"代码",
"名称",
]
temp_df = temp_df[
[
"日期",
"代码",
"名称",
"今开",
"最新价",
"最高",
"最低",
"振幅",
]
]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
temp_df["今开"] = pd.to_numeric(temp_df["今开"], errors="coerce")
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["振幅"] = pd.to_numeric(temp_df["振幅"], errors="coerce")
return temp_df
if __name__ == "__main__":
forex_spot_em_df = forex_spot_em()
print(forex_spot_em_df)
forex_hist_em_df = forex_hist_em(symbol="USDCNH")
print(forex_hist_em_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/12/10 21:55
Desc:
"""
@@ -0,0 +1,95 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/8/4 17:22
Desc: 历年世界 500 强榜单数据
https://www.fortunechina.com/fortune500/index.htm
特殊情况说明
2010年由于网页端没有公布公司所属的国家, 2010 年数据没有国家这列
"""
from functools import lru_cache
from io import StringIO
import pandas as pd
import requests
from bs4 import BeautifulSoup
from tqdm import tqdm
@lru_cache()
def _fortune_rank_year_url_map() -> dict:
"""
年份和网址映射
https://www.fortunechina.com/fortune500/index.htm
:return: 年份和网址映射
:rtype: dict
"""
url = "https://www.fortunechina.com/fortune500/index.htm"
r = requests.get(url)
soup = BeautifulSoup(r.text, features="lxml")
url_2023 = "https://www.fortunechina.com/fortune500/c/2023-08/02/content_436874.htm"
node_list = soup.find_all(name="div", attrs={"class": "swiper-slide"})
url_list = [item.find("a")["href"] for item in node_list]
year_list = [item.find("a").text for item in node_list]
year_url_map = dict(zip(year_list, url_list))
year_url_map["2023"] = url_2023
return year_url_map
def fortune_rank(year: str = "2015") -> pd.DataFrame:
"""
财富 500 强公司从 1996 年开始的排行榜
https://www.fortunechina.com/fortune500/index.htm
:param year: str 年份
:return: pandas.DataFrame
"""
year_url_map = _fortune_rank_year_url_map()
url = year_url_map[year]
r = requests.get(url)
r.encoding = "utf-8"
if int(year) < 2007:
df = pd.read_html(StringIO(r.text))[0].iloc[1:-1,]
df.columns = pd.read_html(StringIO(r.text))[0].iloc[0, :].tolist()
return df
elif 2006 < int(year) < 2010:
df = pd.read_html(StringIO(r.text))[0].iloc[1:,]
df.columns = pd.read_html(StringIO(r.text))[0].iloc[0, :].tolist()
for page in tqdm(range(2, 11), leave=False):
# page =2
r = requests.get(url.rsplit(".", maxsplit=1)[0] + "_" + str(page) + ".htm")
r.encoding = "utf-8"
temp_df = pd.read_html(StringIO(r.text))[0].iloc[1:,]
temp_df.columns = pd.read_html(StringIO(r.text))[0].iloc[0, :].tolist()
df = pd.concat(objs=[df, temp_df], ignore_index=True)
return df
else:
df = pd.read_html(StringIO(r.text))[0]
return df
if __name__ == "__main__":
fortune_rank_df = fortune_rank(year="2023") # 2010 不一样
print(fortune_rank_df)
fortune_rank_df = fortune_rank(year="2022") # 2010 不一样
print(fortune_rank_df)
fortune_rank_df = fortune_rank(year="2008") # 2010 不一样
print(fortune_rank_df)
fortune_rank_df = fortune_rank(year="2008") # 2010 不一样
print(fortune_rank_df)
fortune_rank_df = fortune_rank(year="2009") # 2010 不一样
print(fortune_rank_df)
for item in range(1996, 2008):
print(item)
fortune_rank_df = fortune_rank(year=str(item)) # 2010 不一样
print(fortune_rank_df)
for item in range(2010, 2023):
print(item)
fortune_rank_df = fortune_rank(year=str(item)) # 2010 不一样
print(fortune_rank_df)
@@ -0,0 +1,117 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/4/10 18:24
Desc: 彭博亿万富豪指数
https://www.bloomberg.com/billionaires/
"""
import pandas as pd
import requests
from bs4 import BeautifulSoup
def index_bloomberg_billionaires_hist(year: str = "2021") -> pd.DataFrame:
"""
Bloomberg Billionaires Index
https://stats.areppim.com/stats/links_billionairexlists.htm
:param year: choice of {"2021", "2019", "2018", ...}
:type year: str
:return: 彭博亿万富豪指数历史数据
:rtype: pandas.DataFrame
"""
url = f"https://stats.areppim.com/listes/list_billionairesx{year[-2:]}xwor.htm"
r = requests.get(url)
soup = BeautifulSoup(r.text, "lxml")
trs = soup.findAll("table")[0].findAll("tr")
heads = trs[1]
if "Rank" not in heads.text:
heads = trs[0]
dic_keys = []
dic = {}
for head in heads:
head = head.text
dic_keys.append(head)
for dic_key in dic_keys:
dic[dic_key] = []
for ll in trs:
item = ll.findAll("td")
for i in range(len(item)):
v = item[i].text
if i == 0 and not v.isdigit():
break
dic[dic_keys[i]].append(v)
temp_df = pd.DataFrame(dic)
temp_df = temp_df.rename(
{
"Rank": "rank",
"Name": "name",
"Age": "age",
"Citizenship": "country",
"Country": "country",
"Net Worth(bil US$)": "total_net_worth",
"Total net worth$Billion": "total_net_worth",
"$ Last change": "last_change",
"$ YTD change": "ytd_change",
"Industry": "industry",
},
axis=1,
)
return temp_df
def index_bloomberg_billionaires() -> pd.DataFrame:
"""
Bloomberg Billionaires Index
https://www.bloomberg.com/billionaires/
:return: 彭博亿万富豪指数
:rtype: pandas.DataFrame
"""
url = "https://www.bloomberg.com/billionaires"
headers = {
"accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
"accept-encoding": "gzip, deflate, br",
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8",
"cache-control": "no-cache",
"pragma": "no-cache",
"sec-fetch-dest": "document",
"sec-fetch-mode": "navigate",
"sec-fetch-site": "same-origin",
"sec-fetch-user": "?1",
"upgrade-insecure-requests": "1",
"referer": "https://www.bloomberg.com/",
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.116 Safari/537.36",
}
r = requests.get(url, headers=headers)
soup = BeautifulSoup(r.text, "lxml")
big_content_list = list()
soup_node = soup.find(attrs={"class": "table-chart"}).find_all(
attrs={"class": "table-row"}
)
for row in soup_node:
temp_content_list = row.text.strip().replace("\n", "").split(" ")
content_list = [item for item in temp_content_list if item != ""]
big_content_list.append(content_list)
temp_df = pd.DataFrame(big_content_list)
temp_df.columns = [
"rank",
"name",
"total_net_worth",
"last_change",
"YTD_change",
"country",
"industry",
]
return temp_df
if __name__ == "__main__":
index_bloomberg_billionaires_df = index_bloomberg_billionaires()
print(index_bloomberg_billionaires_df)
index_bloomberg_billionaires_hist_df = index_bloomberg_billionaires_hist(
year="2021"
)
print(index_bloomberg_billionaires_hist_df)
@@ -0,0 +1,46 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/1/26 15:10
Desc: 福布斯中国-榜单
https://www.forbeschina.com/lists
"""
import pandas as pd
import requests
from bs4 import BeautifulSoup
def forbes_rank(symbol: str = "2021福布斯中国创投人100") -> pd.DataFrame:
"""
福布斯中国-榜单
https://www.forbeschina.com/lists
https://www.forbeschina.com/lists/1750
:param symbol: choice of {"2020福布斯美国富豪榜", "2020福布斯新加坡富豪榜", "2020福布斯中国名人榜", *}
:type symbol: str
:return: 具体指标的榜单
:rtype: pandas.DataFrame
"""
url = "https://www.forbeschina.com/lists"
r = requests.get(url, verify=False)
soup = BeautifulSoup(r.text, "lxml")
need_list = [
item.find_all("a") for item in soup.find_all("div", attrs={"class": "col-sm-4"})
]
all_list = []
for item in need_list:
all_list.extend(item)
name_url_dict = dict(
zip(
[item.text.strip() for item in all_list],
["https://www.forbeschina.com" + item["href"] for item in all_list],
)
)
r = requests.get(name_url_dict[symbol], verify=False)
temp_df = pd.read_html(r.text)[0]
return temp_df
if __name__ == "__main__":
forbes_rank_df = forbes_rank(symbol="2021福布斯中国香港富豪榜")
print(forbes_rank_df)
@@ -0,0 +1,338 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/12/22 20:00
Desc: 胡润排行榜
https://www.hurun.net/
"""
import warnings
import pandas as pd
import requests
from bs4 import BeautifulSoup
def hurun_rank(indicator: str = "胡润百富榜", year: str = "2023") -> pd.DataFrame:
"""
胡润排行榜
https://www.hurun.net/CN/HuList/Index?num=3YwKs889SRIm
:param indicator: choice of {"胡润百富榜", "胡润全球富豪榜", "胡润印度榜", "胡润全球独角兽榜", "全球瞪羚企业榜", "胡润Under30s创业领袖榜", "胡润中国500强民营企业", "胡润世界500强", "胡润艺术榜"}
:type indicator: str
:param year: 指定年份; {"胡润百富榜": "2014-至今", "胡润全球富豪榜": "2019-至今", "胡润印度榜": "2018-至今", "胡润全球独角兽榜": "2019-至今", "中国瞪羚企业榜": "2021-至今", "全球瞪羚企业榜": "2021-至今", "胡润Under30s创业领袖榜": "2019-至今", "胡润中国500强民营企业": "2019-至今", "胡润世界500强": "2020-至今", "胡润艺术榜": "2019-至今"}
:type year: str
:return: 指定 indicator year 的数据
:rtype: pandas.DataFrame
"""
url = "https://www.hurun.net/zh-CN/Rank/HsRankDetails?pagetype=rich"
r = requests.get(url)
soup = BeautifulSoup(r.text, "lxml")
url_list = []
for item in soup.find_all("ul", attrs={"class": "dropdown-menu"}):
for inner_item in item.find_all("a"):
url_list.append("https://www.hurun.net" + inner_item["href"])
name_list = []
for item in soup.find_all("ul", attrs={"class": "dropdown-menu"}):
for inner_item in item.find_all("a"):
name_list.append(inner_item.text.strip())
name_url_map = dict(zip(name_list, url_list))
r = requests.get(name_url_map[indicator])
soup = BeautifulSoup(r.text, "lxml")
code_list = [
item["value"].split("=")[2]
for item in soup.find(attrs={"id": "exampleFormControlSelect1"}).find_all(
"option"
)
]
year_list = [
item.text.split(" ")[0]
for item in soup.find(attrs={"id": "exampleFormControlSelect1"}).find_all(
"option"
)
]
year_code_map = dict(zip(year_list, code_list))
params = {
"num": year_code_map[year],
"search": "",
"offset": "0",
"limit": "20000",
}
if year == "2018":
warnings.warn("正在下载中")
offset = 0
limit = 20
big_df = pd.DataFrame()
while offset < 2200:
try:
params.update(
{
"offset": offset,
"limit": limit,
}
)
url = "https://www.hurun.net/zh-CN/Rank/HsRankDetailsList"
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["rows"])
offset = offset + 20
big_df = pd.concat([big_df, temp_df], ignore_index=True)
except requests.exceptions.JSONDecodeError:
offset = offset + 40
continue
big_df.rename(
columns={
"hs_Rank_Rich_Ranking": "排名",
"hs_Rank_Rich_Wealth": "财富",
"hs_Rank_Rich_Ranking_Change": "排名变化",
"hs_Rank_Rich_ChaName_Cn": "姓名",
"hs_Rank_Rich_ComName_Cn": "企业",
"hs_Rank_Rich_Industry_Cn": "行业",
},
inplace=True,
)
big_df = big_df[
[
"排名",
"财富",
"姓名",
"企业",
"行业",
]
]
return big_df
url = "https://www.hurun.net/zh-CN/Rank/HsRankDetailsList"
r = requests.get(url, params=params)
data_json = r.json()
temp_df = pd.DataFrame(data_json["rows"])
if indicator == "胡润百富榜":
temp_df.rename(
columns={
"hs_Rank_Rich_Ranking": "排名",
"hs_Rank_Rich_Wealth": "财富",
"hs_Rank_Rich_Ranking_Change": "排名变化",
"hs_Rank_Rich_ChaName_Cn": "姓名",
"hs_Rank_Rich_ComName_Cn": "企业",
"hs_Rank_Rich_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"财富",
"姓名",
"企业",
"行业",
]
]
elif indicator == "胡润全球富豪榜":
temp_df.rename(
columns={
"hs_Rank_Global_Ranking": "排名",
"hs_Rank_Global_Wealth": "财富",
"hs_Rank_Global_Ranking_Change": "排名变化",
"hs_Rank_Global_ChaName_Cn": "姓名",
"hs_Rank_Global_ComName_Cn": "企业",
"hs_Rank_Global_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"财富",
"姓名",
"企业",
"行业",
]
]
elif indicator == "胡润印度榜":
temp_df.rename(
columns={
"hs_Rank_India_Ranking": "排名",
"hs_Rank_India_Wealth": "财富",
"hs_Rank_India_Ranking_Change": "排名变化",
"hs_Rank_India_ChaName_Cn": "姓名",
"hs_Rank_India_ComName_Cn": "企业",
"hs_Rank_India_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"财富",
"姓名",
"企业",
"行业",
]
]
elif indicator == "胡润全球独角兽榜":
temp_df.rename(
columns={
"hs_Rank_Unicorn_Ranking": "排名",
"hs_Rank_Unicorn_Wealth": "财富",
"hs_Rank_Unicorn_Ranking_Change": "排名变化",
"hs_Rank_Unicorn_ChaName_Cn": "姓名",
"hs_Rank_Unicorn_ComName_Cn": "企业",
"hs_Rank_Unicorn_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"财富",
"姓名",
"企业",
"行业",
]
]
elif indicator == "中国瞪羚企业榜":
temp_df.rename(
columns={
"hs_Rank_CGazelles_ComHeadquarters_Cn": "企业总部",
"hs_Rank_CGazelles_Name_Cn": "掌门人/联合创始人",
"hs_Rank_CGazelles_ComName_Cn": "企业信息",
"hs_Rank_CGazelles_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"企业信息",
"掌门人/联合创始人",
"企业总部",
"行业",
]
]
elif indicator == "全球瞪羚企业榜":
temp_df.rename(
columns={
"hs_Rank_GGazelles_ComHeadquarters_Cn": "企业总部",
"hs_Rank_GGazelles_Name_Cn": "掌门人/联合创始人",
"hs_Rank_GGazelles_ComName_Cn": "企业信息",
"hs_Rank_GGazelles_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"企业信息",
"掌门人/联合创始人",
"企业总部",
"行业",
]
]
elif indicator == "胡润Under30s创业领袖榜":
temp_df.rename(
columns={
"hs_Rank_U30_ComHeadquarters_Cn": "企业总部",
"hs_Rank_U30_ChaName_Cn": "姓名",
"hs_Rank_U30_ComName_Cn": "企业信息",
"hs_Rank_U30_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"姓名",
"企业信息",
"企业总部",
"行业",
]
]
elif indicator == "胡润中国500强民营企业":
temp_df.rename(
columns={
"hs_Rank_CTop500_Ranking": "排名",
"hs_Rank_CTop500_Wealth": "企业估值",
"hs_Rank_CTop500_Ranking_Change": "排名变化",
"hs_Rank_CTop500_ChaName_Cn": "CEO",
"hs_Rank_CTop500_ComName_Cn": "企业信息",
"hs_Rank_CTop500_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"排名变化",
"企业估值",
"企业信息",
"CEO",
"行业",
]
]
elif indicator == "胡润世界500强":
temp_df.rename(
columns={
"hs_Rank_GTop500_Ranking": "排名",
"hs_Rank_GTop500_Wealth": "企业估值",
"hs_Rank_GTop500_Ranking_Change": "排名变化",
"hs_Rank_GTop500_ChaName_Cn": "CEO",
"hs_Rank_GTop500_ComName_Cn": "企业信息",
"hs_Rank_GTop500_Industry_Cn": "行业",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"排名变化",
"企业估值",
"企业信息",
"CEO",
"行业",
]
]
elif indicator == "胡润艺术榜":
temp_df.rename(
columns={
"hs_Rank_Art_Ranking": "排名",
"hs_Rank_Art_Turnover": "成交额",
"hs_Rank_Art_Ranking_Change": "排名变化",
"hs_Rank_Art_Name_Cn": "姓名",
"hs_Rank_Art_Age": "年龄",
"hs_Rank_Art_ArtCategory_Cn": "艺术类别",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"排名变化",
"成交额",
"姓名",
"年龄",
"艺术类别",
]
]
return temp_df
if __name__ == "__main__":
hurun_rank_df = hurun_rank(indicator="胡润百富榜", year="2023")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润全球富豪榜", year="2023")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润全球独角兽榜", year="2023")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润印度榜", year="2021")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="全球瞪羚企业榜", year="2021")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润Under30s创业领袖榜", year="2021")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润世界500强", year="2022")
print(hurun_rank_df)
hurun_rank_df = hurun_rank(indicator="胡润艺术榜", year="2023")
print(hurun_rank_df)
@@ -0,0 +1,76 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2022/10/30 21:12
Desc: 新财富 500 人富豪榜
http://www.xcf.cn/zhuanti/ztzz/hdzt1/500frb/index.html
"""
import json
import pandas as pd
import requests
def xincaifu_rank(year: str = "2022") -> pd.DataFrame:
"""
新财富 500 人富豪榜
http://www.xcf.cn/zhuanti/ztzz/hdzt1/500frb/index.html
:param year: 具体排名年份, 数据从 2003-至今
:type year: str
:return: 排行榜
:rtype: pandas.DataFrame
"""
url = "http://service.ikuyu.cn/XinCaiFu2/pcremoting/bdListAction.do"
params = {
"method": "getPage",
"callback": "jsonpCallback",
"sortBy": "",
"order": "",
"type": "4",
"keyword": "",
"pageSize": "1000",
"year": year,
"pageNo": "1",
"from": "jsonp",
}
r = requests.get(url, params=params)
data_text = r.text
data_json = json.loads(data_text[data_text.find("{") : -1])
temp_df = pd.DataFrame(data_json["data"]["rows"])
temp_df.columns
temp_df.rename(
columns={
"assets": "财富",
"year": "年份",
"sex": "性别",
"name": "姓名",
"rank": "排名",
"company": "主要公司",
"industry": "相关行业",
"id": "-",
"addr": "公司总部",
"rankLst": "-",
"age": "年龄",
},
inplace=True,
)
temp_df = temp_df[
[
"排名",
"财富",
"姓名",
"主要公司",
"相关行业",
"公司总部",
"性别",
"年龄",
"年份",
]
]
return temp_df
if __name__ == "__main__":
xincaifu_rank_df = xincaifu_rank(year="2022")
print(xincaifu_rank_df)
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2019/9/30 13:58
Desc:
"""
@@ -0,0 +1,911 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2024/4/29 16:00
Desc: 中国证券投资基金业协会-信息公示数据
中国证券投资基金业协会-新版: https://gs.amac.org.cn
"""
import pandas as pd
import requests
from akshare.utils.tqdm import get_tqdm
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/123.0.0.0 Safari/537.36",
"Content-Type": "application/json",
}
def _get_pages(url: str = "", payload: str = "") -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-私募基金管理人公示 页数
暂时不使用本函数, 直接可以获取所有数据
"""
res = requests.post(url=url, json=payload, headers=headers)
res.encoding = "utf-8"
json_df = res.json()
return json_df["totalPages"]
def get_data(url: str = "", payload: str = "") -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-私募基金管理人公示
"""
res = requests.post(url=url, json=payload, headers=headers)
res.encoding = "utf-8"
json_df = res.json()
return json_df
# 中国证券投资基金业协会-信息公示-会员信息
# 中国证券投资基金业协会-信息公示-会员信息-会员机构综合查询
def amac_member_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-会员信息-会员机构综合查询
https://gs.amac.org.cn/amac-infodisc/res/pof/member/index.html
:return: 会员机构综合查询
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/pofMember"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "20",
}
r = requests.post(url, params=params, json={}, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"managerName",
"memberBehalf",
"memberType",
"memberCode",
"memberDate",
"primaryInvestType",
"markStar",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"机构(会员)名称",
"会员代表",
"会员类型",
"会员编号",
"入会时间",
"机构类型",
"是否星标",
]
manager_data_out["入会时间"] = pd.to_datetime(
manager_data_out["入会时间"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-从业人员信息
# 中国证券投资基金业协会-信息公示-从业人员信息-基金从业人员资格注册信息
def amac_person_fund_org_list(symbol: str = "公募基金管理公司") -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-从业人员信息-基金从业人员资格注册信息
https://gs.amac.org.cn/amac-infodisc/res/pof/person/personOrgList.html
:param symbol: choice of {"公募基金管理公司", "公募基金管理公司资管子公司", "商业银行", "证券公司", "证券公司子公司",
"私募基金管理人", "保险公司子公司", "保险公司", "外包服务机构", "期货公司", "期货公司资管子公司", "媒体机构",
"证券投资咨询机构", "评价机构", "外资私募证券基金管理人", "支付结算", "独立服务机构", "地方自律组织", "境外机构",
"律师事务所", "会计师事务所", "交易所", "独立第三方销售机构", "证券公司资管子公司", "证券公司私募基金子公司", "其他"}
:type symbol: str
:return: 基金从业人员资格注册信息
:rtype: pandas.DataFrame
"""
symbol_map = {
"保险公司子公司": "bxgszgs",
"期货公司资管子公司": "qhgszgzgs",
"公募基金管理公司资管子公司": "gmjjglgszgzgs",
"商业银行": "syyh",
"交易所": "jys",
"证券公司私募基金子公司": "zqgssmjjzgs",
"地方自律组织": "dfzlzz",
"证券公司": "zqgs",
"评价机构": "pjjg",
"独立第三方销售机构": "dldsfxsjg",
"证券投资咨询机构": "zqtzzxjg",
"外资私募证券基金管理人": "wzsmzqjjglr",
"境外机构": "jwjg",
"证券公司子公司": "zqgszgs",
"公募基金管理公司": "gmjjglgs",
"媒体机构": "mtjg",
"支付结算": "zfjs",
"证券公司资管子公司": "zqgszgzgs",
"会计师事务所": "kjssws",
"独立服务机构": "dlfwjg",
"律师事务所": "lssws",
"期货公司": "qhgs",
"保险公司": "bxgs",
"其他": "qt",
"外包服务机构": "wbfwjg",
"私募基金管理人": "smjjglr",
}
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/personOrg"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "20",
}
r = requests.post(
url,
params=params,
json={"orgType": symbol_map[symbol], "page": "1"},
headers=headers,
)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(
url,
params=params,
json={"orgType": symbol_map[symbol], "page": "1"},
verify=False,
headers=headers,
)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"orgName",
"orgType",
"workerTotalNum",
"operNum",
"salesmanNum",
"investmentManagerNum",
"fundManagerNum",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.reset_index(inplace=True)
manager_data_out["index"] = manager_data_out.index + 1
manager_data_out.columns = [
"序号",
"机构名称",
"机构类型",
"员工人数",
"基金从业资格",
"基金销售业务资格",
"基金经理",
"投资经理",
]
manager_data_out["员工人数"] = pd.to_numeric(manager_data_out["员工人数"])
manager_data_out["基金从业资格"] = pd.to_numeric(manager_data_out["基金从业资格"])
manager_data_out["基金销售业务资格"] = pd.to_numeric(
manager_data_out["基金销售业务资格"]
)
manager_data_out["基金经理"] = pd.to_numeric(manager_data_out["基金经理"])
manager_data_out["投资经理"] = pd.to_numeric(manager_data_out["投资经理"])
return manager_data_out
# 中国证券投资基金业协会-信息公示-从业人员信息-债券投资交易相关人员公示
def amac_person_bond_org_list() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-从业人员信息-债券投资交易相关人员公示
https://human.amac.org.cn/web/org/personPublicity.html
:return: 债券投资交易相关人员公示
:rtype: pandas.DataFrame
"""
import urllib3
import ssl
ctx = ssl.create_default_context()
ctx.options |= ssl.OP_LEGACY_SERVER_CONNECT
# 使用自定义的 SSL 上下文发起 HTTPS 请求
http = urllib3.PoolManager(ssl_context=ctx)
url = "https://human.amac.org.cn/web/api/publicityAddress?rand=0.6288001872566391&pageNum=1&pageSize=5000"
r = http.request(method="GET", url=url)
data_json = r.json()
temp_df = pd.DataFrame(data_json["list"])
temp_df.reset_index(inplace=True)
temp_df["index"] = range(1, len(temp_df) + 1)
temp_df.columns = [
"序号",
"_",
"_",
"机构名称",
"机构类型",
"公示网址",
]
temp_df = temp_df[
[
"序号",
"机构类型",
"机构名称",
"公示网址",
]
]
return temp_df
# 中国证券投资基金业协会-信息公示-私募基金管理人公示
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人综合查询
def amac_manager_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人综合查询
https://gs.amac.org.cn/amac-infodisc/res/pof/manager/index.html
:return: 私募基金管理人综合查询
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/manager"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"managerName",
"artificialPersonName",
"primaryInvestType",
"registerProvince",
"registerNo",
"establishDate",
"registerDate",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"私募基金管理人名称",
"法定代表人/执行事务合伙人(委派代表)姓名",
"机构类型",
"注册地",
"登记编号",
"成立时间",
"登记时间",
]
manager_data_out["成立时间"] = pd.to_datetime(
manager_data_out["成立时间"], unit="ms"
).dt.date
manager_data_out["登记时间"] = pd.to_datetime(
manager_data_out["登记时间"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人分类公示
def amac_manager_classify_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人分类公示
https://gs.amac.org.cn/amac-infodisc/res/pof/manager/managerList.html
:return: 私募基金管理人分类公示
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/manager"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"managerName",
"artificialPersonName",
"primaryInvestType",
"registerNo",
"registerProvince",
"officeAdrAgg",
"establishDate",
"registerDate",
"fundCount",
"memberType",
"hasSpecialTips",
"hasCreditTips",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"私募基金管理人名称",
"法定代表人/执行事务合伙人(委派代表)姓名",
"机构类型",
"登记编号",
"注册地",
"办公地",
"成立时间",
"登记时间",
"在管基金数量",
"会员类型",
"是否有提示信息",
"是否有诚信信息",
]
manager_data_out["成立时间"] = pd.to_datetime(
manager_data_out["成立时间"], unit="ms"
).dt.date
manager_data_out["登记时间"] = pd.to_datetime(
manager_data_out["登记时间"], unit="ms"
).dt.date
manager_data_out["在管基金数量"] = pd.to_numeric(manager_data_out["在管基金数量"])
manager_data_out["是否有提示信息"] = manager_data_out["是否有提示信息"].map(
{True: "", False: ""}
)
manager_data_out["是否有诚信信息"] = manager_data_out["是否有诚信信息"].map(
{True: "", False: ""}
)
return manager_data_out
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-证券公司私募基金子公司管理人信息公示
def amac_member_sub_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-私募基金管理人公示-证券公司私募基金子公司管理人信息公示
https://gs.amac.org.cn/amac-infodisc/res/pof/member/index.html?primaryInvestType=private
:return: 证券公司私募基金子公司管理人信息公示
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/pofMember"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"managerName",
"memberBehalf",
"memberType",
"memberCode",
"memberDate",
"primaryInvestType",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"机构(会员)名称",
"会员代表",
"会员类型",
"会员编号",
"入会时间",
"公司类型",
]
manager_data_out["入会时间"] = pd.to_datetime(
manager_data_out["入会时间"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品
# 中国证券投资基金业协会-信息公示-基金产品-私募基金管理人基金产品
def amac_fund_info(start_page: str = "1", end_page: str = "2000") -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品-私募基金管理人基金产品
https://gs.amac.org.cn/amac-infodisc/res/pof/fund/index.html
:param start_page: 开始页码, 获取指定页码直接的数据
:type start_page: str
:param end_page: 结束页码, 获取指定页码直接的数据
:type end_page: str
:return: 私募基金管理人基金产品
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/fund"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = int(data_json["totalPages"])
if total_page > int(end_page):
real_end_page = int(end_page)
else:
real_end_page = total_page
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(int(start_page) - 1, real_end_page), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"fundName",
"managerName",
"managerType",
"workingState",
"putOnRecordDate",
"establishDate",
"mandatorName",
] # 定义要取的 value 的 keys
manager_data_out = big_df[keys_list].copy()
manager_data_out.columns = [
"基金名称",
"私募基金管理人名称",
"私募基金管理人类型",
"运行状态",
"备案时间",
"建立时间",
"托管人名称",
]
manager_data_out["建立时间"] = pd.to_datetime(
manager_data_out["建立时间"], unit="ms"
).dt.date
manager_data_out["备案时间"] = pd.to_datetime(
manager_data_out["备案时间"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品-证券公司集合资管产品公示
def amac_securities_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-证券公司集合资管产品公示
https://gs.amac.org.cn/amac-infodisc/res/pof/securities/index.html
:return: 证券公司集合资管产品公示
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/securities"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"cpmc",
"cpbm",
"gljg",
"slrq",
"dqr",
"tzlx",
"sffj",
"tgjg",
"barq",
"yzzt",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"产品名称",
"产品编码",
"管理人名称",
"成立日期",
"到期时间",
"投资类型",
"是否分级",
"托管人名称",
"备案日期",
"运作状态",
]
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品-证券公司直投基金
def amac_aoin_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-证券公司直投基金
https://gs.amac.org.cn/amac-infodisc/res/aoin/product/index.html
:return: 证券公司直投基金
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/aoin/product"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"code",
"name",
"aoinName",
"managerName",
"createDate",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"产品编码",
"产品名称",
"直投子公司",
"管理机构",
"设立日期",
]
manager_data_out["设立日期"] = pd.to_datetime(
manager_data_out["设立日期"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品公示-证券公司私募投资基金
def amac_fund_sub_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-证券公司私募投资基金
https://gs.amac.org.cn/amac-infodisc/res/pof/subfund/index.html
:return: 证券公司私募投资基金
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/subfund"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"productCode",
"productName",
"mgrName",
"trustee",
"foundDate",
"registeredDate",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"产品编码",
"产品名称",
"私募基金管理人名称",
"托管人名称",
"成立日期",
"备案日期",
]
manager_data_out["备案日期"] = pd.to_datetime(
manager_data_out["备案日期"], unit="ms"
).dt.date
manager_data_out["成立日期"] = pd.to_datetime(
manager_data_out["成立日期"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品公示-基金公司及子公司集合资管产品公示
def amac_fund_account_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-基金公司及子公司集合资管产品公示
https://gs.amac.org.cn/amac-infodisc/res/fund/account/index.html
:return: 基金公司及子公司集合资管产品公示
:rtype: pandas.DataFrame
"""
import warnings
warnings.filterwarnings(action="ignore", category=FutureWarning)
url = "https://gs.amac.org.cn/amac-infodisc/api/fund/account"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"registerDate",
"registerCode",
"name",
"manager",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"成立日期",
"产品编码",
"产品名称",
"管理人名称",
]
manager_data_out["成立日期"] = pd.to_datetime(
manager_data_out["成立日期"], unit="ms"
).dt.date
return manager_data_out
# 中国证券投资基金业协会-信息公示-基金产品公示-资产支持专项计划
def amac_fund_abs() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-资产支持专项计划公示信息
https://gs.amac.org.cn/amac-infodisc/res/fund/abs/index.html
:return: 资产支持专项计划公示信息
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/fund/abs"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.reset_index(inplace=True)
big_df["index"] = range(1, len(big_df) + 1)
big_df.columns = [
"编号",
"_",
"_",
"专项计划全称",
"备案编号",
"管理人",
"托管人",
"备案通过时间",
"成立日期",
"预期到期时间",
]
big_df["备案通过时间"] = pd.to_datetime(big_df["备案通过时间"], unit="ms").dt.date
big_df["成立日期"] = pd.to_datetime(big_df["成立日期"], unit="ms").dt.date
big_df["预期到期时间"] = pd.to_datetime(
big_df["预期到期时间"], unit="ms", errors="coerce"
).dt.date
big_df = big_df[
[
"编号",
"备案编号",
"专项计划全称",
"管理人",
"托管人",
"成立日期",
"预期到期时间",
"备案通过时间",
]
]
return big_df
# 中国证券投资基金业协会-信息公示-基金产品公示-期货公司集合资管产品公示
def amac_futures_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-基金产品公示-期货公司集合资管产品公示
https://gs.amac.org.cn/amac-infodisc/res/pof/futures/index.html
:return: 期货公司集合资管产品公示
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/pof/futures"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"mpiName",
"mpiProductCode",
"aoiName",
"mpiTrustee",
"mpiCreateDate",
"tzlx",
"sfjgh",
"registeredDate",
"dueDate",
"fundStatus",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"产品名称",
"产品编码",
"管理人名称",
"托管人名称",
"成立日期",
"投资类型",
"是否分级",
"备案日期",
"到期日",
"运作状态",
]
return manager_data_out
# 中国证券投资基金业协会-信息公示-诚信信息
# 中国证券投资基金业协会-信息公示-诚信信息-已注销私募基金管理人名单
def amac_manager_cancelled_info() -> pd.DataFrame:
"""
中国证券投资基金业协会-信息公示-诚信信息公示-已注销私募基金管理人名单
https://gs.amac.org.cn/amac-infodisc/res/cancelled/manager/index.html
主动注销: 100
依公告注销: 200
协会注销: 300
:return: 已注销私募基金管理人名单
:rtype: pandas.DataFrame
"""
url = "https://gs.amac.org.cn/amac-infodisc/api/cancelled/manager"
params = {
"rand": "0.7665138514630696",
"page": "1",
"size": "100",
}
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
total_page = data_json["totalPages"]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(0, int(total_page)), leave=False):
params.update({"page": page})
r = requests.post(url, params=params, json={}, verify=False, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["content"])
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
keys_list = [
"orgName",
"orgCode",
"orgSignDate",
"cancelDate",
"status",
] # 定义要取的 value 的 keys
manager_data_out = pd.DataFrame(big_df)
manager_data_out = manager_data_out[keys_list]
manager_data_out.columns = [
"管理人名称",
"统一社会信用代码",
"登记时间",
"注销时间",
"注销类型",
]
manager_data_out["登记时间"] = pd.to_datetime(
manager_data_out["登记时间"], unit="ms"
).dt.date
manager_data_out["注销时间"] = pd.to_datetime(
manager_data_out["注销时间"], unit="ms"
).dt.date
manager_data_out.sort_values(["注销时间"], ignore_index=True, inplace=True)
return manager_data_out
if __name__ == "__main__":
# 中国证券投资基金业协会-信息公示-会员信息
# 中国证券投资基金业协会-信息公示-会员信息-会员机构综合查询
amac_member_info_df = amac_member_info()
print(amac_member_info_df)
# 中国证券投资基金业协会-信息公示-从业人员信息
# 中国证券投资基金业协会-信息公示-从业人员信息-基金从业人员资格注册信息
amac_person_fund_org_list_df = amac_person_fund_org_list(symbol="公募基金管理公司")
print(amac_person_fund_org_list_df)
# 中国证券投资基金业协会-信息公示-从业人员信息
# 中国证券投资基金业协会-信息公示-从业人员信息-债券投资交易相关人员公示
amac_person_bond_org_list_df = amac_person_bond_org_list()
print(amac_person_bond_org_list_df)
# 中国证券投资基金业协会-信息公示-私募基金管理人公示
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人综合查询
amac_manager_info_df = amac_manager_info()
print(amac_manager_info_df)
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-私募基金管理人分类公示
amac_manager_classify_info_df = amac_manager_classify_info()
print(amac_manager_classify_info_df)
# 中国证券投资基金业协会-信息公示-私募基金管理人公示-证券公司私募基金子公司管理人信息公示
amac_member_sub_info_df = amac_member_sub_info()
print(amac_member_sub_info_df)
# 中国证券投资基金业协会-信息公示-基金产品
# 中国证券投资基金业协会-信息公示-基金产品-私募基金管理人基金产品
amac_fund_info_df = amac_fund_info(start_page="1", end_page="100")
print(amac_fund_info_df)
example_df = amac_fund_info_df[
amac_fund_info_df["私募基金管理人名称"].str.contains("聚宽")
]
print(example_df)
# 中国证券投资基金业协会-信息公示-基金产品-证券公司集合资管产品公示
amac_securities_info_df = amac_securities_info()
print(amac_securities_info_df)
# 中国证券投资基金业协会-信息公示-基金产品-证券公司直投基金
amac_aoin_info_df = amac_aoin_info()
print(amac_aoin_info_df)
# 中国证券投资基金业协会-信息公示-基金产品公示-证券公司私募投资基金
amac_fund_sub_info_df = amac_fund_sub_info()
print(amac_fund_sub_info_df)
# 中国证券投资基金业协会-信息公示-基金产品公示-基金公司及子公司集合资管产品公示
amac_fund_account_info_df = amac_fund_account_info()
print(amac_fund_account_info_df)
# 中国证券投资基金业协会-信息公示-基金产品公示-资产支持专项计划
amac_fund_abs_df = amac_fund_abs()
print(amac_fund_abs_df)
# 中国证券投资基金业协会-信息公示-基金产品公示-期货公司集合资管产品公示
amac_futures_info_df = amac_futures_info()
print(amac_futures_info_df)
# 中国证券投资基金业协会-信息公示-诚信信息
# 中国证券投资基金业协会-信息公示-诚信信息-已注销私募基金管理人名单
amac_manager_cancelled_info_df = amac_manager_cancelled_info()
print(amac_manager_cancelled_info_df)
@@ -0,0 +1,145 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/9/20 17:40
Desc: 东方财富网站-天天基金网-基金档案-基金公告
https://fundf10.eastmoney.com/jjgg_000001.html
"""
import time
import pandas as pd
import requests
def fund_announcement_dividend_em(symbol: str = "000001") -> pd.DataFrame:
"""
东方财富网站-天天基金网-基金档案-基金公告-分红配送
https://fundf10.eastmoney.com/jjgg_000001_2.html
:param symbol: 基金代码; 可以通过调用 ak.fund_name_em() 接口获取
:type symbol: str
:return: 分红配送-公告列表
:rtype: pandas.DataFrame
"""
url = "http://api.fund.eastmoney.com/f10/JJGG"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/80.0.3987.149 Safari/537.36",
"Referer": f"http://fundf10.eastmoney.com/jjgg_{symbol}_2.html",
}
params = {
"fundcode": symbol,
"pageIndex": "1",
"pageSize": "1000",
"type": "2",
"_": round(time.time() * 1000),
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["Data"])
temp_df.columns = [
"基金代码",
"公告标题",
"基金名称",
"_",
"_",
"公告日期",
"_",
"报告ID",
]
temp_df = temp_df[["基金代码", "公告标题", "基金名称", "公告日期", "报告ID"]]
temp_df.sort_values(by=["公告日期"], inplace=True, ignore_index=True)
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
return temp_df
def fund_announcement_report_em(symbol: str = "000001") -> pd.DataFrame:
"""
东方财富网站-天天基金网-基金档案-基金公告-定期报告
https://fundf10.eastmoney.com/jjgg_000001_3.html
:param symbol: 基金代码; 可以通过调用 ak.fund_name_em() 接口获取
:type symbol: str
:return: 定期报告-公告列表
:rtype: pandas.DataFrame
"""
url = "http://api.fund.eastmoney.com/f10/JJGG"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/80.0.3987.149 Safari/537.36",
"Referer": f"http://fundf10.eastmoney.com/jjgg_{symbol}_3.html",
}
params = {
"fundcode": symbol,
"pageIndex": "1",
"pageSize": "1000",
"type": "3",
"_": round(time.time() * 1000),
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["Data"])
temp_df.columns = [
"基金代码",
"公告标题",
"基金名称",
"_",
"_",
"公告日期",
"_",
"报告ID",
]
temp_df = temp_df[["基金代码", "公告标题", "基金名称", "公告日期", "报告ID"]]
temp_df.sort_values(by=["公告日期"], inplace=True, ignore_index=True)
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
return temp_df
def fund_announcement_personnel_em(symbol: str = "000001") -> pd.DataFrame:
"""
东方财富网站-天天基金网-基金档案-基金公告-人事调整
https://fundf10.eastmoney.com/jjgg_000001_4.html
:param symbol: 基金代码; 可以通过调用 ak.fund_name_em() 接口获取
:type symbol: str
:return: 人事调整-公告列表
:rtype: pandas.DataFrame
"""
url = "http://api.fund.eastmoney.com/f10/JJGG"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.149 Safari/537.36",
"Referer": f"http://fundf10.eastmoney.com/jjgg_{symbol}_4.html",
}
params = {
"fundcode": symbol,
"pageIndex": "1",
"pageSize": "1000",
"type": "4",
"_": round(time.time() * 1000),
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["Data"])
temp_df.columns = [
"基金代码",
"公告标题",
"基金名称",
"_",
"_",
"公告日期",
"_",
"报告ID",
]
temp_df = temp_df[["基金代码", "公告标题", "基金名称", "公告日期", "报告ID"]]
temp_df.sort_values(by=["公告日期"], inplace=True, ignore_index=True)
temp_df["公告日期"] = pd.to_datetime(temp_df["公告日期"], errors="coerce").dt.date
return temp_df
if __name__ == "__main__":
fund_announcement_dividend_em_df = fund_announcement_dividend_em(symbol="000001")
print(fund_announcement_dividend_em_df)
fund_announcement_report_em_df = fund_announcement_report_em(symbol="000001")
print(fund_announcement_report_em_df)
fund_announcement_personnel_em_df = fund_announcement_personnel_em(symbol="000001")
print(fund_announcement_personnel_em_df)
@@ -0,0 +1,106 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/11/11 16:30
Desc: 东方财富-基金
"""
from io import StringIO
import pandas as pd
import requests
def fund_aum_em() -> pd.DataFrame:
"""
东方财富-基金-基金公司排名列表
https://fund.eastmoney.com/Company/lsgm.html
:return: 基金公司排名列表
:rtype: pandas.DataFrame
"""
url = "https://fund.eastmoney.com/Company/home/gspmlist"
params = {"fundType": "0"}
r = requests.get(url, params=params)
temp_df = pd.read_html(StringIO(r.text))[0]
del temp_df["相关链接"]
del temp_df["天相评级"]
temp_df.columns = [
"序号",
"基金公司",
"成立时间",
"全部管理规模",
"全部基金数",
"全部经理数",
]
expanded_df = temp_df["全部管理规模"].str.split(" ", expand=True)
temp_df["全部管理规模"] = expanded_df.iloc[:, 0].str.replace(",", "")
temp_df["更新日期"] = expanded_df.iloc[:, 1]
temp_df["全部管理规模"] = pd.to_numeric(temp_df["全部管理规模"], errors="coerce")
temp_df["全部基金数"] = pd.to_numeric(temp_df["全部基金数"], errors="coerce")
temp_df["全部经理数"] = pd.to_numeric(temp_df["全部经理数"], errors="coerce")
temp_df["成立时间"] = pd.to_datetime(temp_df["成立时间"], errors="coerce").dt.date
return temp_df
def fund_aum_trend_em() -> pd.DataFrame:
"""
东方财富-基金-基金市场管理规模走势图
https://fund.eastmoney.com/Company/default.html
:return: 基金市场管理规模走势图
:rtype: pandas.DataFrame
"""
url = "https://fund.eastmoney.com/Company/home/GetFundTotalScaleForChart"
payload = {"fundType": "0"}
r = requests.get(url, data=payload)
data_json = r.json()
temp_df = pd.DataFrame()
temp_df["date"] = data_json["x"]
temp_df["value"] = data_json["y"]
temp_df["date"] = pd.to_datetime(temp_df["date"], errors="coerce").dt.date
temp_df["value"] = pd.to_numeric(temp_df["value"], errors="coerce")
return temp_df
def fund_aum_hist_em(year: str = "2023") -> pd.DataFrame:
"""
东方财富-基金-基金公司历年管理规模排行列表
https://fund.eastmoney.com/Company/lsgm.html
:param year: query year
:type year: str
:return: 基金公司历年管理规模排行列表
:rtype: pandas.DataFrame
"""
url = "https://fund.eastmoney.com/Company/home/HistoryScaleTable"
params = {"year": year}
r = requests.get(url, params=params)
temp_df = pd.read_html(StringIO(r.text))[0]
temp_df.columns = [
"序号",
"基金公司",
"总规模",
"股票型",
"混合型",
"债券型",
"指数型",
"QDII",
"货币型",
]
temp_df["总规模"] = pd.to_numeric(temp_df["总规模"], errors="coerce")
temp_df["股票型"] = pd.to_numeric(temp_df["股票型"], errors="coerce")
temp_df["混合型"] = pd.to_numeric(temp_df["混合型"], errors="coerce")
temp_df["债券型"] = pd.to_numeric(temp_df["债券型"], errors="coerce")
temp_df["指数型"] = pd.to_numeric(temp_df["指数型"], errors="coerce")
temp_df["QDII"] = pd.to_numeric(temp_df["QDII"], errors="coerce")
temp_df["货币型"] = pd.to_numeric(temp_df["货币型"], errors="coerce")
return temp_df
if __name__ == "__main__":
fund_aum_em_df = fund_aum_em()
print(fund_aum_em_df)
fund_aum_trend_em_df = fund_aum_trend_em()
print(fund_aum_trend_em_df)
fund_em_aum_hist_df = fund_aum_hist_em(year="2023")
print(fund_em_aum_hist_df)
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,497 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/4/27 00:00
Desc: 东方财富-ETF行情
https://quote.eastmoney.com/sh513500.html
"""
from functools import lru_cache
import pandas as pd
import requests
from akshare.utils.func import fetch_paginated_data
@lru_cache()
def _fund_etf_code_id_map_em() -> dict:
"""
东方财富-ETF代码和市场标识映射
https://quote.eastmoney.com/center/gridlist.html#fund_etf
:return: ETF 代码和市场标识映射
:rtype: dict
"""
url = "https://88.push2.eastmoney.com/api/qt/clist/get"
params = {
"pn": "1",
"pz": "100",
"po": "1",
"np": "1",
"ut": "bd1d9ddb04089700cf9c27f6f7426281",
"fltt": "2",
"invt": "2",
"wbp2u": "|0|0|0|web",
"fid": "f3",
"fs": "b:MK0021,b:MK0022,b:MK0023,b:MK0024",
"fields": "f3,f12,f13",
}
temp_df = fetch_paginated_data(url, params)
temp_dict = dict(zip(temp_df["f12"], temp_df["f13"]))
return temp_dict
def fund_etf_spot_em() -> pd.DataFrame:
"""
东方财富-ETF 实时行情
https://quote.eastmoney.com/center/gridlist.html#fund_etf
:return: ETF 实时行情
:rtype: pandas.DataFrame
"""
url = "https://push2delay.eastmoney.com/api/qt/clist/get"
params = {
"pn": "1",
"pz": "100",
"po": "1",
"np": "1",
"ut": "bd1d9ddb04089700cf9c27f6f7426281",
"fltt": "2",
"invt": "2",
"wbp2u": "|0|0|0|web",
"fid": "f12",
"fs": "b:MK0021,b:MK0022,b:MK0023,b:MK0024,b:MK0827",
"fields": (
"f1,f2,f3,f4,f5,f6,f7,f8,f9,f10,"
"f12,f13,f14,f15,f16,f17,f18,f20,f21,"
"f23,f24,f25,f22,f11,f30,f31,f32,f33,"
"f34,f35,f38,f62,f63,f64,f65,f66,f69,"
"f72,f75,f78,f81,f84,f87,f115,f124,f128,"
"f136,f152,f184,f297,f402,f441"
),
}
temp_df = fetch_paginated_data(url, params)
temp_df.rename(
columns={
"f12": "代码",
"f14": "名称",
"f2": "最新价",
"f4": "涨跌额",
"f3": "涨跌幅",
"f5": "成交量",
"f6": "成交额",
"f7": "振幅",
"f17": "开盘价",
"f15": "最高价",
"f16": "最低价",
"f18": "昨收",
"f8": "换手率",
"f10": "量比",
"f30": "现手",
"f31": "买一",
"f32": "卖一",
"f33": "委比",
"f34": "外盘",
"f35": "内盘",
"f62": "主力净流入-净额",
"f184": "主力净流入-净占比",
"f66": "超大单净流入-净额",
"f69": "超大单净流入-净占比",
"f72": "大单净流入-净额",
"f75": "大单净流入-净占比",
"f78": "中单净流入-净额",
"f81": "中单净流入-净占比",
"f84": "小单净流入-净额",
"f87": "小单净流入-净占比",
"f38": "最新份额",
"f21": "流通市值",
"f20": "总市值",
"f402": "基金折价率",
"f441": "IOPV实时估值",
"f297": "数据日期",
"f124": "更新时间",
},
inplace=True,
)
temp_df = temp_df[
[
"代码",
"名称",
"最新价",
"IOPV实时估值",
"基金折价率",
"涨跌额",
"涨跌幅",
"成交量",
"成交额",
"开盘价",
"最高价",
"最低价",
"昨收",
"振幅",
"换手率",
"量比",
"委比",
"外盘",
"内盘",
"主力净流入-净额",
"主力净流入-净占比",
"超大单净流入-净额",
"超大单净流入-净占比",
"大单净流入-净额",
"大单净流入-净占比",
"中单净流入-净额",
"中单净流入-净占比",
"小单净流入-净额",
"小单净流入-净占比",
"现手",
"买一",
"卖一",
"最新份额",
"流通市值",
"总市值",
"数据日期",
"更新时间",
]
]
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["开盘价"] = pd.to_numeric(temp_df["开盘价"], errors="coerce")
temp_df["最高价"] = pd.to_numeric(temp_df["最高价"], errors="coerce")
temp_df["最低价"] = pd.to_numeric(temp_df["最低价"], errors="coerce")
temp_df["昨收"] = pd.to_numeric(temp_df["昨收"], errors="coerce")
temp_df["换手率"] = pd.to_numeric(temp_df["换手率"], errors="coerce")
temp_df["量比"] = pd.to_numeric(temp_df["量比"], errors="coerce")
temp_df["委比"] = pd.to_numeric(temp_df["委比"], errors="coerce")
temp_df["外盘"] = pd.to_numeric(temp_df["外盘"], errors="coerce")
temp_df["内盘"] = pd.to_numeric(temp_df["内盘"], errors="coerce")
temp_df["流通市值"] = pd.to_numeric(temp_df["流通市值"], errors="coerce")
temp_df["总市值"] = pd.to_numeric(temp_df["总市值"], errors="coerce")
temp_df["振幅"] = pd.to_numeric(temp_df["振幅"], errors="coerce")
temp_df["现手"] = pd.to_numeric(temp_df["现手"], errors="coerce")
temp_df["买一"] = pd.to_numeric(temp_df["买一"], errors="coerce")
temp_df["卖一"] = pd.to_numeric(temp_df["卖一"], errors="coerce")
temp_df["最新份额"] = pd.to_numeric(temp_df["最新份额"], errors="coerce")
temp_df["IOPV实时估值"] = pd.to_numeric(temp_df["IOPV实时估值"], errors="coerce")
temp_df["基金折价率"] = pd.to_numeric(temp_df["基金折价率"], errors="coerce")
temp_df["主力净流入-净额"] = pd.to_numeric(
temp_df["主力净流入-净额"], errors="coerce"
)
temp_df["主力净流入-净占比"] = pd.to_numeric(
temp_df["主力净流入-净占比"], errors="coerce"
)
temp_df["超大单净流入-净额"] = pd.to_numeric(
temp_df["超大单净流入-净额"], errors="coerce"
)
temp_df["超大单净流入-净占比"] = pd.to_numeric(
temp_df["超大单净流入-净占比"], errors="coerce"
)
temp_df["大单净流入-净额"] = pd.to_numeric(
temp_df["大单净流入-净额"], errors="coerce"
)
temp_df["大单净流入-净占比"] = pd.to_numeric(
temp_df["大单净流入-净占比"], errors="coerce"
)
temp_df["中单净流入-净额"] = pd.to_numeric(
temp_df["中单净流入-净额"], errors="coerce"
)
temp_df["中单净流入-净占比"] = pd.to_numeric(
temp_df["中单净流入-净占比"], errors="coerce"
)
temp_df["小单净流入-净额"] = pd.to_numeric(
temp_df["小单净流入-净额"], errors="coerce"
)
temp_df["小单净流入-净占比"] = pd.to_numeric(
temp_df["小单净流入-净占比"], errors="coerce"
)
temp_df["数据日期"] = pd.to_datetime(
temp_df["数据日期"], format="%Y%m%d", errors="coerce"
)
temp_df["更新时间"] = (
pd.to_datetime(temp_df["更新时间"], unit="s", errors="coerce")
.dt.tz_localize("UTC")
.dt.tz_convert("Asia/Shanghai")
)
return temp_df
def get_market_id(symbol: str) -> int:
"""
东方财富-ETF市场标识判断
:param symbol: ETF 代码
:type symbol: str
:return: ETF 代码和市场标识1:上证 0:深证
:rtype: int
"""
if symbol.startswith(("0", "1", "3", "2", "5", "6")):
if symbol.startswith(("5", "6")):
return 1
else:
return 0
else:
return 1
def fund_etf_hist_em(
symbol: str = "159707",
period: str = "daily",
start_date: str = "19700101",
end_date: str = "20500101",
adjust: str = "",
) -> pd.DataFrame:
"""
东方财富-ETF行情
https://quote.eastmoney.com/sz159707.html
:param symbol: ETF 代码
:type symbol: str
:param period: choice of {'daily', 'weekly', 'monthly'}
:type period: str
:param start_date: 开始日期
:type start_date: str
:param end_date: 结束日期
:type end_date: str
:param adjust: choice of {"qfq": "前复权", "hfq": "后复权", "": "不复权"}
:type adjust: str
:return: 每日行情
:rtype: pandas.DataFrame
"""
# code_id_dict = _fund_etf_code_id_map_em()
adjust_dict = {"qfq": "1", "hfq": "2", "": "0"}
period_dict = {"daily": "101", "weekly": "102", "monthly": "103"}
url = "https://push2his.eastmoney.com/api/qt/stock/kline/get"
params = {
"fields1": "f1,f2,f3,f4,f5,f6",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58,f59,f60,f61,f116",
"ut": "7eea3edcaed734bea9cbfc24409ed989",
"klt": period_dict[period],
"fqt": adjust_dict[adjust],
"beg": start_date,
"end": end_date,
}
try:
# market_id = code_id_dict[symbol]
market_id = get_market_id(symbol)
params.update({"secid": f"{market_id}.{symbol}"})
r = requests.get(url, timeout=15, params=params)
data_json = r.json()
except KeyError:
market_id = 1
params.update({"secid": f"{market_id}.{symbol}"})
r = requests.get(url, timeout=15, params=params)
data_json = r.json()
if not data_json["data"]:
market_id = 0
params.update({"secid": f"{market_id}.{symbol}"})
r = requests.get(url, timeout=15, params=params)
data_json = r.json()
if not (data_json["data"] and data_json["data"]["klines"]):
return pd.DataFrame()
temp_df = pd.DataFrame([item.split(",") for item in data_json["data"]["klines"]])
temp_df.columns = [
"日期",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"振幅",
"涨跌幅",
"涨跌额",
"换手率",
]
temp_df.index = pd.to_datetime(temp_df["日期"], errors="coerce")
temp_df.reset_index(inplace=True, drop=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["振幅"] = pd.to_numeric(temp_df["振幅"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["换手率"] = pd.to_numeric(temp_df["换手率"], errors="coerce")
return temp_df
def fund_etf_hist_min_em(
symbol: str = "159707",
start_date: str = "1979-09-01 09:32:00",
end_date: str = "2222-01-01 09:32:00",
period: str = "5",
adjust: str = "",
) -> pd.DataFrame:
"""
东方财富-ETF 行情
https://quote.eastmoney.com/sz159707.html
:param symbol: ETF 代码
:type symbol: str
:param start_date: 开始日期
:type start_date: str
:param end_date: 结束日期
:type end_date: str
:param period: choice of {"1", "5", "15", "30", "60"}
:type period: str
:param adjust: choice of {'', 'qfq', 'hfq'}
:type adjust: str
:return: 每日分时行情
:rtype: pandas.DataFrame
"""
# code_id_dict = _fund_etf_code_id_map_em()
# 商品期货类 ETF
# code_id_dict.update(
# {
# "159980": "0",
# "159981": "0",
# "159985": "0",
# "511090": "1",
# "511220": "1",
# "511380": "1",
# }
# )
adjust_map = {
"": "0",
"qfq": "1",
"hfq": "2",
}
if period == "1":
url = "https://push2his.eastmoney.com/api/qt/stock/trends2/get"
params = {
"fields1": "f1,f2,f3,f4,f5,f6,f7,f8,f9,f10,f11,f12,f13",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58",
"ut": "7eea3edcaed734bea9cbfc24409ed989",
"ndays": "5",
"iscr": "0",
"secid": f"{get_market_id(symbol)}.{symbol}",
}
r = requests.get(url, timeout=15, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
[item.split(",") for item in data_json["data"]["trends"]]
)
temp_df.columns = [
"时间",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"均价",
]
temp_df.index = pd.to_datetime(temp_df["时间"])
temp_df = temp_df[start_date:end_date]
temp_df.reset_index(drop=True, inplace=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["均价"] = pd.to_numeric(temp_df["均价"], errors="coerce")
temp_df["时间"] = pd.to_datetime(temp_df["时间"]).astype(str)
return temp_df
else:
url = "https://push2his.eastmoney.com/api/qt/stock/kline/get"
params = {
"fields1": "f1,f2,f3,f4,f5,f6",
"fields2": "f51,f52,f53,f54,f55,f56,f57,f58,f59,f60,f61",
"ut": "7eea3edcaed734bea9cbfc24409ed989",
"klt": period,
"fqt": adjust_map[adjust],
"secid": f"{get_market_id(symbol)}.{symbol}",
"beg": "0",
"end": "20500000",
}
r = requests.get(url, timeout=15, params=params)
data_json = r.json()
temp_df = pd.DataFrame(
[item.split(",") for item in data_json["data"]["klines"]]
)
temp_df.columns = [
"时间",
"开盘",
"收盘",
"最高",
"最低",
"成交量",
"成交额",
"振幅",
"涨跌幅",
"涨跌额",
"换手率",
]
temp_df.index = pd.to_datetime(temp_df["时间"])
temp_df = temp_df[start_date:end_date]
temp_df.reset_index(drop=True, inplace=True)
temp_df["开盘"] = pd.to_numeric(temp_df["开盘"], errors="coerce")
temp_df["收盘"] = pd.to_numeric(temp_df["收盘"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
temp_df["振幅"] = pd.to_numeric(temp_df["振幅"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["换手率"] = pd.to_numeric(temp_df["换手率"], errors="coerce")
temp_df["时间"] = pd.to_datetime(temp_df["时间"]).astype(str)
temp_df = temp_df[
[
"时间",
"开盘",
"收盘",
"最高",
"最低",
"涨跌幅",
"涨跌额",
"成交量",
"成交额",
"振幅",
"换手率",
]
]
return temp_df
if __name__ == "__main__":
fund_etf_spot_em_df = fund_etf_spot_em()
print(fund_etf_spot_em_df)
fund_etf_hist_hfq_em_df = fund_etf_hist_em(
symbol="513500",
period="daily",
start_date="20000101",
end_date="20230201",
adjust="hfq",
)
print(fund_etf_hist_hfq_em_df)
fund_etf_hist_qfq_em_df = fund_etf_hist_em(
symbol="511010",
period="daily",
start_date="20000101",
end_date="20230718",
adjust="",
)
print(fund_etf_hist_qfq_em_df)
fund_etf_hist_em_df = fund_etf_hist_em(
symbol="159985",
period="daily",
start_date="20000101",
end_date="20231211",
adjust="",
)
print(fund_etf_hist_em_df)
fund_etf_hist_min_em_df = fund_etf_hist_min_em(
symbol="511380",
period="1",
adjust="",
start_date="2025-04-10 09:30:00",
end_date="2025-04-10 17:40:00",
)
print(fund_etf_hist_min_em_df)
@@ -0,0 +1,205 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/11/10 15:30
Desc: 新浪财经-基金行情
https://vip.stock.finance.sina.com.cn/fund_center/index.html#jjhqetf
"""
import pandas as pd
import py_mini_racer
import requests
from akshare.stock.cons import hk_js_decode
from akshare.utils import demjson
def fund_etf_category_sina(symbol: str = "LOF基金") -> pd.DataFrame:
"""
新浪财经-基金列表
https://vip.stock.finance.sina.com.cn/fund_center/index.html#jjhqetf
:param symbol: choice of {"封闭式基金", "ETF基金", "LOF基金"}
:type symbol: str
:return: 指定 symbol 的基金列表
:rtype: pandas.DataFrame
"""
fund_map = {
"封闭式基金": "close_fund",
"ETF基金": "etf_hq_fund",
"LOF基金": "lof_hq_fund",
}
url = (
"https://vip.stock.finance.sina.com.cn/quotes_service/api/jsonp.php/"
"IO.XSRV2.CallbackList['da_yPT46_Ll7K6WD']/Market_Center.getHQNodeDataSimple"
)
params = {
"page": "1",
"num": "5000",
"sort": "symbol",
"asc": "0",
"node": fund_map[symbol],
"[object HTMLDivElement]": "qvvne",
}
r = requests.get(url, params=params)
data_text = r.text
data_json = demjson.decode(data_text[data_text.find("([") + 1 : -2])
temp_df = pd.DataFrame(data_json)
if symbol == "封闭式基金":
temp_df.columns = [
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"买入",
"卖出",
"昨收",
"今开",
"最高",
"最低",
"成交量",
"成交额",
"_",
"_",
]
else:
temp_df.columns = [
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"买入",
"卖出",
"昨收",
"今开",
"最高",
"最低",
"成交量",
"成交额",
"_",
"_",
"_",
"_",
]
temp_df = temp_df[
[
"代码",
"名称",
"最新价",
"涨跌额",
"涨跌幅",
"买入",
"卖出",
"昨收",
"今开",
"最高",
"最低",
"成交量",
"成交额",
]
]
temp_df["最新价"] = pd.to_numeric(temp_df["最新价"], errors="coerce")
temp_df["涨跌额"] = pd.to_numeric(temp_df["涨跌额"], errors="coerce")
temp_df["涨跌幅"] = pd.to_numeric(temp_df["涨跌幅"], errors="coerce")
temp_df["买入"] = pd.to_numeric(temp_df["买入"], errors="coerce")
temp_df["卖出"] = pd.to_numeric(temp_df["卖出"], errors="coerce")
temp_df["昨收"] = pd.to_numeric(temp_df["昨收"], errors="coerce")
temp_df["今开"] = pd.to_numeric(temp_df["今开"], errors="coerce")
temp_df["最高"] = pd.to_numeric(temp_df["最高"], errors="coerce")
temp_df["最低"] = pd.to_numeric(temp_df["最低"], errors="coerce")
temp_df["成交量"] = pd.to_numeric(temp_df["成交量"], errors="coerce")
temp_df["成交额"] = pd.to_numeric(temp_df["成交额"], errors="coerce")
return temp_df
def fund_etf_hist_sina(symbol: str = "sh510050") -> pd.DataFrame:
"""
新浪财经-基金-ETF 基金-日行情数据
https://finance.sina.com.cn/fund/quotes/159996/bc.shtml
:param symbol: 基金名称, 可以通过 ak.fund_etf_category_sina() 函数获取
:type symbol: str
:return: 日行情数据
:rtype: pandas.DataFrame
"""
url = (
f"https://finance.sina.com.cn/realstock/company/{symbol}/hisdata_klc2/klc_kl.js"
)
r = requests.get(url)
js_code = py_mini_racer.MiniRacer()
js_code.eval(hk_js_decode)
dict_list = js_code.call(
"d", r.text.split("=")[1].split(";")[0].replace('"', "")
) # 执行js解密代码
temp_df = pd.DataFrame(dict_list)
if temp_df.empty: # 处理获取数据为空的问题
return pd.DataFrame()
temp_df["date"] = pd.to_datetime(temp_df["date"], errors="coerce").dt.tz_localize(
None
)
temp_df["open"] = pd.to_numeric(temp_df["open"], errors="coerce")
temp_df["high"] = pd.to_numeric(temp_df["high"], errors="coerce")
temp_df["low"] = pd.to_numeric(temp_df["low"], errors="coerce")
temp_df["close"] = pd.to_numeric(temp_df["close"], errors="coerce")
temp_df["volume"] = pd.to_numeric(temp_df["volume"], errors="coerce")
# 转换日期列为日期类型
temp_df["date"] = temp_df["date"].dt.date
temp_df = temp_df.sort_values(by="date", ascending=True)
return temp_df
def fund_etf_dividend_sina(symbol: str = "sh510050") -> pd.DataFrame:
"""
新浪财经-基金-ETF 基金-累计分红
https://finance.sina.com.cn/fund/quotes/510050/bc.shtml
:param symbol: 基金名称, 可以通过 ak.fund_etf_category_sina() 函数获取
:type symbol: str
:return: 累计分红
:rtype: pandas.DataFrame
"""
# 构建复权数据URL
factor_url = f"https://finance.sina.com.cn/realstock/company/{symbol}/hfq.js"
r = requests.get(factor_url)
text = r.text
if text.startswith("var"):
json_str = text.split("=")[1].strip().rsplit("}", maxsplit=1)[0].strip()
data = eval(json_str + "}") # 这里使用eval而不是json.loads因为数据格式特殊
if isinstance(data, dict) and "data" in data:
df = pd.DataFrame(data["data"])
# 重命名列
df.columns = ["date", "f", "s", "u"] if len(df.columns) == 4 else df.columns
# 移除1900-01-01的数据
df = df[df["date"] != "1900-01-01"]
# 转换日期
df["date"] = pd.to_datetime(df["date"])
# 转换数值类型
df[["f", "s", "u"]] = df[["f", "s", "u"]].astype(float)
# 按日期排序
df = df.sort_values(by="date", ascending=True, ignore_index=True)
temp_df = df[["date", "u"]].copy()
temp_df.columns = ["日期", "累计分红"]
temp_df["日期"] = pd.to_datetime(temp_df["日期"], errors="coerce").dt.date
return temp_df
else:
return pd.DataFrame()
else:
return pd.DataFrame()
if __name__ == "__main__":
fund_etf_category_sina_df = fund_etf_category_sina(symbol="封闭式基金")
print(fund_etf_category_sina_df)
fund_etf_category_sina_df = fund_etf_category_sina(symbol="ETF基金")
print(fund_etf_category_sina_df)
fund_etf_category_sina_df = fund_etf_category_sina(symbol="LOF基金")
print(fund_etf_category_sina_df)
fund_etf_hist_sina_df = fund_etf_hist_sina(symbol="sh510050")
print(fund_etf_hist_sina_df)
fund_etf_dividend_sina_df = fund_etf_dividend_sina(symbol="sh510050")
print(fund_etf_dividend_sina_df)
@@ -0,0 +1,71 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/1/20 15:00
Desc: 上海证券交易所-ETF基金份额数据
https://www.sse.com.cn/assortment/fund/etf/list/scale/
"""
import pandas as pd
import requests
def fund_etf_scale_sse(date: str = "20250115") -> pd.DataFrame:
"""
上海证券交易所-产品-基金产品-ETF产品-ETF产品列表-基金规模
https://www.sse.com.cn/assortment/fund/etf/list/scale/
:param date: 统计日期, 默认为空返回最新数据, 格式如 "20250115"
:type date: str
:return: ETF基金份额数据
:rtype: pandas.DataFrame
"""
data_str = "-".join([date[:4], date[4:6], date[6:]])
url = "https://query.sse.com.cn/commonQuery.do"
params = {
"isPagination": "true",
"pageHelp.pageSize": "10000",
"pageHelp.pageNo": "1",
"pageHelp.beginPage": "1",
"pageHelp.cacheSize": "1",
"pageHelp.endPage": "1",
"sqlId": "COMMON_SSE_ZQPZ_ETFZL_XXPL_ETFGM_SEARCH_L",
"STAT_DATE": data_str,
}
headers = {
"Referer": "https://www.sse.com.cn/",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/88.0.4324.150 Safari/537.36",
}
r = requests.get(url, params=params, headers=headers)
data_json = r.json()
temp_df = pd.DataFrame(data_json["result"])
temp_df.rename(
columns={
"NUM": "序号",
"SEC_CODE": "基金代码",
"SEC_NAME": "基金简称",
"ETF_TYPE": "ETF类型",
"STAT_DATE": "统计日期",
"TOT_VOL": "基金份额",
},
inplace=True,
)
temp_df = temp_df[
[
"序号",
"基金代码",
"基金简称",
"ETF类型",
"统计日期",
"基金份额",
]
]
temp_df["序号"] = pd.to_numeric(temp_df["序号"], errors="coerce")
temp_df["统计日期"] = pd.to_datetime(temp_df["统计日期"], errors="coerce").dt.date
temp_df["基金份额"] = pd.to_numeric(temp_df["基金份额"], errors="coerce") * 10000
return temp_df
if __name__ == "__main__":
fund_etf_scale_sse_df = fund_etf_scale_sse(date="20250115")
print(fund_etf_scale_sse_df)
@@ -0,0 +1,69 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/1/20 15:00
Desc: 深圳证券交易所-ETF基金份额数据
https://fund.szse.cn/marketdata/fundslist/index.html
"""
import warnings
import pandas as pd
import requests
def fund_etf_scale_szse() -> pd.DataFrame:
"""
深圳证券交易所-基金产品-基金列表-ETF基金份额
https://fund.szse.cn/marketdata/fundslist/index.html
:return: ETF基金份额数据
:rtype: pandas.DataFrame
"""
url = "https://fund.szse.cn/api/report/ShowReport"
params = {
"SHOWTYPE": "xlsx",
"CATALOGID": "1000_lf",
"TABKEY": "tab1",
"random": "0.07610353191740105",
}
headers = {
"Referer": "https://fund.szse.cn/marketdata/fundslist/index.html",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
"Chrome/88.0.4324.150 Safari/537.36",
}
r = requests.get(url, params=params, headers=headers)
with warnings.catch_warnings(record=True):
warnings.simplefilter("always")
temp_df = pd.read_excel(r.content, engine="openpyxl", dtype={"基金代码": str})
temp_df.rename(
columns={
"当前规模(份)": "基金份额",
},
inplace=True,
)
temp_df = temp_df[
[
"基金代码",
"基金简称",
"基金类别",
"投资类别",
"上市日期",
"基金份额",
"基金管理人",
"基金发起人",
"基金托管人",
"净值",
]
]
temp_df["上市日期"] = pd.to_datetime(temp_df["上市日期"], errors="coerce").dt.date
temp_df["基金份额"] = (
temp_df["基金份额"].astype(str).str.replace(",", "", regex=False)
)
temp_df["基金份额"] = pd.to_numeric(temp_df["基金份额"], errors="coerce")
temp_df["净值"] = pd.to_numeric(temp_df["净值"], errors="coerce")
return temp_df
if __name__ == "__main__":
fund_etf_scale_szse_df = fund_etf_scale_szse()
print(fund_etf_scale_szse_df)
@@ -0,0 +1,151 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/2/10 16:00
Desc: 同花顺理财-基金数据-每日净值-ETF
https://fund.10jqka.com.cn/datacenter/jz/kfs/etf/
"""
import json
import pandas as pd
import requests
def fund_etf_category_ths(symbol: str = "ETF", date: str = "") -> pd.DataFrame:
"""
同花顺理财-基金数据-每日净值-实时行情
https://fund.10jqka.com.cn/datacenter/jz/
:param symbol: 基金类型; choice of {"股票型", "债券型", "混合型", "ETF", "LOF", "QDII", "保本型", "指数型", ""}; "" 表示全部
:type symbol: str
:param date: 查询日期
:type date: str
:return: 基金实时行情
:rtype: pandas.DataFrame
"""
symbol_map = {
"股票型": "gpx",
"债券型": "zqx",
"混合型": "hhx",
"ETF": "ETF",
"LOF": "LOF",
"QDII": "QDII",
"保本型": "bbx",
"指数型": "zsx",
"": "all",
}
inner_symbol = symbol_map.get(symbol, "ETF")
inner_date = "-".join([date[:4], date[4:6], date[6:]]) if date != "" else 0
url = (
f"https://fund.10jqka.com.cn/data/Net/info/"
f"{inner_symbol}_rate_desc_{inner_date}_0_1_9999_0_0_0_jsonp_g.html"
)
r = requests.get(url, timeout=15)
data_text = r.text[2:-1]
data_json = json.loads(data_text)
temp_df = pd.DataFrame(data_json["data"]["data"]).T
temp_df.reset_index(inplace=True, drop=True)
temp_df.reset_index(inplace=True)
temp_df["index"] = temp_df["index"] + 1
temp_df.rename(
columns={
"index": "序号",
"code": "基金代码",
"typename": "基金类型",
"net": "当前-单位净值",
"name": "基金名称",
"totalnet": "当前-累计净值",
"newnet": "最新-单位净值",
"newtotalnet": "最新-累计净值",
"newdate": "最新-交易日",
"net1": "前一日-单位净值",
"totalnet1": "前一日-累计净值",
"ranges": "增长值",
"rate": "增长率",
"shstat": "赎回状态",
"sgstat": "申购状态",
},
inplace=True,
)
temp_df = temp_df[
[
"序号",
"基金代码",
"基金名称",
"当前-单位净值",
"当前-累计净值",
"前一日-单位净值",
"前一日-累计净值",
"增长值",
"增长率",
"赎回状态",
"申购状态",
"最新-交易日",
"最新-单位净值",
"最新-累计净值",
"基金类型",
]
]
query_date = inner_date if inner_date != 0 else temp_df["最新-交易日"][0]
temp_df["查询日期"] = query_date
temp_df["查询日期"] = pd.to_datetime(temp_df["查询日期"], errors="coerce").dt.date
temp_df["当前-单位净值"] = pd.to_numeric(temp_df["当前-单位净值"], errors="coerce")
temp_df["当前-累计净值"] = pd.to_numeric(temp_df["当前-累计净值"], errors="coerce")
temp_df["前一日-单位净值"] = pd.to_numeric(
temp_df["前一日-单位净值"], errors="coerce"
)
temp_df["前一日-累计净值"] = pd.to_numeric(
temp_df["前一日-累计净值"], errors="coerce"
)
temp_df["增长值"] = pd.to_numeric(temp_df["增长值"], errors="coerce")
temp_df["增长率"] = pd.to_numeric(temp_df["增长率"], errors="coerce")
temp_df["最新-单位净值"] = pd.to_numeric(temp_df["最新-单位净值"], errors="coerce")
temp_df["最新-累计净值"] = pd.to_numeric(temp_df["最新-累计净值"], errors="coerce")
temp_df["最新-交易日"] = pd.to_datetime(
temp_df["最新-交易日"], errors="coerce"
).dt.date
return temp_df
def fund_etf_spot_ths(date: str = "") -> pd.DataFrame:
"""
同花顺理财-基金数据-每日净值-ETF-实时行情
https://fund.10jqka.com.cn/datacenter/jz/kfs/etf/
:param date: 查询日期
:type date: str
:return: ETF 实时行情
:rtype: pandas.DataFrame
"""
return fund_etf_category_ths(date=date, symbol="ETF")
if __name__ == "__main__":
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="股票型")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="债券型")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="混合型")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="ETF")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="LOF")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="QDII")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="保本型")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="指数型")
print(fund_etf_category_ths_df)
fund_etf_category_ths_df = fund_etf_category_ths(date="20240620", symbol="")
print(fund_etf_category_ths_df)
fund_etf_spot_ths_df = fund_etf_spot_ths(date="20240620")
print(fund_etf_spot_ths_df)
@@ -0,0 +1,167 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2025/12/22 17:00
Desc: 天天基金-基金档案
https://fundf10.eastmoney.com/jjfl_015641.html
"""
import re
from io import StringIO
import pandas as pd
import requests
from bs4 import BeautifulSoup
def fund_fee_em(symbol: str = "015641", indicator: str = "认购费率") -> pd.DataFrame:
"""
天天基金-基金档案-购买信息
https://fundf10.eastmoney.com/jjfl_015641.html
:param symbol: 基金代码
:type symbol: str
:param indicator: choice of {"交易状态", "申购与赎回金额", "交易确认日", "运作费用", "认购费率(前端)", "认购费率(后端)","申购费率(前端)", "赎回费率"}
:type indicator: str
:return: 交易规则
:rtype: pandas.DataFrame
"""
url = f"https://fundf10.eastmoney.com/jjfl_{symbol}.html"
r = requests.get(url)
soup = BeautifulSoup(r.text, features="html.parser")
tables_dict = {}
title_elements = soup.find_all(name="h4", class_="t")
for title_elem in title_elements:
title_text = title_elem.get_text(strip=True)
title_text = re.sub(r"\s+", " ", title_text).strip()
if title_text == "申购与赎回金额":
next_table = title_elem.find_all_next("table")[0]
next_next_table = title_elem.find_all_next("table")[1]
table_html = str(next_table)
next_table_html = str(next_next_table)
df_1 = pd.read_html(StringIO(table_html))[0]
df_2 = pd.read_html(StringIO(next_table_html))[0]
df = pd.concat(objs=[df_1, df_2], ignore_index=True)
tables_dict[title_text] = df
continue
else:
next_table = title_elem.find_next("table")
if next_table:
try:
# 将表格转换为HTML字符串,然后使用pd.read_html读取
table_html = str(next_table)
df = pd.read_html(StringIO(table_html))[0]
tables_dict[title_text] = df
except Exception as e:
print("Error:", e)
continue
if indicator == "交易状态":
temp_df = tables_dict[indicator]
elif indicator == "申购与赎回金额":
temp_df = tables_dict[indicator]
elif indicator == "交易确认日":
temp_df = tables_dict[indicator]
elif indicator == "运作费用":
temp_df = tables_dict[indicator]
elif indicator == "认购费率(后端)":
temp_df = tables_dict[indicator]
elif indicator == "认购费率(前端)":
temp_df = tables_dict[indicator]
temp_df[["原费率", "天天基金优惠费率"]] = temp_df[
"原费率|天天基金优惠费率"
].str.split("|", expand=True)
del temp_df["原费率|天天基金优惠费率"]
temp_df.loc[3, "天天基金优惠费率"] = temp_df.loc[3, "原费率"]
temp_df["原费率"] = temp_df["原费率"].str.strip()
temp_df["天天基金优惠费率"] = temp_df["天天基金优惠费率"].str.strip()
elif indicator == "申购费率(前端)":
temp_df = tables_dict[indicator]
if "原费率|天天基金优惠费率 银行卡购买|活期宝购买" not in temp_df.columns:
# assert temp_df.columns.tolist() == ["适用金额", "适用期限", "费率"]
return temp_df
splited = temp_df["原费率|天天基金优惠费率 银行卡购买|活期宝购买"].str.split(
"|", expand=True
)
if splited.shape[1] == 1:
temp_df.rename(
columns={"原费率|天天基金优惠费率 银行卡购买|活期宝购买": "原费率"},
inplace=True,
)
temp_df["天天基金优惠费率-银行卡购买"] = temp_df["原费率"]
temp_df["天天基金优惠费率-活期宝购买"] = temp_df["原费率"]
else:
temp_df[
["原费率", "天天基金优惠费率-银行卡购买", "天天基金优惠费率-活期宝购买"]
] = splited
temp_df["天天基金优惠费率-银行卡购买"] = temp_df[
"天天基金优惠费率-银行卡购买"
].fillna(temp_df["原费率"])
temp_df["天天基金优惠费率-活期宝购买"] = temp_df[
"天天基金优惠费率-活期宝购买"
].fillna(temp_df["原费率"])
del temp_df["原费率|天天基金优惠费率 银行卡购买|活期宝购买"]
temp_df["原费率"] = temp_df["原费率"].str.strip()
temp_df["天天基金优惠费率-银行卡购买"] = temp_df[
"天天基金优惠费率-银行卡购买"
].str.strip()
temp_df["天天基金优惠费率-活期宝购买"] = temp_df[
"天天基金优惠费率-活期宝购买"
].str.strip()
elif indicator in ("赎回费率", "赎回费率(前端)", "赎回费率(后端)"):
temp_df = tables_dict[indicator]
if "原费率|天天基金优惠费率" in temp_df.columns:
temp_df[["原费率", "天天基金优惠费率"]] = temp_df[
"原费率|天天基金优惠费率"
].str.split("|", expand=True)
del temp_df["原费率|天天基金优惠费率"]
else:
temp_df = pd.DataFrame([])
return temp_df
if __name__ == "__main__":
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="交易状态")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="申购与赎回金额")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="交易确认日")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="运作费用")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="认购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="019005", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="000011", indicator="赎回费率")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="018403", indicator="赎回费率")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="100035", indicator="赎回费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="022364", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="022365", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="006030", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="022568", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="960029", indicator="申购费率(前端)")
print(fund_fee_em_df)
fund_fee_em_df = fund_fee_em(symbol="000011", indicator="认购费率(后端)")
print(fund_fee_em_df)
@@ -0,0 +1,263 @@
# -*- coding:utf-8 -*-
# !/usr/bin/env python
"""
Date: 2026/2/22 13:00
Desc: 天天基金网-基金数据-分红送配
https://fund.eastmoney.com/data/fundfenhong.html
"""
import pandas as pd
import requests
from akshare.utils.tqdm import get_tqdm
def fund_fh_em(
year: str = "2025",
typ: str = "",
rank: str = "BZDM",
sort: str = "asc",
page: int = -1,
) -> pd.DataFrame:
"""
天天基金网-基金数据-分红送配-基金分红
https://fund.eastmoney.com/data/fundfenhong.html#DJR,desc,1,,,
:param year: 查询年份
:type year: str
:param typ: 基金类型空串表示全部; choice of {"指数型-其他", "指数型-海外股票", "指数型-固收", "指数型-股票", "债券型-中短债",
"债券型-长债", "债券型-理财", "债券型-混合债", "债券型-混合一级", "债券型-混合二级", "货币型-普通货币", "货币型-浮动净值",
"混合型-平衡", "混合型-偏债", "混合型-偏股", "混合型-灵活", "混合型-绝对收益", "股票型", "REITs", "Reits", "QDII-商品",
"QDII-普通股票", "QDII-混合债", "QDII-混合偏股", "QDII-纯债", "QDII-REITs", "FOF"}
:type typ: str
:param rank: 排序字段choice of {"BZDM", "ABBNAME", "DJR", "FSRQ", "FHFCZ", "FFR"}; "BZDM": 基金代码,
"ABBNAME": 基金简称, "DJR": 权益登记日, "FSRQ": 除息日期, "FHFCZ": 分红(/), "FFR": 分红发放日
:type rank: str
:param sort: 排序方向排序方式; choice of {"asc", "desc"}
:type sort: str
:param page: 查询页数请求第page页数据; -1 表示全部页面
:type page: int
:return: 基金分红
:rtype: pandas.DataFrame
"""
def get_df_from_response(response):
text = response.text
return pd.DataFrame(eval(text[text.find("[["): text.find(";var jjfh_jjgs")]))
url = "https://fund.eastmoney.com/Data/funddataIndex_Interface.aspx"
params = {
"dt": "8",
"page": "1" if page == -1 else str(page),
"rank": rank,
"sort": sort,
"gs": "",
"ftype": typ,
"year": year,
}
r = requests.get(url, params=params)
data_list = [get_df_from_response(r)]
if page == -1:
data_text = r.text
total_page = eval(data_text[data_text.find("=") + 1: data_text.find(";")])[0]
tqdm = get_tqdm()
for p in tqdm(range(2, total_page + 1), leave=False):
params.update({"page": str(p)})
r = requests.get(url, params=params)
data_list.append(get_df_from_response(r))
big_df = pd.concat(objs=data_list, ignore_index=True)
big_df.reset_index(inplace=True)
big_df["index"] = big_df.index + 1
# 处理空数据时报错的问题
if big_df.empty:
big_df = big_df.reindex(
columns=[
"序号",
"基金代码",
"基金简称",
"权益登记日",
"除息日期",
"分红",
"分红发放日",
"-",
]
)
big_df.columns = [
"序号",
"基金代码",
"基金简称",
"权益登记日",
"除息日期",
"分红",
"分红发放日",
"-",
]
big_df = big_df[
["序号", "基金代码", "基金简称", "权益登记日", "除息日期", "分红", "分红发放日"]
]
big_df["权益登记日"] = pd.to_datetime(big_df["权益登记日"]).dt.date
big_df["除息日期"] = pd.to_datetime(big_df["除息日期"]).dt.date
big_df["分红发放日"] = pd.to_datetime(big_df["分红发放日"]).dt.date
big_df["分红"] = pd.to_numeric(big_df["分红"])
return big_df
def fund_cf_em(
year: str = "2025",
typ: str = "",
rank: str = "FSRQ",
sort: str = "desc",
page: int = -1,
) -> pd.DataFrame:
"""
天天基金网-基金数据-分红送配-基金拆分
https://fund.eastmoney.com/data/fundchaifen.html#FSRQ,desc,1,,,
:param year: 查询年份
:type year: str
:param typ: 基金类型空串表示全部; choice of {"", "指数型-其他", "指数型-海外股票", "指数型-固收", "指数型-股票",
"债券型-中短债", "债券型-长债", "债券型-可转债", "债券型-混合债", "债券型-混合一级", "债券型-混合二级",
"商品(不含QDII", "货币型", "混合型-平衡", "混合型-偏债", "混合型-偏股", "混合型-灵活", "股票型", "QDII", "FOF"}
:type typ: str
:param rank: 排序字段choice of {"BZDM", "ABBNAME", "FSRQ", "FHFCZ"}; "BZDM": 基金代码,
"ABBNAME": 基金简称, "FSRQ": 拆分折算日, "FHFCZ": 拆分折算(每份)
:type rank: str
:param sort: 排序方向choice of {"asc", "desc"}
:type sort: str
:param page: 查询页数请求第page页数据; -1 表示全部页面
:type page: int
:return: 基金拆分
:rtype: pandas.DataFrame
"""
def get_df_from_response(response):
text = response.text
code = text[text.find("[["): text.find(";var jjcf_jjgs")]
if code:
return pd.DataFrame(eval(code))
return pd.DataFrame()
url = "https://fund.eastmoney.com/Data/funddataIndex_Interface.aspx"
params = {
"dt": "9",
"page": "1" if page == -1 else str(page),
"rank": rank,
"sort": sort,
"gs": "",
"ftype": typ,
"year": year,
}
r = requests.get(url, params=params)
data_list = [get_df_from_response(r)]
if page == -1:
data_text = r.text
total_page = eval(data_text[data_text.find("=") + 1: data_text.find(";")])[0]
tqdm = get_tqdm()
for p in tqdm(range(2, total_page + 1), leave=False):
params.update({"page": str(p)})
r = requests.get(url, params=params)
data_list.append(get_df_from_response(r))
big_df = pd.concat(objs=data_list, ignore_index=True)
big_df.reset_index(inplace=True)
big_df.loc[:, "index"] = big_df["index"] + 1
# 处理空数据时报错的问题
if big_df.empty:
big_df = big_df.reindex(
columns=[
"序号",
"基金代码",
"基金简称",
"拆分折算日",
"拆分类型",
"拆分折算",
"-",
]
)
big_df.columns = [
"序号",
"基金代码",
"基金简称",
"拆分折算日",
"拆分类型",
"拆分折算",
"-",
]
big_df = big_df[
["序号", "基金代码", "基金简称", "拆分折算日", "拆分类型", "拆分折算"]
]
big_df["拆分折算日"] = pd.to_datetime(big_df["拆分折算日"]).dt.date
big_df["拆分折算"] = pd.to_numeric(big_df["拆分折算"], errors="coerce")
return big_df
def fund_fh_rank_em() -> pd.DataFrame:
"""
天天基金网-基金数据-分红送配-基金分红排行
https://fund.eastmoney.com/data/fundleijifenhong.html
:return: 基金分红排行
:rtype: pandas.DataFrame
"""
url = "https://fund.eastmoney.com/Data/funddataIndex_Interface.aspx"
params = {
"dt": "10",
"page": "1",
"rank": "FHFCZ",
"sort": "desc",
"gs": "",
"ftype": "",
}
r = requests.get(url, params=params)
data_text = r.text
total_page = eval(data_text[data_text.find("=") + 1: data_text.find(";")])[0]
big_df = pd.DataFrame()
tqdm = get_tqdm()
for page in tqdm(range(1, total_page + 1), leave=False):
params.update({"page": str(page)})
r = requests.get(url, params=params)
data_text = r.text
temp_list = eval(
data_text[data_text.find("[["): data_text.find(";var fhph_jjgs")]
)
temp_df = pd.DataFrame(temp_list)
big_df = pd.concat(objs=[big_df, temp_df], ignore_index=True)
big_df.reset_index(inplace=True)
big_df["index"] = big_df.index + 1
# 处理空数据时报错的问题
if big_df.empty:
big_df = big_df.reindex(
columns=[
"序号",
"基金代码",
"基金简称",
"累计分红",
"累计次数",
"成立日期",
"-",
]
)
big_df.columns = [
"序号",
"基金代码",
"基金简称",
"累计分红",
"累计次数",
"成立日期",
"-",
]
big_df = big_df[
["序号", "基金代码", "基金简称", "累计分红", "累计次数", "成立日期"]
]
big_df["成立日期"] = pd.to_datetime(big_df["成立日期"]).dt.date
big_df["累计分红"] = pd.to_numeric(big_df["累计分红"], errors="coerce")
big_df["累计次数"] = pd.to_numeric(big_df["累计次数"], errors="coerce")
return big_df
if __name__ == "__main__":
fund_fh_em_df = fund_fh_em(year="2025")
print(fund_fh_em_df)
fund_cf_em_df = fund_cf_em(year="2025")
print(fund_cf_em_df)
fund_fh_rank_em_df = fund_fh_rank_em()
print(fund_fh_rank_em_df)
@@ -0,0 +1,54 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2026/05/01
Desc: 同花顺-基金基本信息
https://fund.10jqka.com.cn/161130/interduce.html
"""
import pandas as pd
import requests
from bs4 import BeautifulSoup
from akshare.utils.cons import headers
def fund_info_ths(symbol: str = "161130") -> pd.DataFrame:
"""
同花顺-基金数据-基金基本信息
https://fund.10jqka.com.cn/161130/interduce.html
:param symbol: 基金代码
:type symbol: str
:return: 基金基本信息
:rtype: pandas.DataFrame
"""
url = f"https://fund.10jqka.com.cn/{symbol}/interduce.html"
r = requests.get(url, headers=headers, timeout=15)
soup = BeautifulSoup(r.content, features="lxml", from_encoding="utf-8")
# 查找基金信息对话框
g_dialog = soup.find("ul", class_="g-dialog")
if not g_dialog:
raise ValueError("未找到基金信息,可能网页结构已变化")
# 提取所有基金信息
fund_data = {}
lis = g_dialog.find_all("li")
for li in lis:
key_elem = li.find("span", class_="key")
value_elem = li.find("span", class_="value")
if key_elem and value_elem:
key = key_elem.get_text(strip=True)
value = value_elem.get_text(strip=True)
fund_data[key] = value
# 转换为DataFrame
temp_df = pd.DataFrame(list(fund_data.items()), columns=["字段", ""])
return temp_df
if __name__ == "__main__":
# 测试获取基金基本信息
fund_info_ths_df = fund_info_ths(symbol="161130")
print(fund_info_ths_df)
@@ -0,0 +1,83 @@
#!/usr/bin/env python
# -*- coding:utf-8 -*-
"""
Date: 2023/11/7 18:30
Desc: 基金数据-新发基金-新成立基金
https://fund.eastmoney.com/data/xinfound.html
"""
import pandas as pd
import requests
from akshare.utils import demjson
def fund_new_found_em() -> pd.DataFrame:
"""
基金数据-新发基金-新成立基金
https://fund.eastmoney.com/data/xinfound.html
:return: 新成立基金
:rtype: pandas.DataFrame
"""
url = "https://fund.eastmoney.com/data/FundNewIssue.aspx"
params = {
"t": "xcln",
"sort": "jzrgq,desc",
"y": "",
"page": "1,50000",
"isbuy": "1",
"v": "0.4069919776543214",
}
r = requests.get(url, params=params)
data_text = r.text
data_json = demjson.decode(data_text.strip("var newfunddata="))
temp_df = pd.DataFrame(data_json["datas"])
temp_df.columns = [
"基金代码",
"基金简称",
"发行公司",
"_",
"基金类型",
"募集份额",
"成立日期",
"成立来涨幅",
"基金经理",
"申购状态",
"集中认购期",
"_",
"_",
"_",
"_",
"_",
"_",
"_",
"优惠费率",
]
temp_df = temp_df[
[
"基金代码",
"基金简称",
"发行公司",
"基金类型",
"集中认购期",
"募集份额",
"成立日期",
"成立来涨幅",
"基金经理",
"申购状态",
"优惠费率",
]
]
temp_df["募集份额"] = pd.to_numeric(temp_df["募集份额"], errors="coerce")
temp_df["成立日期"] = pd.to_datetime(temp_df["成立日期"], errors="coerce").dt.date
temp_df["成立来涨幅"] = pd.to_numeric(
temp_df["成立来涨幅"].str.replace(",", ""), errors="coerce"
)
temp_df["优惠费率"] = temp_df["优惠费率"].str.strip("%")
temp_df["优惠费率"] = pd.to_numeric(temp_df["优惠费率"], errors="coerce")
return temp_df
if __name__ == "__main__":
fund_new_found_em_df = fund_new_found_em()
print(fund_new_found_em_df)

Some files were not shown because too many files have changed in this diff Show More