【问题标题】:List subnets in an AWS by VPC ID按 VPC ID 列出 AWS 中的子网
【发布时间】:2020-05-03 18:03:20
【问题描述】:

我需要列出 AWS 中特定 VPC 中的子网。

执行此操作时出现此错误:

Traceback (most recent call last):
  File ".\aws_create_ec2.py", line 253, in <module>
    main()
  File ".\aws_create_ec2.py", line 249, in main
    create_instances()
  File ".\aws_create_ec2.py", line 146, in create_instances
    subnet_list = ec2_client.describe_subnets(
  File "C:\Users\User\AppData\Local\Programs\Python\Python38-32\lib\site-packages\botocore\client.py", line 272, in _api_call
    return self._make_api_call(operation_name, kwargs)
  File "C:\Users\User\AppData\Local\Programs\Python\Python38-32\lib\site-packages\botocore\client.py", line 548, in _make_api_call
    request_dict = self._convert_to_request_dict(
  File "C:\Users\User\AppData\Local\Programs\Python\Python38-32\lib\site-packages\botocore\client.py", line 596, in _convert_to_request_dict
    request_dict = self._serializer.serialize_to_request(
  File "C:\Users\User\AppData\Local\Programs\Python\Python38-32\lib\site-packages\botocore\validate.py", line 297, in serialize_to_request
    raise ParamValidationError(report=report.generate_report())
botocore.exceptions.ParamValidationError: Parameter validation failed:
Unknown parameter in input: "VpcIds", must be one of: Filters, SubnetIds, DryRun, NextToken, MaxResults

我正在使用这些命令:

 vpc_id = input("Enter the vpc id: ")
 subnet_list = ec2_client.describe_subnets(
     VpcIds=[
         vpc_id,
       ]
    )

如何使用此命令正确过滤我想要的 VPC?

另外,如何使用正则表达式验证用户输入,使其符合正确的格式?例如,用户输入匹配类似于:vpc-68b1ff12

【问题讨论】:

    标签: python boto3


    【解决方案1】:

    函数describe_subnets也可以这样使用:

     vpc_id = "my-vpc-id"
     client = boto3.client("ec2")
     subnet_list = client.describe_subnets(
         Filters=[{"Name":"vpc-id", "Values":[vpc_id]}]
     )
    

    这里有完整的文档https://boto3.amazonaws.com/v1/documentation/api/latest/reference/services/ec2.html#EC2.Client.describe_subnets

    【讨论】:

      【解决方案2】:

      错误消息意味着VpcIds 不是describe_subnets 的有效参数。有效参数列表记录在here。

      在 VPC 中获取子网的另一种方法是:

      subnets = boto3.resource("ec2").subnets.filter(
          Filters=[{"Name": "vpc-id", "Values": [vpc_id]}]
      )
      subnet_ids = [sn.id for sn in subnets]
      

      【讨论】:

      • Imo 这应该是公认的答案。当前接受的答案是关于在 VPC 中获取子网的方法
      【解决方案3】:

      很难判断哪些代码运行失败了,但我认为这可以分两步完成...首先列出所有VPCs,然后列出每个VPC中的所有subnets

      类似这样的:

      import boto3
      
      session = boto3.Session(region_name='us-east-1')
      ec2_resource = session.resource("ec2")
      ec2_client = session.client("ec2")
      subnet_ids = []
      for vpc in ec2_resource.vpcs.all():
          # here you can choose which subnet based on the id
          if vpc.id == 'vpc-abcd1234':
              for subnet in vpc.subnets.all():
                  subnet_ids.append(subnet.id)
      # the result of this call has the data you're looking for
      print(ec2_client.describe_subnets(SubnetIds=subnet_ids))
      

      要验证输入,您可以使用这样的正则表达式:

      import re
      pattern = re.compile('vpc-\w{8}$')
      print(pattern.match('vpc-abcd1'))
      print(pattern.match('vpc-abcd1234'))
      print(pattern.match('vpc-abcd1-34'))
      print(pattern.match('vpc-abcd134567890'))
      print(pattern.match('apc-1a2b3c4d'))
      print(pattern.match('vpc-1a2b3c4d'))
      

      将打印:

      None
      <re.Match object; span=(0, 12), match='vpc-abcd1234'>
      None
      None
      None
      <re.Match object; span=(0, 12), match='vpc-1a2b3c4d'>
      

      为了确保您的输入有效,在循环中调用验证,例如:

      import re
      
      pattern = re.compile('vpc-\w{8}$')
      
      def get_input():
          found = input("vpc id:")
          match = pattern.match(found)
          while not match:
              found = input('vpc id:')
              match = pattern.match(found)
      
          return found
      

      【讨论】:

        猜你喜欢
        • 2018-02-05
        • 2017-03-12
        • 2021-03-14
        • 2022-01-18
        • 2017-12-03
        • 2017-12-23
        • 2021-06-10
        • 2020-06-12
        • 2018-06-16
        相关资源
        最近更新 更多