GuidesAPI Reference
Log In

Getting Started With Amazon ECS On Prodvana

To deploy Amazon ECS with Prodvana, you will need the following:

  • An ECS cluster
  • A Docker image built and published to a registry that your ECS cluster can pull from
  • A Kubernetes Runtime, used entirely for management of ECS workload. No user-facing workload will run here. You can find instructions on creating a cluster here: AWS: Configuring an EKS Cluster.

📘

Only Fargate Supported

For now, Prodvana only supports managing ECS services on Fargate.

1. Prepare a Kubernetes Runtime

Create a Kubernetes Runtime using your cloud provider of choice.

Link your Kubernetes Runtime to Prodvana. See Configuring a Runtime.

2. Configure an Amazon ECS Runtime

Follow this guide to configure an IAM role for Prodvana to manage ECS.

Make a note of the Namespace name and Service Account name you used when configuring the IAM permissions.

Create a new config file for your ECS Runtime.

runtime:
  name: my-ecs-runtime  # this can be whatever you want
  awsEcs:
    proxyRuntime:
      runtime: KUBERNETES_RUNTIME  # the name you picked when linking your Kubernetes Runtime
      containerOrchestration:
        k8s:
          namespace: NAMESPACE  # must match the namespace created in the IAM role guide above
      inheritRoleFromRuntimeEnv:
          k8sServiceAccount: default # replace if you used a different Service Account in the IAM guide
    region: REGION
    ecsCluster: CLUSTER

Apply the config file to create the ECS Runtime.

pvnctl configs apply my-ecs-runtime.pvn.yaml

You should repeat this step once for each ECS cluster you want to deploy to, giving each of them a unique Runtime name and optionally a different AWS service account.

3. Create an Application

Create a new Application that uses your ECS Runtime, by creating a new config file.

application:
  name: my-application  # can be whatever you want
  releaseChannels:
    - name: staging
      runtimes:
        - runtime: my-ecs-runtime  # need to match the Runtime name you picked earlier

Apply the config file to create the Application.

pvnctl configs apply my-application.pvn.yaml

If you have more than one ECS Runtime, you can deploy your Application across multiple Release Channels and order them. For example:

application:
  name: my-application
  releaseChannels:
    - name: staging
      runtimes:
        - runtime: ecs-staging
    - name: production
      runtimes:
        - runtime: ecs-prod
      preconditions:
        - releaseChannelStable:
            releaseChannel: staging
        - manualApproval: {}

4. Create an ECS Task Definition

Create an ECS task definition.

A good starting point is to take the output of aws ecs register-task-definition --generate-cli-skeleton and modify it to suit your needs.

Here is an example of a simple task definition to run nginx.

{
  "family": "nginx",
  "networkMode": "awsvpc",
  "executionRoleArn": "arn:aws:iam::ACCOUNT_ID:role/ecsTaskExecutionRole",
  "containerDefinitions": [
    {
      "name": "nginx",
      "image": "nginx:latest",
      "portMappings": [
        {
          "containerPort": 80,
          "hostPort": 80,
          "protocol": "tcp"
        }
      ],
      "essential": true
    }
  ],
  "cpu": ".25 vCPU",
  "memory": "0.5 GB",
  "requiresCompatibilities": ["FARGATE"]
}

Migrating an Existing Task Definition

If you have an existing ECS task definition (e.g. you are migrating an existing service to be managed by Prodvana), you can create the JSON one of two ways.

Use the AWS Console (Recommended)

Go to the AWS console, under "Elastic Container Service", "Task Definition" (also at https://console.aws.amazon.com/ecs/v2/task-definitions).

Click on the task definition you want, for the revision you want (the latest revision is likely what you want). Click "Create new revision" -> "Create new revision with JSON".

Copy the content of the JSON in the editor that opens up.

Use the AWS CLI

aws ecs describe-task-definition --task-definition $TASK_DEFINITION_NAME --query taskDefinition will give back a JSON you can use. This approach will result in JSON with more unnecessary, auto-populated fields than the AWS console approach, but it is safe to use. Remember to remove taskDefinitionArn.

5. Create an ECS Service Spec

Create an ECS service definition.

A good starting point is to take the output of aws ecs create-service --generate-cli-skeleton and modify it to suit your needs. You can omit serviceName, cluster, and taskDefinition, as they will be filled in by Prodvana.

Here is an example of a service spec to run nginx.

{
  "launchType": "FARGATE",
  "platformVersion": "LATEST",
  "networkConfiguration": {
    "awsvpcConfiguration": {
      "assignPublicIp": "ENABLED",
      "securityGroups": ["sg-12345678"],
      "subnets": ["subnet-12345678"]
    }
  },
  "desiredCount": 1
}

6. Create a Prodvana Service

Create a Prodvana Service by creating a new config file:

service:
  name: my-ecs-service
  application: my-application  # needs to match the Application name you picked earlier
  awsEcs:
    taskDefinition:
      local:
        path: task-definition.json  # relative path to task definition json you made earlier
    serviceDefinition:
      local:
        path: service-definition.json  # relative path to service definition you made earlier
      

🚧

ECS Service Names Must Be Unique

If in the previous step, you created an Application with multiple Release Channels all deploying to a single ECS Runtime, you must customize the ECS service name to ensure uniqueness. See our example here.

Apply the config file to create the Service.

pvnctl configs apply my-ecs-service.pvn.yaml

7. Deploy Your Service

Go to my-demo-organization.runprodvana.com -> your Application name -> your Service name, and click "Manage Release" -> "Create a New Release". Prodvana will deploy your ECS service, creating it if needed. If there are issues with your configuration or credentials, Prodvana will display an error.

Congratulations! You have deployed your first ECS service with Prodvana.

8. Parametrize the Docker Image

📘

Optional

This step shows how you can parametrize the Docker image, allowing the image to be changed without having to edit the ECS task definition file. If you'd like a full gitops workflow where everything is checked in to code, you can skip this step.

You can use a Docker image parameter to refer to your image.

First, link your repository integration to Prodvana. For example, to link an ECR repository, see Elastic Container Registry (ECR).

Next, modify your Prodvana Service config file:

service:
  name: my-ecs-service
  application: my-application
  awsEcs:  ... # unchanged from before
  parameters:
    - name: image
      required: true
      dockerImage:
        imageRegistryInfo:
          containerRegistry: YOUR_REGISTRY_INTEGRATION_NAME
          imageRepository: REPOSITORY  # this is the part of the Docker image url after the domain. For example, for `12345678.dkr.ecr.us-west-2.amazonaws.com/demo_api`, it is `demo_api`

service:
  name: my-ecs-service
  application: my-application
  awsEcs:  ... # unchanged from before
  parameters:
    - name: image
      required: true
      dockerImage:
        imageRegistryInfo:
          containerRegistry: dockerhub-public
          imageRepository: library/nginx

You can now use the image parameter in your ECS task definition json.

{
  "containerDefinitions": [
    {
      "image": "{{.Params.image}}",
       ...
    }
  ],
  ...
}

There are a number of other variables available, including builtin ones. See Configuring Services.

Apply the config file to pick up the change.

pvnctl configs apply my-ecs-service.pvn.yaml

Now go to the Prodvana UI, at my-demo-organization.runprodvana.com -> your Application -> your Service, click on "Manage Release" -> "Create a New Release". Click "Edit" to pick up the new config file and you will see the option to specify the image parameter value.