pip install aliyun-python-sdk-ecs==4.24.13
pip install aliyun-python-sdk-slb==3.3.9
pip install aliyun-python-sdk-vpc==3.0.16
pip install aliyun-python-sdk-bssopenapi==2.0.3
pip install pandas
pip install xlrd
pip install openpyxl
#!/usr/bin/env python
# coding=utf-8
'''
Author: LJX
Date: 2022-01-06 16:31:14
LastEditors: LJX
LastEditTime: 2022-02-08 16:17:20
namespace: https://www.cnblogs.com/lanheader
Description: 计算流量使用情况
'''
from platform import platform
from aliyunsdkcore.client import AcsClient
from aliyunsdkcore.request import CommonRequest
from aliyunsdkcore.auth.credentials import AccessKeyCredential
from aliyunsdkcore.auth.credentials import StsTokenCredential
from aliyunsdkcore.acs_exception.exceptions import ClientException
from aliyunsdkcore.acs_exception.exceptions import ServerException
from aliyunsdkecs.request.v20140526.DescribeInstancesRequest import DescribeInstancesRequest
from aliyunsdkslb.request.v20140515.DescribeLoadBalancersRequest import DescribeLoadBalancersRequest
from aliyunsdkbssopenapi.request.v20171214.QueryDPUtilizationDetailRequest import QueryDPUtilizationDetailRequest
import csv
import os
import json
import pandas as pd
import time
import datetime
class ParseNetwork(object):
def __init__(self, filename=''):
self.filename = filename
def get_eip(self, postion):
"""
:调用阿里云接口获取弹性IP地址
:param page_size:
:return:弹性IP地址
"""
client = AcsClient(region_id=postion,
credential=self.credentials)
request = CommonRequest()
request.set_accept_format('json')
request.set_domain('vpc.aliyuncs.com')
request.set_method('POST')
request.set_protocol_type('https') # https | http
request.set_version('2016-04-28')
request.set_action_name('DescribeEipAddresses')
request.add_query_param('RegionId', postion)
request.add_query_param('PageNumber', "1")
request.add_query_param('PageSize', "100")
request.add_query_param('Status', "InUse")
response = client.do_action(request)
data = json.loads(str(response, encoding='utf-8')
)["EipAddresses"]['EipAddress']
return data
def parse_eip(self):
"""
:pandas格式化弹性ip数据
:param page_size:
:return:弹性IPpandas 对象
"""
data = []
for postion in self.positions:
restult = self.get_eip(postion)
# print(postion + ':{0}'.format(len(restult)))
data += restult
print("eip总长度:{0}".format(len(data)))
df = pd.DataFrame(data)
# 这里可写入execl进行查看数据
# df.to_excel('eip.xlsx', index=False)
df.set_index('AllocationId', inplace=True)
df.shape[0]
return df
def instances_count(self, postion, page_size=100):
"""
返回页码数量
:param page_size:
:return:
"""
# 创建 request,并设置参数
client = AcsClient(region_id=postion,
credential=self.credentials)
request = DescribeInstancesRequest()
request.set_PageSize(page_size)
# 发起 API 请求并打印返回
response = client.do_action_with_exception(request)
ret = json.loads(str(response, encoding='utf-8'))
# 页码
total_page, b = divmod(ret['TotalCount'], page_size)
if b:
total_page = total_page + 1
return total_page
def get_ecs(self, postion):
"""
:获取ecs信息
:param page_size:
:return:ecs信息
"""
client = AcsClient(region_id=postion,
credential=self.credentials)
total_page = self.instances_count(postion, page_size=100)
data = []
for page_num in range(1, total_page + 1):
request = DescribeInstancesRequest()
request.set_accept_format('json')
request.set_PageSize(100)
request.set_PageNumber(page_num)
response = client.do_action_with_exception(request)
data += json.loads(str(response, encoding='utf-8')
)["Instances"]["Instance"]
return data
def parse_ecs(self):
"""
:pandas格式化ecs信息
:param page_size:
:return:ecs格式化信息
"""
data = []
for postion in self.positions:
restult = self.get_ecs(postion)
data += restult
print("ecs总长度:{0}".format(len(data)))
df = pd.DataFrame(data)
# 这里可写入execl进行查看数据
# df.to_excel('ecs.xlsx', index=False)
df.set_index("InstanceId", inplace=True)
return df
def get_slb(self, postion):
"""
:获取slb信息
:param page_size:
:return:ecs信息
"""
client = AcsClient(region_id=postion,
credential=self.credentials)
request = DescribeLoadBalancersRequest()
request.set_accept_format('json')
response = client.do_action_with_exception(request)
data = json.loads(str(response, encoding='utf-8')
)["LoadBalancers"]["LoadBalancer"]
return data
def parse_slb(self):
"""
:pandas格式化slb数据
:param page_size:
:return:格式化slb数据
"""
data = []
for postion in self.positions:
restult = self.get_slb(postion)
data += restult
print("slb总长度:{0}".format(len(data)))
df = pd.DataFrame(data)
# 这里可写入execl进行查看数据
#df.to_excel('slb.xlsx', index=False)
df.set_index("LoadBalancerId", inplace=True)
return df
def main_eip(self, df_eip, df_ecs, eip):
"""
:清洗eip数据
:param page_size:
:return
"""
try:
if eip in df_eip.index:
instanceid = df_eip.loc[eip, "InstanceId"]
return "ECS+弹性IP:" + df_ecs.loc[instanceid, "InstanceName"]
else:
# print("未查到相关信息eip:{0}".format(eip))
return "未绑定弹性IP:{0}".format(eip)
except Exception as e:
print(e)
def main_slb(self, df_slb, i):
"""
:清洗slb数据
:param page_size:
:return
"""
return "SLB:" + df_slb.loc[i, "LoadBalancerName"]
def main_ecs(self, df_ecs, i):
"""
:清洗ecs数据
:param page_size:
:return
"""
return "ECS+公网IP:" + df_ecs.loc[i, "InstanceName"]
def get_data(self, postion, startTime, endTime, instance_id):
"""
:获取数据
:param page_size:
:return
"""
result = []
count_result = 0
count_once = 0
lastToken = None
while 1:
client = AcsClient(region_id=postion,
credential=self.credentials)
request = QueryDPUtilizationDetailRequest()
request.set_accept_format('json')
request.set_StartTime(startTime)
if lastToken is not None:
request.set_LastToken(lastToken)
request.set_EndTime(endTime)
request.set_IncludeShare(True)
request.set_InstanceId(instance_id)
request.set_Limit(300)
response = client.do_action_with_exception(request)
count_once += 1
lastToken = json.loads(str(response, encoding='utf-8')
)["Data"]["NextToken"]
result += json.loads(str(response, encoding='utf-8')
)["Data"]["DetailList"]["DetailList"]
count = len(json.loads(str(response, encoding='utf-8')
)["Data"]["DetailList"]["DetailList"])
count_result += count
print("当前{0} 次查询:{1}个,现在总数{2}".format(
str(count_once), str(count), str(count_result)))
if lastToken == "":
break
print("总条数共:{0}个".format(str(count_result)))
return result
def parse_source_data(self):
"""
:pandas 格式化数据源
:param page_size:
:return
"""
data = []
# startTime = "2021-7-1 00:00:00"
startTime = input("请输入查询起始时间,格式%Y-%m-%d %H:%M:%S :")
endTime = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
instance_id = input("请输入资源包ID:")
postion = "cn-shenzhen"
data = self.get_data(
postion, startTime, endTime, instance_id)
print("数据源总长度:{0}".format(len(data)))
df = pd.DataFrame(data)
return df
def main_api(self):
"""
:阿里云读取接口
:param page_size:
:return
"""
df = self.parse_source_data()
print('共使用:{0}GB'.format(
int(df.loc[:, 'DeductMeasure'].sum())/1024/1024/1024))
print('共剩余:{0}GB'.format(int(input("请输入流量包总量(单位TB):"))*1024 -
int(df.loc[:, 'DeductMeasure'].sum())/1024/1024/1024))
unit = input("请输入过滤单位(KB/MB/GB)")
if unit == "KB":
val = 1024
if unit == "MB":
val = 1024*1024
if unit == "GB":
val = 1024*1024*1024
df_eip = self.parse_eip()
df_ecs = self.parse_ecs()
df_slb = self.parse_slb()
restult = []
# 过滤弹性IP
for i in df.loc[df["DeductedProductDetail"] == "弹性公网IP(后付费)", 'DeductedInstanceId'].unique():
dic1 = {}
used1 = int(df.loc[df['DeductedInstanceId'] == i,
'DeductMeasure'].sum())/val
name1 = self.main_eip(df_eip, df_ecs, i)
if name1 == None:
name1 = i
if int(used1) != 0:
dic1["名称"] = name1
dic1["使用量"] = int(used1)
restult.append(dic1)
# 过滤 ecs
for i in df.loc[df["DeductedProductDetail"] == "云服务器ECS(包月)", 'DeductedInstanceId'].unique():
dic2 = {}
used2 = int(df.loc[df['DeductedInstanceId'] == i,
'DeductMeasure'].sum())/val
name2 = self.main_ecs(df_ecs, i)
if name2 == None:
name2 = i
if int(used2) != 0:
dic2["名称"] = name2
dic2["使用量"] = int(used2)
restult.append(dic2)
# 过滤 slb
for i in df.loc[df["DeductedProductDetail"] == "传统型负载均衡CLB(按量付费)", 'DeductedInstanceId'].unique():
dic3 = {}
used3 = int(df.loc[df['DeductedInstanceId'] == i,
'DeductMeasure'].sum())/val
name3 = self.main_slb(df_slb, i)
if name3 == None:
name3 = i
if int(used3) != 0:
dic3["名称"] = name3
dic3["使用量"] = int(used3)
restult.append(dic3)
result_data = pd.DataFrame(restult)
for index, row in result_data.sort_values(by='使用量', ascending=False).iterrows():
print("{0}:使用量为{1} {2}".format(row["名称"], row["使用量"], unit))
# 以下为读文件分析,非调用接口实现
# def main_file(self):
# """
# :阿里云读取文件
# :param page_size:
# :return
# """
# df = pd.read_csv(self.filename, encoding='utf-8')
# print('共使用:{0}GB'.format(
# int(df.loc[:, '使用量(原始单位)'].sum())/1024/1024/1024))
# print('共剩余:{0}GB'.format(int(input("请输入流量包总量:"))*1024 -
# int(df.loc[:, '使用量(原始单位)'].sum())/1024/1024/1024))
# df_eip = self.parse_eip()
# df_ecs = self.parse_ecs()
# df_slb = self.parse_slb()
# # 过滤弹性IP
# for i in df.loc[df["抵扣产品"] == "弹性公网IP", '抵扣实例ID'].unique():
# used = int(df.loc[df['抵扣实例ID'] == i,
# '使用量(原始单位)'].sum())/1024/1024/1024
# name = self.main_eip(df_eip, df_ecs, i)
# print("{0}:使用量为{1} GB".format(name, used))
# # 过滤 ecs
# for i in df.loc[df["抵扣产品"] == "云服务器ECS-包年包月", '抵扣实例ID'].unique():
# used = int(df.loc[df['抵扣实例ID'] == i,
# '使用量(原始单位)'].sum())/1024/1024/1024
# name = self.main_ecs(df_ecs, i)
# print("{0}:使用量为{1} GB".format(name, used))
# # 过滤 slb
# for i in df.loc[df["抵扣产品"] == "负载均衡", '抵扣实例ID'].unique():
# used = int(df.loc[df['抵扣实例ID'] == i,
# '使用量(原始单位)'].sum())/1024/1024/1024
# name = self.main_slb(df_slb, i)
# print("{0}:使用量为{1} GB".format(name, used))
def main(self):
"""
:主方法
:param page_size:
:return
"""
self.credentials = AccessKeyCredential(
'xxxxx', 'xxxxx')
self.positions = ['cn-shenzhen', 'cn-hongkong',
'cn-hangzhou', 'cn-chengdu', 'cn-qingdao'] # 这里可添加区域
self.main_api()
if __name__ == '__main__':
PN = ParseNetwork(
filename="xxxxx.csv")
PN.main()