136 lines
5.8 KiB
Python
136 lines
5.8 KiB
Python
import time
|
||
import datetime
|
||
import requests
|
||
import pandas as pd
|
||
from pathlib import Path
|
||
from bs4 import BeautifulSoup
|
||
import pandas as pd
|
||
import matplotlib.pyplot as plt
|
||
import matplotlib.dates as mdates
|
||
|
||
API_URL = "https://energy-iot.chinatowercom.cn/api/device/device/historyPerformance"
|
||
|
||
headers = {
|
||
"Accept-Encoding": "gzip, deflate, br, zstd",
|
||
"Connection": "keep-alive",
|
||
"Content-Length": "211",
|
||
"Cookie": "HWWAFSESTIME=1732173820506; HWWAFSESID=1739685743c73769ff; dc04ed2361044be8a9355f6efb378cf2=WyIzNTI0NjE3OTgzIl0",
|
||
"Host": "energy-iot.chinatowercom.cn",
|
||
"Origin": "https://energy-iot.chinatowercom.cn",
|
||
"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/131.0.0.0 Safari/537.36 Edg/131.0.0.0",
|
||
"accept": "application/json, text/plain, */*",
|
||
"accept-language": "zh-CN,zh;q=0.9,en;q=0.8,en-GB;q=0.7,en-US;q=0.6",
|
||
"authorization": "Bearer eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiIl0sInVzZXJfbmFtZSI6IndlYl9tYW5hZ2V8d2FuZ2xlaTQiLCJzY29wZSI6WyJhbGwiXSwiZXhwIjoxNzMyMjc4NDA5LCJ1c2VySWQiOjI0Mjg1LCJqdGkiOiJkODE0YTZhYy05YmJmLTQ0ZjQtYWRhYi0wMzAzNjUzNmNhNWIiLCJjbGllbnRfaWQiOiJ3ZWJfbWFuYWdlIn0.VhJaDKwzjekwOCsw_jOF_jvg7sX45okFcxkLyWtbfFVGWVWANhKNhVqj5Dn0Qb3wUXH3e-w74sDN1RI9QADngMOGP_H7aTwI_nukj6VmjpFA7kEtOBwa6ouvPZQMa1qa3UWl21Ac6GoLu14T4TIf4kQAMTdaYAMFrwDAXAkqvIDmKKjZbnDFUjUIcj-J_Y-LfHCEBjtcz7Rp_wMO-PMA5wII6kbcNoSFiYb0djcFQyeBcIUSUTRPixPcTYBkS-IhNrsOePIWlpNYMHbPxZdrZkV4M65BmBn4A9MUjWYHm7iIut8WVMdCXR4Sxp9m0mJHXR_IPWES4O7aBcuMkOmjyw",
|
||
"content-type": "application/json;charset=UTF-8",
|
||
"sec-ch-ua": "\"Microsoft Edge\";v=\"131\", \"Chromium\";v=\"131\", \"Not_A Brand\";v=\"24\"",
|
||
"sec-ch-ua-mobile": "?0",
|
||
"sec-ch-ua-platform": "Windows",
|
||
}
|
||
|
||
SemaMap = {
|
||
'apt_temp': ('0305117001', 'adapter', "设备温度"),
|
||
'apt_volt_in': ('0305118001', 'adapter', "输入电压"),
|
||
'apt_curr_in': ('0305119001', 'adapter', "输入电流"),
|
||
'apt_volt_out': ('0305120001', 'adapter', "输出电压"),
|
||
'apt_curr_out': ('0305121001', 'adapter', "输出电流"),
|
||
'apt_power_out': ('0305122001', 'adapter', "输出功率"),
|
||
}
|
||
|
||
def get_history_data(device_id, data_type, times: tuple[int, int]):
|
||
""" 读取信号量历史数据, 返回接口json数据 """
|
||
body = {
|
||
"startTimestamp": times[0],
|
||
"endTimestamp": times[1],
|
||
"deviceCode": f"{device_id}",
|
||
"mid": f"{data_type}",
|
||
"businessType": "7",
|
||
"pageNum": 2,
|
||
"pageSize": 5,
|
||
"total": 0
|
||
}
|
||
req = requests.post(API_URL, data=body, headers=headers)
|
||
return req.json()
|
||
|
||
def adapter_status_graphs(device_id, times: tuple[int, int]):
|
||
""" 获取数据, 绘制图表 """
|
||
data_volt_in = get_history_data(device_id, SemaMap["apt_volt_in"], times)
|
||
data_curr_in = get_history_data(device_id, SemaMap["apt_curr_in"], times)
|
||
data_volt_out = get_history_data(device_id, SemaMap["apt_volt_out"], times)
|
||
data_power_out = get_history_data(device_id, SemaMap["apt_power_out"], times)
|
||
|
||
data_apt = []
|
||
for item in zip(data_volt_in['data'], data_volt_out['data'], data_curr_in['data'], data_power_out['data']):
|
||
print(item)
|
||
piont_time = time.mktime(time.strptime(item[0]['collectTime'], r"%Y-%m-%d %H:%M:%S"))
|
||
point_apt = {
|
||
'time': int(piont_time),
|
||
'volt_in': item[0]['value'],
|
||
'volt_out': item[1]['value'],
|
||
'curr_in': item[2]['value'],
|
||
'power_out': item[3]['value'],
|
||
}
|
||
data_apt.append(point_apt)
|
||
table_apt = pd.DataFrame(data_apt)
|
||
|
||
# 图表绘制
|
||
chart_apt(table_apt)
|
||
|
||
def chart_apt(table_apt):
|
||
""" 绘制适配器信息图表 """
|
||
fig, ax1 = plt.subplots(figsize=(12, 6))
|
||
ax1.plot(table_apt['time'], table_apt['volt_in'], color='green', label='Input Voltage')
|
||
ax1.plot(table_apt['time'], table_apt['volt_out'], color='red', label='Output Voltage')
|
||
# ax1.xaxis.set_major_formatter(mdates.DateFormatter('%Y-%m-%d %H:%M:%S'))
|
||
|
||
# 设置x轴的主要刻度定位器为自动日期定位器,这使得x轴上的刻度根据数据自动选择最合适的日期格式
|
||
ax1.xaxis.set_major_locator(mdates.AutoDateLocator())
|
||
|
||
ax2 = ax1.twinx()
|
||
# 绘制斜线阴影
|
||
for i in range(len(table_apt) - 1):
|
||
ax1.fill_between(
|
||
[table_apt['time'].iloc[i], table_apt['time'].iloc[i + 1]],
|
||
[table_apt['power_out'].iloc[i], table_apt['power_out'].iloc[i + 1]],
|
||
color='red', alpha=0.5)
|
||
|
||
lines, labels = ax1.get_legend_handles_labels()
|
||
shadows, shadow_labels = ax2.get_legend_handles_labels()
|
||
ax1.legend(lines + shadows, labels + shadow_labels, loc='upper left')
|
||
|
||
ax1.set_title('Device Data Visualization')
|
||
ax1.set_xlabel('Time')
|
||
ax1.set_ylabel('Voltage (V)')
|
||
ax2.set_ylabel('Power (W)')
|
||
|
||
plt.show()
|
||
|
||
def sim_data_apt(times:tuple[int, int]):
|
||
""" 模拟数据 """
|
||
t_start = time.mktime(time.strptime(times[0], r"%Y-%m-%d %H:%M:%S"))
|
||
t_end = time.mktime(time.strptime(times[1], r"%Y-%m-%d %H:%M:%S"))
|
||
count_data = (t_end - t_start) / (10 * 60)
|
||
time_list = range(int(t_start), int(t_end), 20 * 60)
|
||
time_list = tuple(map(lambda x: time.strftime(r"%Y-%m-%d %H:%M:%S", time.localtime(x)), time_list))
|
||
data = {
|
||
'time': time_list,
|
||
'volt_in': 10 + 10 * np.random.random(len(time_list)),
|
||
'curr_in': 1 + 2 * np.random.random(len(time_list)),
|
||
'volt_out': 54 + 2 * np.random.random(len(time_list)),
|
||
}
|
||
data['power_out'] = tuple(map(lambda x: x[0] * x[1], zip(data['volt_in'],data['curr_in'])))
|
||
|
||
return pd.DataFrame(data)
|
||
|
||
if __name__=='__main__':
|
||
import numpy as np
|
||
|
||
data = sim_data_apt(('2024-10-1 00:00:00', '2024-10-1 12:00:00'))
|
||
|
||
chart_apt(data)
|
||
|
||
plt.waitforbuttonpress()
|
||
|
||
pass |