You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

私有子网中CodeBuild连接S3遇TCP 443超时问题求助

问题:CodeBuild部署在私有子网无法访问S3构件超时

我把CodeBuild部署在VPC的私有子网中,目的是访问子网内的RDS集群,但CodeBuild抛出以下超时错误:

CLIENT_ERROR: RequestError: send request failed caused by: Get "https://abcdatabase-schema-abcdatabaseschemap-jatjfe01aqps.s3.amazonaws.com/abcDatabase-Sc/Artifact_S/LrJBqSR.zip": dial tcp 52.217.128.121:443: i/o timeout for primary source and source version arn:aws:s3:::abcdatabase-schema-abcdatabaseschemap-jatjfe01aqps/abcDatabase-Sc/Artifact_S/LrJBqSR.zip

这是TCP 443超时错误,说明CodeBuild从S3下载构件时网络不通。我已配置S3 VPC网关终端节点,按逻辑应该能建立连接且无需NAT网关,以下是我的CDK配置代码:

VPC栈代码

private readonly coreVpc: EC2.Vpc;
constructor(scope: CDK.App, id: string, props?: VpcStackStackProps) {
  super(scope, id, props);

  const vpcName: string = "CoreVpc";

  // Create VPC
  this.coreVpc = new EC2.Vpc(this, "CoreVpc", {
    vpcName: vpcName,
    cidr: "10.0.0.0/16",
    enableDnsHostnames: true,
    enableDnsSupport: true,
    maxAzs: 3, // 3 availability zones
    // Each zone will have one public subnet and one private subnet.
    subnetConfiguration: [
      {
        cidrMask: 19,
        name: "PublicSubnet",
        subnetType: EC2.SubnetType.PUBLIC,
      },
      {
        cidrMask: 19,
        name: "PrivateSubnet",
        subnetType: EC2.SubnetType.PRIVATE_ISOLATED,
      },
    ],
  });

  // Create security group for the VPC
  const vpcEndpointSecurityGroup = new EC2.SecurityGroup(
    this,
    `${vpcName}-VPCEndpointSecurityGroup`,
    {
      securityGroupName: `${vpcName}-VPCEndpointSecurityGroup`,
      vpc: this.coreVpc,
      description: "Security group for granting AWS services access to the CoreVpc",
      allowAllOutbound: false,
    }
  );
  vpcEndpointSecurityGroup.addIngressRule(
    EC2.Peer.ipv4(this.coreVpc.vpcCidrBlock),
    EC2.Port.tcp(443),
    "Allow HTTPS ingress traffic"
  );

  vpcEndpointSecurityGroup.addEgressRule(
    EC2.Peer.ipv4(this.coreVpc.vpcCidrBlock),
    EC2.Port.tcp(443),
    "Allow HTTPS egress traffic"
  );

  const privateSubnets = this.coreVpc.selectSubnets(
    {
      subnetType: EC2.SubnetType.PRIVATE_ISOLATED
    }
  );

  // Grant AWS CodeBuild service access to the VPC's private subnets.
  new EC2.InterfaceVpcEndpoint(
    this, 'CodeBuildInterfaceVpcEndpoint', {
      service: EC2.InterfaceVpcEndpointAwsService.CODEBUILD,
      vpc: this.coreVpc,
      privateDnsEnabled: true,
      securityGroups: [vpcEndpointSecurityGroup],
      subnets: privateSubnets
    }
  );

  // Grant VPC access to S3 service.
  new EC2.GatewayVpcEndpoint(
    this, 'S3InterfaceVpcEndpoint', {
      service: EC2.GatewayVpcEndpointAwsService.S3,
      vpc: this.coreVpc,
    }
  );
}
}

CodeBuild栈代码

export class CodeBuildStack extends CDK.Stack {
  constructor(scope: Construct, id: string, props: CodeBuildStackProps) {
    super(scope, id, props);

    const buildspecFile = FS.readFileSync("./config/buildspec.yml", "utf-8");
    const buildspecFileYaml = YAML.parse(buildspecFile, {
      prettyErrors: true,
    });

    // Grant write permissions to the DeploymentRole to the artifact S3 bucket.
    const deploymentRoleArn: string = `arn:aws:iam::${props.env?.account}:role/${props.pipelineName}-DeploymentRole`;
    const deploymentRole = IAM.Role.fromRoleArn(
      this,
      `CodeBuild${props.pipelineStageInfo.stageName}DeploymentRoleConstructID`,
      deploymentRoleArn,
      {
        mutable: false,
        // Causes CDK to update the resource policy where required, instead of the Role
        addGrantsToResources: true,
      }
    );

    const coreVpc: EC2.IVpc = EC2.Vpc.fromLookup(
      this,
      `${props.pipelineStageInfo.stageName}VpcLookupId`,
      {
        vpcName: "CoreVpc",
      }
    );
    
    const securityGroupForVpc: EC2.ISecurityGroup =
      EC2.SecurityGroup.fromLookupByName(
        this,
        "SecurityGroupLookupForVpcEndpoint",
        "CoreVpc-VPCEndpointSecurityGroup",
        coreVpc
      );

    new CodeBuild.Project(
      this,
      `${props.pipelineName}-${props.pipelineStageInfo.stageName}-ColdBuild`,
      {
        projectName: `${props.pipelineName}-${props.pipelineStageInfo.stageName}-ColdBuild`,
        environment: {
          buildImage: CodeBuild.LinuxBuildImage.STANDARD_5_0,
        },
        buildSpec: CodeBuild.BuildSpec.fromObjectToYaml(buildspecFileYaml),
        vpc: coreVpc,
        securityGroups: [securityGroupForVpc],
        role: deploymentRole,
      }
    );
  }
}

排查原因与解决方法

1. S3网关终端节点路由表关联缺失

S3网关终端节点需要关联私有子网的路由表,否则私有子网内的流量不会走终端节点访问S3。你的代码创建S3网关终端节点时未指定routeTables参数,CDK默认只会将终端节点关联到公有子网的路由表,私有子网路由表没有添加指向S3网关的路由,导致CodeBuild流量尝试走公网(私有子网无NAT网关,因此超时)。

解决方法:创建S3网关终端节点时,明确关联私有子网的路由表:

new EC2.GatewayVpcEndpoint(
  this, 'S3GatewayVpcEndpoint', {
    service: EC2.GatewayVpcEndpointAwsService.S3,
    vpc: this.coreVpc,
    routeTables: this.coreVpc.selectSubnets({subnetType: EC2.SubnetType.PRIVATE_ISOLATED}).routeTables
  }
);

2. CodeBuild安全组出站规则限制

你给CodeBuild使用的CoreVpc-VPCEndpointSecurityGroup安全组,出站规则仅允许访问VPC CIDR的443端口。虽然S3网关终端节点的流量在VPC内流转,但安全组需要允许HTTPS流量到S3服务范围。

解决方法:修改安全组出站规则,允许HTTPS(443)出站到任意地址(路由会自动将S3流量导向网关):

vpcEndpointSecurityGroup.addEgressRule(
  EC2.Peer.anyIpv4(),
  EC2.Port.tcp(443),
  "Allow HTTPS egress to S3 and other AWS services"
);

3. S3存储桶访问策略限制

检查S3存储桶的桶策略,确保允许CodeBuild角色访问该桶,并且允许通过VPC终端节点访问。可添加条件限制仅允许VPC内访问:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": "arn:aws:iam::ACCOUNT_ID:role/CODEBUILD_ROLE_ARN"
      },
      "Action": ["s3:GetObject", "s3:ListBucket"],
      "Resource": [
        "arn:aws:s3:::abcdatabase-schema-abcdatabaseschemap-jatjfe01aqps",
        "arn:aws:s3:::abcdatabase-schema-abcdatabaseschemap-jatjfe01aqps/*"
      ],
      "Condition": {
        "StringEquals": {
          "aws:sourceVpc": "VPC_ID"
        }
      }
    }
  ]
}

4. 确认私有子网DNS配置

虽然你已开启enableDnsHostnames和enableDnsSupport,需确保私有子网的DNS服务器为VPC默认DNS(VPC CIDR+2),这样S3域名才能正确解析到VPC终端节点地址,而非公网IP。


内容的提问来源于stack exchange,提问作者Yang Liu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.17 23:40:31