如何使用 terraform 连接不同 VPC 中的副本 Postgres RDS 及其源?

Posted

技术标签:

【中文标题】如何使用 terraform 连接不同 VPC 中的副本 Postgres RDS 及其源?【英文标题】:How do I use terraform to connect a replica Postgres RDS and its Source in a different VPC? 【发布时间】:2021-11-21 18:51:57 【问题描述】:

我正在尝试设置开发环境:1x 私有子网,1x 开发 VPC 中的公共子网;私有子网中的 Postgres RDS 实例;每个子网的资源都在自己的安全组中。源 RDS 实例位于 prod VPC 中。我创建了一个对等连接,每个 VPC 的 CIDR 不重叠。

我得到了

错误:创建数据库实例时出错:无效参数组合:数据库实例和 EC2 安全组位于不同的 VPC 中。数据库实例在 prod-vpc 中,EC2 安全组在 dev-vpc 中

这是我对 terraform 的定义。我还将其他对等方的相关 CIDR 添加到每个对等 VPC 的路由表中。源 RDS 和 prod VPC 都是在单独的进程中创建的,并且已经存在于这个 terraform 进程之外。

module "vpc" 
  source               = "terraform-aws-modules/vpc/aws"
  version              = "2.77.0"
  name                 = "dev-vpc"
  cidr                 = "192.168.0.0/16"
  azs                  = ["us-west-2a"]
  enable_dns_hostnames = true
  enable_dns_support   = true


module "keypair" 
  source      = "git::https://github.com/rhythmictech/terraform-aws-secretsmanager-keypair"
  name_prefix = "ec2-ssh"
  description = "SSH keypair for instances"


resource "aws_security_group" "dev-sg-pub" 
  vpc_id = module.vpc.vpc_id
  ingress 
    from_port   = 5432 # testing
    to_port     = 5432 # testing
    protocol    = "tcp"
    cidr_blocks = ["192.168.1.0/28","192.168.2.0/24"]
    self        = true
  
  egress 
    from_port   = 5432 # testing
    to_port     = 5432 # testing
    protocol    = "tcp"
    cidr_blocks = ["0.0.0.0/0"]
  


resource "aws_security_group" "dev-sg-priv" 
  vpc_id = module.vpc.vpc_id
  ingress 
    from_port       = 5432 # testing
    to_port         = 5432 # testing
    protocol        = "tcp"
    cidr_blocks     = ["192.168.1.0/28", "192.168.2.0/24"]
    security_groups = ["sg-xxxxxxxxxxxxxxx"] # the pub subnet's sg
    self            = true
  
  egress 
    from_port   = 5432 # testing
    to_port     = 5432 # testing
    protocol    = "tcp"
    cidr_blocks = ["192.168.1.0/28", "192.168.2.0/24"]
  


resource "aws_subnet" "dev-subnet-pub" 
  vpc_id      = module.vpc.vpc_id
  cidr_block  = "192.168.1.0/28"
  tags = 
    Name        = "dev-subnet-pub"
    Terraform   = "true"
    Environment = "dev"
  


resource "aws_subnet" "dev-subnet-priv" 
  vpc_id      = module.vpc.vpc_id
  cidr_block  = "192.168.2.0/24"
  tags = 
    Name        = "dev-subnet-priv"
    Terraform   = "true"
    Environment = "dev"
  


resource "aws_vpc_peering_connection" "dev-peer-conn"    
  peer_vpc_id   = "vpc-xxxxxxxxxxxxxxa"
  vpc_id        = module.vpc.vpc_id
  auto_accept   = true


resource "aws_db_instance" "dev-replica" 
   name                   = "dev-replica"
   identifier             = "dev-replica"
   replicate_source_db    = "arn:aws:rds:us-west-2:9999999999:db:tf-xxxxxxxx"
   instance_class         = "db.t3.small"
   apply_immediately      = false
   publicly_accessible    = false
   skip_final_snapshot    = true
   vpc_security_group_ids = [aws_security_group.dev-sg-priv.id, "sg-xxxxxxxxxxx"]
   depends_on = [aws_vpc_peering_connection.dev-peer-conn]

【问题讨论】:

【参考方案1】:

不能这样做。 SG 具有 VAC 范围,您的 RDS 必须使用其所在 VPC 中的 SG。

由于您对您的 VPC 进行了对等,因此您只能在 aws_security_group.dev-sg-priv 中跨 VPC 引用 SG。

【讨论】:

安全组可以跨VPC边界吗? @d8aninja 可以,你可以在aws_security_group.dev-sg-priv引用,但不能直接用于你的RDS。 对不起,我很困惑。 " 安全组只能在为其创建的 VPC 中使用"....docs.aws.amazon.com/vpc/latest/userguide/… 似乎副本的重点是能够在不同的环境中为开发人员用例等共享更新的数据库。如果不是我在这里尝试的方式,是否有建议的方法来做到这一点? @d8aninja 出于开发目的,最好有完全独立的数据库,即生产的迷你版的克隆。副本是只读的,因此将副本用于开发目的仅对测试读取操作有用。

以上是关于如何使用 terraform 连接不同 VPC 中的副本 Postgres RDS 及其源?的主要内容,如果未能解决你的问题,请参考以下文章

terraform - 将 vpc_id 参数从不同的 VPC 传递到多个子网

如何使用 Terraform 创建一个健康的 VPC-Native GKE 集群?

在 terraform 失败的不同 vpc 中创建时出现 rds 副本错误

如何将使用 cidrsubnets 的子网的 CIDR 范围传递给 Terraform 版本 0.14 中的 VPC 模块

Terraform:如何从数据类型中获取元素

如何在 terraform 路由表中引用 AWS 本地前缀列表?