import uuid from datetime import datetime from typing import Dict, List, Tuple from alibabacloud_rds20140815.client import Client as RDSClient from alibabacloud_rds20140815.models import DescribeDBInstancesResponseBodyItemsDBInstance, DescribeDBInstancesRequest, DescribeDBInstanceAttributeRequest, \ DescribeDBInstanceAttributeResponseBodyItemsDBInstanceAttribute from alibabacloud_tea_openapi import models from resource.enums.region import Region from resource.enums.resource import Resource from resource.monitor.basic_monitor import BasicMonitor from resource.utils import * instance_type_map = { "Primary": "主实例", "Readonly": "只读实例", "Guard": "灾备实例", "Temp": "临时实例" } status_map = { "Creating": "创建中", "Running": "使用中", "Deleting": "删除中", "Rebooting": "重启中", "Stopping": "暂停中", "Stopped": "已暂停", "DBInstanceClassChanging": "升降级中", "TRANSING": "迁移中", "EngineVersionUpgrading": "迁移版本中", "TransingToOthers": "迁移数据到其他RDS中", "GuardDBInstanceCreating": "生产灾备实例中", "Restoring": "备份恢复中", "Importing": "数据导入中", "ImportingFromOthers": "从其他RDS实例导入数据中", "DBInstanceNetTypeChanging": "内外网切换中", "GuardSwitching": "容灾切换中", "INS_CLONING": "实例克隆中", "Released": "已释放实例" } storage_type_map = { "local_ssd": "高性能本地盘", "ephemeral_ssd": "性能本地盘", "cloud_ssd": "SSD 云盘", "general_essd": "高性能云盘", "cloud_essd0": "ESSD PL0 云盘", "cloud_essd": "ESSD PL1 云盘", "cloud_essd2": "ESSD PL2 云盘", "cloud_essd3": "ESSD PL3 云盘" } pay_type_map = { "Postpaid": "按量付费", "Prepaid": "包年包月", "SERVERLESS": "Serverless" } category_map = { "Basic": "基础系列", "HighAvailability": "高可用系列", "cluster": "MySQL 集群系列", "AlwaysOn": "SQL Server 集群系列", "Finance": "三节点企业系列", "Serverless_basic": "Serverless 基础系列" } class MySQLMonitor(BasicMonitor): resource = Resource.MySQL def __init__(self): super().__init__() self.region_client_map: Dict[Region, RDSClient] = {} self.fei_shu_sheet_id = "R50CB5" def create_client(self, region: Region) -> RDSClient: config = models.Config( access_key_id=self.access_key_id, access_key_secret=self.access_key_secret, endpoint=region.rds_endpoint ) return RDSClient(config) def get_rds_client(self, region: Region) -> RDSClient: if region in self.region_client_map: return self.region_client_map[region] client = self.create_client(region) self.region_client_map[region] = client return client def get_all_instance(self, region: Region) -> List[DescribeDBInstancesResponseBodyItemsDBInstance]: page_number = 0 all_instances: List[DescribeDBInstancesResponseBodyItemsDBInstance] = [] while True: next_token, instances = self.get_instances(region=region, page_number=page_number) if not instances: break all_instances.extend(instances) page_number += 1 return all_instances def get_instances(self, region: Region, page_size: int = 100, page_number: int = 0, next_token: str = "") -> Tuple[str, List[DescribeDBInstancesResponseBodyItemsDBInstance]]: client = self.get_rds_client(region) request = DescribeDBInstancesRequest( client_token=self.gen_request_id(), page_size=page_size, page_number=page_number, region_id=region.region, instance_level=1, ) response = client.describe_dbinstances(request) body = response.body return body.next_token, body.items.dbinstance def get_instance_detail(self, region: Region, instance_id: str) -> List[DescribeDBInstanceAttributeResponseBodyItemsDBInstanceAttribute]: client = self.get_rds_client(region) request = DescribeDBInstanceAttributeRequest( dbinstance_id=instance_id ) response = client.describe_dbinstance_attribute(request) return response.body.items.dbinstance_attribute @staticmethod def gen_request_id(): return str(uuid.uuid4()).replace("-", "") def run(self): region_list = [Region.HANG_ZHOU, Region.HONG_KONG, Region.US_WEST, Region.SOUTHEAST] for region in region_list: all_instances = self.get_all_instance(region=region) for instance in all_instances: dt = datetime.now().strftime('%Y-%m-%d') instance_id = instance.dbinstance_id instance_name = instance.dbinstance_description category = value_with_mapped_note(instance.category, category_map) memory = convert_storage_unit(instance.dbinstance_memory, "mb", "gb") cpu = instance.dbinstance_cpu status = value_with_mapped_note(instance.dbinstance_status, status_map) instance_type = value_with_mapped_note(instance.dbinstance_type, instance_type_map) engine = instance.engine engine_version = instance.engine_version zone_id = instance.zone_id attributes = self.get_instance_detail(region, instance_id) attribute = attributes[0] disk_used = convert_storage_unit(attribute.dbinstance_disk_used, "b", "gb") storage = attribute.dbinstance_storage storage_type = value_with_mapped_note(attribute.dbinstance_storage_type, storage_type_map) pay_type = value_with_mapped_note(attribute.pay_type, pay_type_map) values = [[dt, region.desc, zone_id, instance_id, instance_name, category, status, instance_type, pay_type, engine, engine_version, memory, cpu, disk_used, storage, storage_type]] start_col = "A2" end_col = calculate_excel_range_bottom_right_cell(start_col, values) self.fei_shu_service.spreadsheet_values_prepend( self.fei_shu_tenant_access_token(), self.fei_shu_spread_sheet_token, f"{self.fei_shu_sheet_id}!{start_col}:{end_col}", values )