예제 #1
0
    public MyStack()
    {
        var vpc = Output.Create(Aws.Ec2.GetVpc.InvokeAsync(new Aws.Ec2.GetVpcArgs
        {
            Default = true,
        }));
        var subnets = vpc.Apply(vpc => Output.Create(Aws.Ec2.GetSubnetIds.InvokeAsync(new Aws.Ec2.GetSubnetIdsArgs
        {
            VpcId = vpc.Id,
        })));
        // Create a security group that permits HTTP ingress and unrestricted egress.
        var webSecurityGroup = new Aws.Ec2.SecurityGroup("webSecurityGroup", new Aws.Ec2.SecurityGroupArgs
        {
            VpcId  = vpc.Apply(vpc => vpc.Id),
            Egress =
            {
                new Aws.Ec2.Inputs.SecurityGroupEgressArgs
                {
                    Protocol   = "-1",
                    FromPort   = 0,
                    ToPort     = 0,
                    CidrBlocks =
                    {
                        "0.0.0.0/0",
                    },
                },
            },
            Ingress =
            {
                new Aws.Ec2.Inputs.SecurityGroupIngressArgs
                {
                    Protocol   = "tcp",
                    FromPort   = 80,
                    ToPort     = 80,
                    CidrBlocks =
                    {
                        "0.0.0.0/0",
                    },
                },
            },
        });
        // Create an ECS cluster to run a container-based service.
        var cluster = new Aws.Ecs.Cluster("cluster", new Aws.Ecs.ClusterArgs
        {
        });
        // Create an IAM role that can be used by our service's task.
        var taskExecRole = new Aws.Iam.Role("taskExecRole", new Aws.Iam.RoleArgs
        {
            AssumeRolePolicy = JsonSerializer.Serialize(new Dictionary <string, object?>
            {
                { "Version", "2008-10-17" },
                { "Statement", new[]
                  {
                      new Dictionary <string, object?>
                      {
                          { "Sid", "" },
                          { "Effect", "Allow" },
                          { "Principal", new Dictionary <string, object?>
                            {
                                { "Service", "ecs-tasks.amazonaws.com" },
                            } },
                          { "Action", "sts:AssumeRole" },
                      },
                  } },
            }),
        });
        var taskExecRolePolicyAttachment = new Aws.Iam.RolePolicyAttachment("taskExecRolePolicyAttachment", new Aws.Iam.RolePolicyAttachmentArgs
        {
            Role      = taskExecRole.Name,
            PolicyArn = "arn:aws:iam::aws:policy/service-role/AmazonECSTaskExecutionRolePolicy",
        });
        // Create a load balancer to listen for HTTP traffic on port 80.
        var webLoadBalancer = new Aws.ElasticLoadBalancingV2.LoadBalancer("webLoadBalancer", new Aws.ElasticLoadBalancingV2.LoadBalancerArgs
        {
            Subnets        = subnets.Apply(subnets => subnets.Ids),
            SecurityGroups =
            {
                webSecurityGroup.Id,
            },
        });
        var webTargetGroup = new Aws.ElasticLoadBalancingV2.TargetGroup("webTargetGroup", new Aws.ElasticLoadBalancingV2.TargetGroupArgs
        {
            Port       = 80,
            Protocol   = "HTTP",
            TargetType = "ip",
            VpcId      = vpc.Apply(vpc => vpc.Id),
        });
        var webListener = new Aws.ElasticLoadBalancingV2.Listener("webListener", new Aws.ElasticLoadBalancingV2.ListenerArgs
        {
            LoadBalancerArn = webLoadBalancer.Arn,
            Port            = 80,
            DefaultActions  =
            {
                new Aws.ElasticLoadBalancingV2.Inputs.ListenerDefaultActionArgs
                {
                    Type           = "forward",
                    TargetGroupArn = webTargetGroup.Arn,
                },
            },
        });
        // Spin up a load balanced service running NGINX
        var appTask = new Aws.Ecs.TaskDefinition("appTask", new Aws.Ecs.TaskDefinitionArgs
        {
            Family                  = "fargate-task-definition",
            Cpu                     = "256",
            Memory                  = "512",
            NetworkMode             = "awsvpc",
            RequiresCompatibilities =
            {
                "FARGATE",
            },
            ExecutionRoleArn     = taskExecRole.Arn,
            ContainerDefinitions = JsonSerializer.Serialize(new[]
            {
                new Dictionary <string, object?>
                {
                    { "name", "my-app" },
                    { "image", "nginx" },
                    { "portMappings", new[]
                      {
                          new Dictionary <string, object?>
                          {
                              { "containerPort", 80 },
                              { "hostPort", 80 },
                              { "protocol", "tcp" },
                          },
                      } },
                },
            }
                                                            ),
        });
        var appService = new Aws.Ecs.Service("appService", new Aws.Ecs.ServiceArgs
        {
            Cluster              = cluster.Arn,
            DesiredCount         = 5,
            LaunchType           = "FARGATE",
            TaskDefinition       = appTask.Arn,
            NetworkConfiguration = new Aws.Ecs.Inputs.ServiceNetworkConfigurationArgs
            {
                AssignPublicIp = true,
                Subnets        = subnets.Apply(subnets => subnets.Ids),
                SecurityGroups =
                {
                    webSecurityGroup.Id,
                },
            },
            LoadBalancers =
            {
                new Aws.Ecs.Inputs.ServiceLoadBalancerArgs
                {
                    TargetGroupArn = webTargetGroup.Arn,
                    ContainerName  = "my-app",
                    ContainerPort  = 80,
                },
            },
        }, new CustomResourceOptions
        {
            DependsOn =
            {
                webListener,
            },
        });

        this.Url = webLoadBalancer.DnsName;
    }
예제 #2
0
    public FargateStack()
    {
        // Read back the default VPC and public subnets, which we will use.
        var vpc = Output.Create(Ec2.GetVpc.InvokeAsync(new Ec2.GetVpcArgs {
            Default = true
        }));
        var vpcId  = vpc.Apply(vpc => vpc.Id);
        var subnet = vpcId.Apply(id => Ec2.GetSubnetIds.InvokeAsync(new Ec2.GetSubnetIdsArgs {
            VpcId = id
        }));
        var subnetIds = subnet.Apply(s => s.Ids);

        // Create a SecurityGroup that permits HTTP ingress and unrestricted egress.
        var webSg = new Ec2.SecurityGroup("web-sg", new Ec2.SecurityGroupArgs
        {
            VpcId  = vpcId,
            Egress =
            {
                new Ec2.Inputs.SecurityGroupEgressArgs
                {
                    Protocol   = "-1",
                    FromPort   = 0,
                    ToPort     = 0,
                    CidrBlocks ={ "0.0.0.0/0"                  }
                }
            },
            Ingress =
            {
                new Ec2.Inputs.SecurityGroupIngressArgs
                {
                    Protocol   = "tcp",
                    FromPort   = 80,
                    ToPort     = 80,
                    CidrBlocks ={ "0.0.0.0/0"                  }
                }
            }
        });

        // Create an ECS cluster to run a container-based service.
        var cluster = new Ecs.Cluster("app-cluster");

        // Create an IAM role that can be used by our service's task.
        var taskExecRole = new Iam.Role("task-exec-role", new Iam.RoleArgs
        {
            AssumeRolePolicy = @"{
""Version"": ""2008-10-17"",
""Statement"": [{
    ""Sid"": """",
    ""Effect"": ""Allow"",
    ""Principal"": {
        ""Service"": ""ecs-tasks.amazonaws.com""
    },
    ""Action"": ""sts:AssumeRole""
}]
}"
        });
        var taskExecAttach = new Iam.RolePolicyAttachment("task-exec-policy", new Iam.RolePolicyAttachmentArgs
        {
            Role      = taskExecRole.Name,
            PolicyArn = "arn:aws:iam::aws:policy/service-role/AmazonECSTaskExecutionRolePolicy"
        });

        // Create a load balancer to listen for HTTP traffic on port 80.
        var webLb = new Elb.LoadBalancer("web-lb", new Elb.LoadBalancerArgs
        {
            Subnets        = subnetIds,
            SecurityGroups = { webSg.Id }
        });
        var webTg = new Elb.TargetGroup("web-tg", new Elb.TargetGroupArgs
        {
            Port       = 80,
            Protocol   = "HTTP",
            TargetType = "ip",
            VpcId      = vpcId
        });
        var webListener = new Elb.Listener("web-listener", new Elb.ListenerArgs
        {
            LoadBalancerArn = webLb.Arn,
            Port            = 80,
            DefaultActions  =
            {
                new Elb.Inputs.ListenerDefaultActionArgs
                {
                    Type           = "forward",
                    TargetGroupArn = webTg.Arn,
                }
            }
        });

        // Create a private ECR registry and build and publish our app's container image to it.
        var appRepo            = new Ecr.Repository("app-repo");
        var appRepoCredentials = appRepo.RegistryId.Apply(async rid =>
        {
            var credentials = await Ecr.GetCredentials.InvokeAsync(new Ecr.GetCredentialsArgs {
                RegistryId = rid
            });
            var data = Convert.FromBase64String(credentials.AuthorizationToken);
            return(Encoding.UTF8.GetString(data).Split(":").ToImmutableArray());
        });
        var image = new Docker.Image("app-img", new Docker.ImageArgs
        {
            Build     = "../App",
            ImageName = appRepo.RepositoryUrl,
            Registry  = new Docker.ImageRegistry
            {
                Server   = appRepo.RepositoryUrl,
                Username = appRepoCredentials.GetAt(0),
                Password = appRepoCredentials.GetAt(1)
            }
        });

        // Spin up a load balanced service running our container image.
        var appTask = new Ecs.TaskDefinition("app-task", new Ecs.TaskDefinitionArgs
        {
            Family                  = "fargate-task-definition",
            Cpu                     = "256",
            Memory                  = "512",
            NetworkMode             = "awsvpc",
            RequiresCompatibilities = { "FARGATE" },
            ExecutionRoleArn        = taskExecRole.Arn,
            ContainerDefinitions    = image.ImageName.Apply(imageName => @"[{
""name"": ""my-app"",
""image"": """ + imageName + @""",
""portMappings"": [{
    ""containerPort"": 80,
    ""hostPort"": 80,
    ""protocol"": ""tcp""
}]
}]")
        });
        var appSvc = new Ecs.Service("app-svc", new Ecs.ServiceArgs
        {
            Cluster              = cluster.Arn,
            DesiredCount         = 3,
            LaunchType           = "FARGATE",
            TaskDefinition       = appTask.Arn,
            NetworkConfiguration = new Ecs.Inputs.ServiceNetworkConfigurationArgs
            {
                AssignPublicIp = true,
                Subnets        = subnetIds,
                SecurityGroups = { webSg.Id }
            },
            LoadBalancers =
            {
                new Ecs.Inputs.ServiceLoadBalancerArgs
                {
                    TargetGroupArn = webTg.Arn,
                    ContainerName  = "my-app",
                    ContainerPort  = 80
                }
            }
        }, new CustomResourceOptions {
            DependsOn = { webListener }
        });

        // Export the resulting web address.
        this.Url = Output.Format($"http://{webLb.DnsName}");
    }
예제 #3
0
    private static void ConfigureEcsCluster()
    {
        cluster = new Ecs.Cluster($"{baseName}-cluster", null, new CustomResourceOptions());

        // Create a SecurityGroup that permits HTTP ingress and unrestricted egress.
        var webSg = new Ec2.SecurityGroup($"{baseName}-web-sg", new Ec2.SecurityGroupArgs
        {
            VpcId  = vpcId,
            Egress =
            {
                new Ec2.Inputs.SecurityGroupEgressArgs
                {
                    Protocol   = "-1",
                    FromPort   = 0,
                    ToPort     = 0,
                    CidrBlocks ={ "0.0.0.0/0"                  },
                },
            },
            Ingress =
            {
                new Ec2.Inputs.SecurityGroupIngressArgs
                {
                    Protocol   = "tcp",
                    FromPort   = 80,
                    ToPort     = 80,
                    CidrBlocks ={ "0.0.0.0/0"                  },
                },
            },
        });

        // Create an IAM role that can be used by our service's task.
        var taskExecRole = new Iam.Role($"{baseName}-task-exec-role", new Iam.RoleArgs
        {
            AssumeRolePolicy = File.ReadAllText("perm.json"),
        });

        var taskExecAttach = new Iam.RolePolicyAttachment($"{baseName}-task-exec-policy", new Iam.RolePolicyAttachmentArgs
        {
            Role      = taskExecRole.Name,
            PolicyArn = "arn:aws:iam::aws:policy/service-role/AmazonECSTaskExecutionRolePolicy",
        });

        // Create a load balancer to listen for HTTP traffic on port 80.
        var webLb = new Elb.LoadBalancer($"{baseName}-web-lb", new Elb.LoadBalancerArgs
        {
            Subnets = new InputList <string>()
            {
                subnetId, subnetTwoId
            },
            SecurityGroups = { webSg.Id },
        });
        var webTg = new Elb.TargetGroup($"{baseName}-web-tg", new Elb.TargetGroupArgs
        {
            Port       = 80,
            Protocol   = "HTTP",
            TargetType = "ip",
            VpcId      = vpcId,
        });
        var webListener = new Elb.Listener($"{baseName}-web-listener", new Elb.ListenerArgs
        {
            LoadBalancerArn = webLb.Arn,
            Port            = 80,
            DefaultActions  =
            {
                new Elb.Inputs.ListenerDefaultActionsArgs
                {
                    Type           = "forward",
                    TargetGroupArn = webTg.Arn,
                },
            },
        });

        var launchConfig = new Ec2.LaunchConfiguration($"{baseName}-launchconfig", new Ec2.LaunchConfigurationArgs()
        {
            ImageId                  = "ami-a1491ad2",
            InstanceType             = "t2.nano",
            AssociatePublicIpAddress = true,
            SecurityGroups           = webSg.Id,
        });

        var scalingGroup = new Group($"{baseName}-autoscaling", new GroupArgs()
        {
            AvailabilityZones = new InputList <string>()
            {
                "eu-west-1a", "eu-west-1b"
            },
            VpcZoneIdentifiers = new InputList <string>()
            {
                subnetId, subnetTwoId
            },
            DesiredCapacity     = 1,
            LaunchConfiguration = launchConfig.Id,
            MaxSize             = 1,
            MinSize             = 0,
        });

        // Spin up a load balanced service running our container image.
        var appTask = new Ecs.TaskDefinition($"{baseName}-app-task", new Ecs.TaskDefinitionArgs
        {
            Family                  = "fargate-task-definition",
            Cpu                     = "256",
            Memory                  = "512",
            NetworkMode             = "awsvpc",
            RequiresCompatibilities = { "FARGATE", "EC2" },
            ExecutionRoleArn        = taskExecRole.Arn,
            ContainerDefinitions    = @"[{
    ""name"": ""my-app"",
    ""image"": ""nginx"",
    ""portMappings"": [{
        ""containerPort"": 80,
        ""hostPort"": 80,
        ""protocol"": ""tcp""
    }]
}]",
        });

        var ec2Svc = new Ecs.Service($"{baseName}-ec2-svc", new Ecs.ServiceArgs()
        {
            Cluster              = cluster.Arn,
            DesiredCount         = 1,
            LaunchType           = "EC2",
            TaskDefinition       = appTask.Arn,
            NetworkConfiguration = new Ecs.Inputs.ServiceNetworkConfigurationArgs
            {
                Subnets = new InputList <string>()
                {
                    subnetId, subnetTwoId
                },
                SecurityGroups = { webSg.Id },
            },
            LoadBalancers =
            {
                new Ecs.Inputs.ServiceLoadBalancersArgs
                {
                    TargetGroupArn = webTg.Arn,
                    ContainerName  = "my-app",
                    ContainerPort  = 80,
                },
            },
        }, new CustomResourceOptions {
            DependsOn = { webListener }
        });
    }