【Python3获取办公室的公网IP并修改阿里云安全组规则】

博客摘录「 python3固定规则_利用Python3获取办公室的公网IP并修改阿里云安全组规则」2023年8月12日

引言

当前云原生时代,服务器已经不像十几年前遥不可及了,很多云厂商已经把技术红利释放出来了,云服务器的优惠活动力度空前,算力已经如同水电煤一样融入千家万户之中。

名人名言:

“任何停止学习的人都已经进入老年,无论他在20岁还是80岁;坚持学习的人则永葆青春。”——亨利·福特

一 、编程环境的准备

a. 编程语言种类繁多

市面上主流的一些编程语言像是C,C++,java,javascript等这些,长期霸占排行榜前几名,最近五、六年突然流行起来的语言Golang、Python3,以云原生作为依托,才得以大放异彩

b. 编程语言选择

当时,在为自己的技术选型,正好看到了崔庆才的Python 3网络爬虫开发实战一书,自此踏入了python3编程世界的大门

c. 编程心态

空杯心态

二、编程阶段

博主是一名狂热的pythonic,从一句简单的hello world都打印不出来的时候,到现在逐渐开始理解了面向对象,其中的心酸只有过来人才能体会到。

a. 基础语法

在学习python3的基础语法过程,当中有很多绕不过去的弯。一旦陷入死胡同就无法正确走出来。这时候就需要有针对性的学习特定语法。
例1:
当初看到这两个列表想要去匹配相同的元素,完全想不到有一种特殊的单行暴力模式就能匹配出两个列表中相同的元素。观察了别人的代码之后才发现原来有一种叫做列表推导式的神奇用法
其实就这一整段代码就可以涵盖了前期很多的基础语法,逻辑判断符号变量类型循环体if分支判断,而上手直接写代码,可以省去前期枯燥乏味语法课(这是博主个人的做法,最好的做法还是系统性的学习,因为到后期会发现基础不牢地动山摇,总会有遗漏的知识点)
在这里插入图片描述

list = ['want_result']
list2 = ['want_result','forget_me','push_forward']
# 原先的写法
empty_list = []
for x in range(len(list2)):
  convert_want_res = list2[x]
  if convert_want_res == list[0]:
    empty_list.append(convert_want_res)
  else:
    pass
print('相同元素',empty_list[0])

在这里插入图片描述

list = ['want_result']
list2 = ['want_result','forget_me','push_forward']
convert_want_result = [x for x in list2 if x in list]
print(convert_want_result)

在这里插入图片描述

b. 运算逻辑符号

这里不展开赘述了,网上的介绍文章一大堆,想要学习的总有办法找到的

c. 数据类型

这里是博主个人的看法
(1) string字符串的精髓是做split()和replace()
(2) int整型
(3) list列表的精髓就是index
(4) dic字典的精髓就是key_list
(5) tuple用来存一些无规律的数据
(6) set用来做去重操作很厉害
(7) bool做一些相关逻辑的判断
(8) decimal精度运算很好用
(9) data_frame做数据分析的专用的

d.循环体

列表推导式运算速度是最快的,一般用来匹配列表中相同的元素,触发特定应用场景下的判断
其次是for循环,for循环是最简单朴素的,可以迭代常见的变量类型字典、列表都不在话下
while循环最慢,但是while循环可以写得很花哨

e. 面向对象

我简单理解为就是可以不用重复造轮子了

f. 框架使用

更加高效的开发效率,有了基础之后更上一层楼

g. 进阶算法

这个到后期,只有做人工智能机器学习相关的会用到,数学要好啊,数学不好都是白搭
至少线性代数要会

三、调用sdk的调试过程

阿里云OPENAPI门户网站
使用openapi去调用接口,而后将所需传入参数依次记录下来。
选择满足需求的api接口有详细的入参提示信息

在这里插入图片描述

a. 入参调整

根据脚本的报错信息有针对性的查找报错信息,MissingParameter说明了缺失关键参数,那么就返回官网查需要的必要入参
在这里插入图片描述

b. 构造函数

任何平时生活工作当中遇到的问题都能拆分步骤,典型的例子就是怎么把一个大象塞进冰箱,这样子做的目的就是解放劳动力,依靠暴力的机器去解决生活当中碰到的问题

c. 借鉴别人的代码

从复制粘贴一个人别人已经写好的DEMO开始,逐步融入自己的想法进去。

四、调用aliyun-sdk的python3代码

在本地运行调试成功之后,还可以打包成exe文件,绑定定时任务。省去多余的操作时间

import json
import requests
import csv
import sys
import time
import hashlib

from bs4 import BeautifulSoup
from datetime import datetime
from prettytable import PrettyTable

from selenium import webdriver
from aliyunsdkcore.client import AcsClient
from aliyunsdkcore import client
from aliyunsdkecs.request.v20140526 import AuthorizeSecurityGroupRequest
from aliyunsdkecs.request.v20140526 import DescribeElasticityAssurancesRequest
from aliyunsdkecs.request.v20140526 import RevokeSecurityGroupRequest
from aliyunsdkecs.request.v20140526 import StartInstanceRequest
from aliyunsdkecs.request.v20140526 import RunInstancesRequest
from aliyunsdkecs.request.v20140526 import DescribeInstancesRequest
from aliyunsdkecs.request.v20140526 import DescribeInstancesRequest
from aliyunsdkecs.request.v20140526 import DescribeRegionsRequest
from aliyunsdkecs.request.v20140526 import DescribeInstancesFullStatusRequest
from aliyunsdkecs.request.v20140526 import DescribeAvailableResourceRequest
from aliyunsdkecs.request.v20140526 import DescribeImagesRequest
from aliyunsdkecs.request.v20140526 import DescribeSecurityGroupsRequest
from aliyunsdkecs.request.v20140526 import DescribeVpcsRequest
from aliyunsdkecs.request.v20140526 import DescribeVSwitchesRequest
from aliyunsdkecs.request.v20140526 import CreateInstanceRequest
from aliyunsdkecs.request.v20140526 import StartInstanceRequest
from aliyunsdkecs.request.v20140526 import AllocatePublicIpAddressRequest
from aliyunsdkecs.request.v20140526 import DescribeSecurityGroupAttributeRequest
from aliyunsdkecs.request.v20140526 import RevokeSecurityGroupRequest

# 伪代码:
# click download secretkey
# use hashlib 
# 

class prefetch:
    def __init__(self):
        self.ipuri = 'https://www.ip138.com/'
        self.website = 'https://ip.tool.chinaz.com/'
        self.ipaddr = []
        self.versionlist = []

    @property
    def get_external_ip(self):
        try:
            website_response = requests.get(url=self.website)
            website_soup = BeautifulSoup(website_response.text, 'lxml')
            ip_addr = website_soup.find("dd", class_="fz24").get_text()
            return ip_addr
        except:
            return None

class secretinfo:
    @property
    def convert_ak(self):
        sercetfile = 'AccessKey.csv'
        csv_file = open(sercetfile)
        csv_res = csv.reader(csv_file)
        rows = [row for row in csv_res]
        aliyunak = rows[1][0]
        return aliyunak

    @property
    def convert_sk(self):
        sercetfile = 'AccessKey.csv'
        csv_file = open(sercetfile)
        csv_res = csv.reader(csv_file)
        rows = [row for row in csv_res]
        aliyunsk = rows[1][1]
        return aliyunsk

class aliyunecs(secretinfo,prefetch,PrettyTable):
    def __init__(self):
        self.ak = super().convert_ak 
        self.sk = super().convert_sk
        self.beauty_value_dictionary = {}
        self.securitygrouplist = []
        self.descriptions = []
        self.beauty_value_dictionary = {}
        self.public_ip_address = prefetch().get_external_ip # 这样子做的目的是处理效率更加高不会每次都去调用存进内存里
        self.feature_ip_dictionary = {}

    def main(self):
        region_name = self.DescribeRegions
        for key,value in region_name.items():
            print('所在区域:',key,'区域id:',value)
        sg_id = self.DescribeSecurityGroups(region_value=value)
        print(sg_id)
        '''
        region_value
        SecurityGroupId
        '''
        # 撤销安全组策略的调用方式:
        self.RevokeSecurityGroupEgressRequest(region_value=value,SecurityGroupId=sg_id)
        '''
        下面两行取消注释为更改安全组
        '''
        # self.DescribeSecurityGroupAttribute(region_value=value)
        # self.authorizeSecurityGroupRequest(region_value=value,SecurityGroupId=self.securitygrouplist)

    # 描述区域函数
    @property
    def DescribeRegions(self):
        regionsclt = client.AcsClient(self.ak , self.sk)
        regionsreq = DescribeRegionsRequest.DescribeRegionsRequest()
        regionsreq.set_accept_format('json')
        regionsre = json.loads(regionsclt.do_action_with_exception(regionsreq))
        regions = {}
        city_name = 'cn-shenzhen'
        for i in regionsre['Regions']['Region']:
            if city_name == i['RegionId']:
                regions[i['LocalName']] = i['RegionId']
            else:
                pass
        return regions
    
    # 描述安全组的函数
    def DescribeSecurityGroups(self,region_value):
        sgidclt = client.AcsClient(self.ak , self.sk,region_id=region_value)
        sgidreq = DescribeSecurityGroupsRequest.DescribeSecurityGroupsRequest()
        sgidreq.set_accept_format('json')
        sgidreq.set_PageSize(50)
        sgidsre = json.loads(sgidclt.do_action_with_exception(sgidreq))
        beauty_value = PrettyTable()
        beauty_value.title = '当前实例所在区域安全组信息'
        beauty_value.field_names = ['序号','安全组名称','Vpc编号','安全组编号','创建时间']
        convert_res = sgidsre['SecurityGroups']['SecurityGroup']
        x = 0
        y = 1
        sg_id = []
        while x < len(convert_res):
            parsed_time = datetime.strptime(convert_res[x]['CreationTime'], "%Y-%m-%dT%H:%M:%SZ")
            formatted_time = parsed_time.strftime("%Y/%m/%d %H:%M:%S")
            self.beauty_value_dictionary['序号'] = str(x+y)
            self.beauty_value_dictionary['安全组名称'] = convert_res[x]['SecurityGroupName']
            self.beauty_value_dictionary['安全组编号'] = convert_res[x]['SecurityGroupId']
            self.beauty_value_dictionary['Vpc编号'] = convert_res[x]['VpcId']
            self.beauty_value_dictionary['创建时间'] =formatted_time
            self.securitygrouplist.append(convert_res[x]['SecurityGroupId'])
            beauty_value.add_row([self.beauty_value_dictionary['序号'],self.beauty_value_dictionary['安全组名称'],self.beauty_value_dictionary['Vpc编号'],self.beauty_value_dictionary['安全组编号'],self.beauty_value_dictionary['创建时间']])
            x += 1
        print(beauty_value)
        return self.securitygrouplist

    # 描述安全组属性的函数
    def DescribeSecurityGroupAttribute(self,region_value):
        sgattrclt = client.AcsClient(self.ak , self.sk,region_id=region_value)
        sgattrreq = DescribeSecurityGroupAttributeRequest.DescribeSecurityGroupAttributeRequest()
        sgattrreq.set_accept_format('json')
        z = 1
        # 新加比较端口信息
        feature_port = '22/22'
        # 这两行是只做特殊变更的逻辑
        # all_policy_ip = '0.0.0.0/0'
        # self.public_ip_address = f"{all_policy_ip}"
        for x in self.securitygrouplist:
            sgattrreq.set_SecurityGroupId(x)
            sgatrrsre = json.loads(sgattrclt.do_action_with_exception(sgattrreq))
            vpcid = sgatrrsre['VpcId']
            sgname = sgatrrsre['SecurityGroupName']
            convert_policy_rule = sgatrrsre['Permissions']['Permission']
            print('vpc:',vpcid,'安全组名称',sgname)

            for y in range(len(convert_policy_rule)):
                '''
                convert_policy_rule[y]['PortRange'] 端口信息
                '''
                parsed_time = datetime.strptime(convert_policy_rule[y]['CreateTime'], "%Y-%m-%dT%H:%M:%SZ")
                formatted_time = parsed_time.strftime("%Y/%m/%d %H:%M:%S")
                if convert_policy_rule[y]['PortRange'] == feature_port:
                    self.feature_ip_dictionary[convert_policy_rule[y]['SourceCidrIp']] = convert_policy_rule[y]['PortRange']
                else:
                    pass

                print('编号:',str(z+y),'权重:',convert_policy_rule[y]['Priority'],'源ip:',convert_policy_rule[y]['SourceCidrIp'],'端口范围:',convert_policy_rule[y]['PortRange'],'创建时间:',formatted_time)
            print('*'*108)

    # 确认更改安全组的函数
    def authorizeSecurityGroupRequest(self,region_value,SecurityGroupId):
        print('当前获取到您的公网Ip:',self.public_ip_address)
        whiteip = ('白名单ip为',self.public_ip_address)
        try:
            convert_ip = whiteip[-1]
        except Exception as e:
            print(f"{e}{'原获取ip网站发生错误'}")
        print(f"{'检测到您要添加的安全组编号为为:'}{[x for x in SecurityGroupId]}")
        print('比对的ip数据结构为:',self.feature_ip_dictionary)
        whiteport = f"{'22'}"
        descriptions = f"{'home-ssh-protocol-connections'}"
        counter_x = 0
        execute_list = []
        ip_key_list = list(self.feature_ip_dictionary.keys())
        while counter_x < len(ip_key_list):
            print('已经存在的ip地址:',ip_key_list[counter_x],'对应匹配的端口号:',self.feature_ip_dictionary.get(ip_key_list[counter_x]))
            if ip_key_list[counter_x] == self.public_ip_address:
                execute_list.append('0')
            else:
                pass
            counter_x += 1
        print(execute_list)
        iplist = []
        portlist = []
        iplist.append(convert_ip)
        portlist.append(whiteport)
        print(iplist)
        print(portlist)
        # 列表拿到 标记标记数字为0的状态说明 改ip地址已经存在
        if execute_list == []:
            sgauthorclt = client.AcsClient(self.ak , self.sk,region_id=region_value)
            sgauthorreq = AuthorizeSecurityGroupRequest.AuthorizeSecurityGroupRequest()
            for SecurityGroupIds in SecurityGroupId:
                sgauthorreq.set_accept_format('json')
                sgauthorreq.set_SecurityGroupId(SecurityGroupIds)
                sgauthorreq.set_IpProtocol('TCP')
                sgauthorreq.set_PortRange(str(portlist[0]) + '/' + str(portlist[0]))
                sgauthorreq.set_SourceCidrIp(str(iplist[0]) + '/32')
                # sgauthorreq.set_SourceCidrIp(str(iplist[0]))
                sgauthorreq.set_Priority('10')
                sgauthorreq.set_Description(descriptions)
                sgauthorreq.set_Policy('accept')
                sgauthorreq.set_action_name('authorizeSecurityGroup')
                sgauthorsre = json.loads(sgauthorclt.do_action_with_exception(sgauthorreq))
                print(f'{sgauthorsre}{type(sgauthorsre)}')

        else:
            pass

    # 撤销安全组的函数
    def RevokeSecurityGroupEgressRequest(self,region_value,SecurityGroupId):
        target_ip = '0.0.0.0/0'
        target_port = '22/22'
        revokesgclt = client.AcsClient(self.ak, self.sk, region_id=region_value)
        revokesgreq = RevokeSecurityGroupRequest.RevokeSecurityGroupRequest()
        for SecurityGroupIds in SecurityGroupId:
            print(SecurityGroupIds,type(SecurityGroupIds))
            revokesgreq.set_accept_format('json')
            revokesgreq.set_SecurityGroupId(SecurityGroupIds)
            revokesgreq.set_SourceGroupId(SecurityGroupIds) # 不传这个入参会报错
            revokesgreq.set_IpProtocol('TCP')
            revokesgreq.set_PortRange(target_port)
            revokesgreq.set_SourceCidrIp(target_ip)
            revokesgreq.set_action_name('revokeSecurityGroup')
            revokesgsre = json.loads(revokesgclt.do_action_with_exception(revokesgreq))
            print(f"{revokesgsre}{type(revokesgsre)}")

if __name__ == '__main__':
    aliyunecs().main()
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值