

# Exemplos de montagem de associação para o Amazon ECS
<a name="bind-mount-examples"></a>

Os exemplos a seguir abrangem casos de uso comuns de uma montagem bind para contêineres.

**Para alocar uma quantidade maior de espaço de armazenamento temporário para uma tarefa do Fargate**

Para tarefas do Amazon ECS hospedadas no Fargate usando a versão `1.4.0` ou posterior (Linux) ou `1.0.0` (windows) da plataforma, você pode alocar mais do que a quantidade padrão de armazenamento temporário para os contêineres da tarefa que serão usados. Esse exemplo pode ser incorporado aos outros exemplos para alocar mais armazenamento temporário para suas tarefas do Fargate.
+ Na definição da tarefa, defina um objeto `ephemeralStorage`. O `sizeInGiB` deve ser um número inteiro entre os valores de `21` e `200` e é expresso em GiB.

  ```
  "ephemeralStorage": {
      "sizeInGiB": integer
  }
  ```

**Para fornecer um volume de dados vazio para um ou mais contêineres**

Em alguns casos, você pode querer fornecer aos contêineres de uma tarefa algum espaço temporário. Por exemplo, você pode ter dois contêineres de banco de dados que precisam acessar o mesmo local de armazenamento de arquivos temporários durante uma tarefa. Isso pode ser feito usando uma montagem bind.

1. Na seção `volumes` da definição de tarefa, defina uma montagem bind com o nome `database_scratch`.

   ```
     "volumes": [
       {
         "name": "database_scratch"
       }
     ]
   ```

1. Na seção `containerDefinitions`, crie as definições de contêiner de banco de dados. Isso deve ser feito para que elas montem o volume.

   ```
   "containerDefinitions": [
       {
         "name": "database1",
         "image": "my-repo/database",
         "cpu": 100,
         "memory": 100,
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "database_scratch",
             "containerPath": "/var/scratch"
           }
         ]
       },
       {
         "name": "database2",
         "image": "my-repo/database",
         "cpu": 100,
         "memory": 100,
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "database_scratch",
             "containerPath": "/var/scratch"
           }
         ]
       }
     ]
   ```

**Para expor um caminho e seu conteúdo em um Dockerfile para um contêiner**

Neste exemplo, você tem um Dockerfile que grava dados que você quer montar em um contêiner. Este exemplo funciona para tarefas hospedadas em instâncias do Fargate ou do Amazon EC2.

1. Crie um Dockerfile. O exemplo a seguir usa a imagem pública do contêiner do Amazon Linux 2 e cria um arquivo denominado `examplefile` no diretório `/var/log/exported`que queremos montar dentro do contêiner. A diretiva `VOLUME` deve especificar um caminho absoluto.

   ```
   FROM public.ecr.aws/amazonlinux/amazonlinux:latest
   RUN mkdir -p /var/log/exported
   RUN touch /var/log/exported/examplefile
   VOLUME ["/var/log/exported"]
   ```

   Por padrão, as permissões de volume são definidas como `0755` e o proprietário como `root`. Essas permissões podem ser alteradas no Dockerfile. No exemplo a seguir, o proprietário do diretório `/var/log/exported` é definido como `node`.

   ```
   FROM public.ecr.aws/amazonlinux/amazonlinux:latest
   RUN yum install -y shadow-utils && yum clean all
   RUN useradd node
   RUN mkdir -p /var/log/exported && chown node:node /var/log/exported					    
   USER node
   RUN touch /var/log/exported/examplefile
   VOLUME ["/var/log/exported"]
   ```

1. Na seção `volumes` da definição da tarefa, defina um volume com o nome `application_logs`.

   ```
     "volumes": [
       {
         "name": "application_logs"
       }
     ]
   ```

1. Na seção `containerDefinitions`, crie as definições do contêiner da aplicação. Isso deve ser feito para que elas montem o armazenamento. O valor `containerPath` deve corresponder ao caminho absoluto especificado na diretiva `VOLUME` do Dockerfile.

   ```
     "containerDefinitions": [
       {
         "name": "application1",
         "image": "my-repo/application",
         "cpu": 100,
         "memory": 100,
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "application_logs",
             "containerPath": "/var/log/exported"
           }
         ]
       },
       {
         "name": "application2",
         "image": "my-repo/application",
         "cpu": 100,
         "memory": 100,
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "application_logs",
             "containerPath": "/var/log/exported"
           }
         ]
       }
     ]
   ```

**Para fornecer um volume de dados vazio para um contêiner vinculado ao ciclo de vida da instância host do Amazon EC2**

Para tarefas hospedadas em instâncias do Amazon EC2, você pode usar montagens bind e ter os dados vinculados ao ciclo de vida da instância host do Amazon EC2. É possível fazer isso usando o parâmetro `host` e especificando um valor `sourcePath`. Todos os arquivos existentes em `sourcePath` são apresentados aos contêineres no valor `containerPath`. Todos os arquivos que são gravados no valor `containerPath` são gravados no valor `sourcePath` na instância do host do Amazon EC2.
**Importante**  
O Amazon ECS não sincroniza seu armazenamento entre instâncias do Amazon EC2. As tarefas que usam armazenamento persistente podem ser colocadas em qualquer instância do Amazon EC2, no cluster que tiver capacidade disponível. Se suas tarefas exigirem armazenamento persistente após a interrupção e a reinicialização, sempre especifique a mesma instância do Amazon EC2 no momento da inicialização da tarefa com o comando [start-task](https://docs.aws.amazon.com/cli/latest/reference/ecs/start-task.html) da AWS CLI. Também podem ser usados volumes do Amazon EFS para armazenamento persistente. Para obter mais informações, consulte [Uso de volumes do Amazon EFS com o Amazon ECS](efs-volumes.md).

1. Na seção `volumes` da definição de tarefa, defina uma montagem bind com os valores `name` e `sourcePath`. No exemplo a seguir, a instância host do Amazon EC2 contém dados em `/ecs/webdata` que você quer montar no contêiner.

   ```
     "volumes": [
       {
         "name": "webdata",
         "host": {
           "sourcePath": "/ecs/webdata"
         }
       }
     ]
   ```

1. Na seção `containerDefinitions`, defina um contêiner com um valor `mountPoints` que faça referência ao nome da montagem bind definida e ao valor `containerPath` para montar a montagem bind no contêiner.

   ```
     "containerDefinitions": [
       {
         "name": "web",
         "image": "public.ecr.aws/docker/library/nginx:latest",
         "cpu": 99,
         "memory": 100,
         "portMappings": [
           {
             "containerPort": 80,
             "hostPort": 80
           }
         ],
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "webdata",
             "containerPath": "/usr/share/nginx/html"
           }
         ]
       }
     ]
   ```

**Para montar um volume definido em vários contêineres em diferentes locais**

É possível definir um volume de dados em uma definição de tarefa e montar esse volume em locais diferentes em diferentes contêineres. Por exemplo, seu contêiner host tem uma pasta de dados de site em `/data/webroot`. É possível montar esse volume de dados como somente leitura em dois servidores Web diferentes com raízes de documentos distintas.

1. Na seção `volumes` de definição de tarefa, defina um volume de dados com o nome `webroot` e o caminho de origem `/data/webroot`.

   ```
     "volumes": [
       {
         "name": "webroot",
         "host": {
           "sourcePath": "/data/webroot"
         }
       }
     ]
   ```

1. Na seção `containerDefinitions`, defina um contêiner para cada servidor da Web com valores `mountPoints` que associam o volume `webroot` com o valor `containerPath` apontando para a raiz do documento desse contêiner.

   ```
     "containerDefinitions": [
       {
         "name": "web-server-1",
         "image": "my-repo/ubuntu-apache",
         "cpu": 100,
         "memory": 100,
         "portMappings": [
           {
             "containerPort": 80,
             "hostPort": 80
           }
         ],
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "webroot",
             "containerPath": "/var/www/html",
             "readOnly": true
           }
         ]
       },
       {
         "name": "web-server-2",
         "image": "my-repo/sles11-apache",
         "cpu": 100,
         "memory": 100,
         "portMappings": [
           {
             "containerPort": 8080,
             "hostPort": 8080
           }
         ],
         "essential": true,
         "mountPoints": [
           {
             "sourceVolume": "webroot",
             "containerPath": "/srv/www/htdocs",
             "readOnly": true
           }
         ]
       }
     ]
   ```

**Para montar volumes de outro contêiner usando `volumesFrom`**

Para tarefas hospedadas em instâncias do Amazon EC2, é possível definir um ou mais volumes em um contêiner e, em seguida, usar o parâmetro `volumesFrom` em uma definição de contêiner diferente (dentro da mesma tarefa) para montar todos os volumes do `sourceContainer` em seus pontos de montagem definidos originalmente. O parâmetro `volumesFrom` se aplica a volumes determinados na definição de tarefa, e os que são incorporados na imagem com um Dockerfile.

1. (Opcional) Para compartilhar um volume incorporado em uma imagem, utilize a instrução `VOLUME` no arquivo Dockerfile. O Dockerfile de exemplo a seguir usa uma imagem `httpd` e, em seguida, adiciona um volume e monta-o em `dockerfile_volume` na raiz do documento Apache. É a pasta usada pelo servidor Web `httpd`.

   ```
   FROM httpd
   VOLUME ["/usr/local/apache2/htdocs/dockerfile_volume"]
   ```

   É possível incorporar uma imagem com esse Dockerfile e enviá-la para um repositório, como o Docker Hub, e usá-la em sua definição de tarefa. A imagem de exemplo `my-repo/httpd_dockerfile_volume` usada nas etapas a seguir foi criada com o Dockerfile anterior.

1. Crie uma definição de tarefa que defina seus outros volumes e pontos de montagem para os contêineres. Nesta seção `volumes` de exemplo, você cria um volume vazio chamado `empty`, que o daemon do Docker gerencia. Há também um volume host definido que se chama `host_etc`. Ele exporta a pasta `/etc` na instância de contêiner host.

   ```
   {
     "family": "test-volumes-from",
     "volumes": [
       {
         "name": "empty",
         "host": {}
       },
       {
         "name": "host_etc",
         "host": {
           "sourcePath": "/etc"
         }
       }
     ],
   ```

   Na seção definições de contêiner, crie um contêiner que monte os volumes definidos anteriormente. Neste exemplo, o contêiner `web` monta os volumes `empty` e `host_etc`. Este é o contêiner que utiliza a imagem criada com um volume no Dockerfile.

   ```
   "containerDefinitions": [
       {
         "name": "web",
         "image": "my-repo/httpd_dockerfile_volume",
         "cpu": 100,
         "memory": 500,
         "portMappings": [
           {
             "containerPort": 80,
             "hostPort": 80
           }
         ],
         "mountPoints": [
           {
             "sourceVolume": "empty",
             "containerPath": "/usr/local/apache2/htdocs/empty_volume"
           },
           {
             "sourceVolume": "host_etc",
             "containerPath": "/usr/local/apache2/htdocs/host_etc"
           }
         ],
         "essential": true
       },
   ```

   Crie outro contêiner que use `volumesFrom` para montar todos os volumes que estão associados com o contêiner `web`. Todos os volumes no contêiner `web` também são montados no contêiner `busybox`. Isso inclui o volume especificado no Dockerfile que foi utilizado para criar a imagem `my-repo/httpd_dockerfile_volume`.

   ```
       {
         "name": "busybox",
         "image": "busybox",
         "volumesFrom": [
           {
             "sourceContainer": "web"
           }
         ],
         "cpu": 100,
         "memory": 500,
         "entryPoint": [
           "sh",
           "-c"
         ],
         "command": [
           "echo $(date) > /usr/local/apache2/htdocs/empty_volume/date && echo $(date) > /usr/local/apache2/htdocs/host_etc/date && echo $(date) > /usr/local/apache2/htdocs/dockerfile_volume/date"
         ],
         "essential": false
       }
     ]
   }
   ```

   Quando essa tarefa é executada, os dois contêineres montam os volumes, e o `command` no contêiner `busybox` grava a data e a hora em um arquivo. Esse arquivo se chama `date` em cada uma das pastas de volume. As pastas ficam visíveis no site exibido pelo contêiner `web`.
**nota**  
Como o contêiner `busybox` executa um comando rápido e, em seguida, é encerrado, ele deve ser definido como `"essential": false` na definição do contêiner. Caso contrário, ele interromperá toda a tarefa quando for encerrado.