Também estou em um estado de migração da infraestrutura existente da AWS para o Terraform, então terei como objetivo atualizar a resposta à medida que desenvolvo.
Tenho confiado muito nos exemplos oficiais do Terraform e em várias tentativas e erros para detalhar áreas nas quais não tenho certeza.
.tfstate
arquivos
A configuração do Terraform pode ser usada para provisionar muitas caixas em diferentes infraestruturas, cada uma delas com um estado diferente. Como também pode ser executado por várias pessoas, esse estado deve estar em um local centralizado (como S3), mas não git.
Isso pode ser confirmado olhando para o Terraform .gitignore
.
Controle do desenvolvedor
Nosso objetivo é fornecer mais controle da infraestrutura aos desenvolvedores, mantendo uma auditoria completa (git log) e a capacidade de verificar a integridade das alterações (solicitações pull). Com isso em mente, o novo fluxo de trabalho de infraestrutura que pretendo é:
- Base básica de AMIs comuns que incluem módulos reutilizáveis, por exemplo, fantoches.
- Infraestrutura central provisionada pelo DevOps usando Terraform.
- Os desenvolvedores alteram a configuração do Terraform no Git conforme necessário (número de instâncias; novo VPC; adição de região / zona de disponibilidade etc.).
- A configuração Git foi enviada por push e uma solicitação de pull foi enviada para ser verificada por um membro do esquadrão DevOps.
- Se aprovado, chama webhook para CI para construir e implantar (sem saber como particionar vários ambientes neste momento)
Edição 1 - Atualização do estado atual
Desde que comecei esta resposta, escrevi muito código TF e me sinto mais confortável em nosso estado de coisas. Encontramos bugs e restrições ao longo do caminho, mas eu aceito que essa é uma característica de usar um software novo que muda rapidamente.
Layout
Temos uma infraestrutura AWS complicada com vários VPCs, cada um com várias sub-redes. A chave para gerenciar isso facilmente foi definir uma taxonomia flexível que engloba região, ambiente, serviço e proprietário, que podemos usar para organizar nosso código de infraestrutura (terraform e fantoche).
Módulos
O próximo passo foi criar um único repositório git para armazenar nossos módulos de terraform. Nossa estrutura de diretório de nível superior para os módulos se parece com isto:
tree -L 1 .
Resultado:
├── README.md
├── aws-asg
├── aws-ec2
├── aws-elb
├── aws-rds
├── aws-sg
├── aws-vpc
└── templates
Cada um define alguns padrões lógicos, mas os expõe como variáveis que podem ser substituídas por nossa "cola".
Cola
Temos um segundo repositório com o nosso glue
que faz uso dos módulos mencionados acima. Ele é apresentado de acordo com nosso documento de taxonomia:
.
├── README.md
├── clientA
│ ├── eu-west-1
│ │ └── dev
│ └── us-east-1
│ └── dev
├── clientB
│ ├── eu-west-1
│ │ ├── dev
│ │ ├── ec2-keys.tf
│ │ ├── prod
│ │ └── terraform.tfstate
│ ├── iam.tf
│ ├── terraform.tfstate
│ └── terraform.tfstate.backup
└── clientC
├── eu-west-1
│ ├── aws.tf
│ ├── dev
│ ├── iam-roles.tf
│ ├── ec2-keys.tf
│ ├── prod
│ ├── stg
│ └── terraform.tfstate
└── iam.tf
Dentro do nível do cliente, temos .tf
arquivos específicos da conta da AWS que provisionam recursos globais (como funções de IAM); a seguir está o nível de região com as chaves públicas SSH EC2; Finalmente, em nosso ambiente ( dev
, stg
, prod
etc) são a nossa setups VPC, a criação da instância e olhando conexões etc, são armazenados.
Nota lateral: Como você pode ver, estou indo contra meu próprio conselho acima de manter o terraform.tfstate
git. Esta é uma medida temporária até que eu mude para o S3, mas é adequado para mim, pois sou atualmente o único desenvolvedor.
Próximos passos
Este ainda é um processo manual e não está no Jenkins, mas estamos portando uma infraestrutura bastante grande e complicada e até agora tudo bem. Como eu disse, poucos bugs mas indo bem!
Editar 2 - Mudanças
Já se passou quase um ano desde que escrevi esta resposta inicial e o estado do Terraform e de mim mudou significativamente. Agora estou em uma nova posição usando o Terraform para gerenciar um cluster do Azure e o Terraform está agora v0.10.7
.
Estado
As pessoas me disseram repetidamente que o estado não deve ser usado no Git - e estão corretas. Usamos isso como uma medida provisória com uma equipe de duas pessoas que dependia da comunicação e disciplina do desenvolvedor. Com uma equipe maior e distribuída, agora estamos aproveitando totalmente o estado remoto no S3 com bloqueio fornecido pelo DynamoDB. Idealmente, isso será migrado para o cônsul agora que é v1.0 para cortar provedores de nuvem cruzada.
Módulos
Anteriormente, criamos e usamos módulos internos. Esse ainda é o caso, mas com o advento e crescimento do registro Terraform , tentamos usá-lo como pelo menos uma base.
Estrutura de arquivo
A nova posição tem uma taxonomia muito mais simples com apenas dois ambientes infx - dev
e prod
. Cada um tem suas próprias variáveis e saídas, reutilizando nossos módulos criados acima. O remote_state
provedor também ajuda no compartilhamento de saídas de recursos criados entre ambientes. Nosso cenário é de subdomínios em diferentes grupos de recursos do Azure para um TLD gerenciado globalmente.
├── main.tf
├── dev
│ ├── main.tf
│ ├── output.tf
│ └── variables.tf
└── prod
├── main.tf
├── output.tf
└── variables.tf
Planejamento
Novamente com os desafios extras de uma equipe distribuída, agora sempre salvamos nossa saída do terraform plan
comando. Podemos inspecionar e saber o que será executado sem o risco de algumas alterações entre o estágio plan
e apply
(embora o bloqueio ajude nisso). Lembre-se de excluir este arquivo de plano, pois ele pode conter variáveis "secretas" de texto simples.
No geral, estamos muito felizes com o Terraform e continuamos a aprender e melhorar com os novos recursos adicionados.
Usamos muito o Terraform e nossa configuração recomendada é a seguinte:
Layout de arquivo
É altamente recomendável armazenar o código do Terraform para cada um de seus ambientes (por exemplo, stage, prod, qa) em conjuntos separados de modelos (e, portanto,
.tfstate
arquivos separados ). Isso é importante para que seus ambientes separados fiquem realmente isolados uns dos outros durante as alterações. Caso contrário, ao mexer com algum código na preparação, é muito fácil explodir algo na produção também. Consulte Terraform, VPC e por que você deseja um arquivo tfstate por env para uma discussão colorida sobre o motivo.Portanto, nosso layout de arquivo típico é assim:
Todo o código do Terraform para o VPC de estágio vai para a
stage
pasta, todo o código para o VPC do produto vai para aprod
pasta e todo o código que reside fora de um VPC (por exemplo, usuários IAM, tópicos SNS, buckets S3) vai para aglobal
pasta .Observe que, por convenção, normalmente dividimos nosso código Terraform em três arquivos:
vars.tf
: Variáveis de entrada.outputs.tf
: Variáveis de saída.main.tf
: Os recursos reais.Módulos
Normalmente, definimos nossa infraestrutura em duas pastas:
infrastructure-modules
: Esta pasta contém módulos pequenos e reutilizáveis com versão. Pense em cada módulo como um plano de como criar uma única peça de infraestrutura, como um VPC ou um banco de dados.infrastructure-live
: Esta pasta contém a infraestrutura real em execução, que ele cria combinando os módulos eminfrastructure-modules
. Pense no código nesta pasta como as casas reais que você construiu a partir de seus projetos.Um módulo Terraform é qualquer conjunto de modelos Terraform em uma pasta. Por exemplo, podemos ter uma pasta chamada
vpc
eminfrastructure-modules
que define todas as tabelas de rota, sub-redes, gateways, ACLs, etc. para um único VPC:Podemos, então, usar esse módulo em
infrastructure-live/stage
einfrastructure-live/prod
para criar as VPCs palco e prod. Por exemplo,infrastructure-live/stage/main.tf
pode ser assim:Para usar um módulo, você usa o
module
recurso e aponta seusource
campo para um caminho local em seu disco rígido (por exemplosource = "../infrastructure-modules/vpc"
) ou, como no exemplo acima, uma URL Git (consulte as fontes do módulo ). A vantagem da URL Git é que podemos especificar um git sha1 ou tag (ref=v0.0.4
) específico. Agora, não apenas definimos nossa infraestrutura como um monte de pequenos módulos, mas podemos criar uma versão desses módulos e atualizar ou reverter com cuidado, conforme necessário.Criamos uma série de pacotes de infraestrutura reutilizáveis, testados e documentados para a criação de VPCs, clusters Docker, bancos de dados e assim por diante, e nos bastidores, a maioria deles são apenas módulos do Terraform com versão.
Estado
Quando você usa o Terraform para criar recursos (por exemplo, instâncias EC2, bancos de dados, VPCs), ele registra informações sobre o que foi criado em um
.tfstate
arquivo. Para fazer alterações nesses recursos, todos em sua equipe precisam acessar este mesmo.tfstate
arquivo, mas você NÃO deve verificá-lo no Git (veja aqui uma explicação do porquê ).Em vez disso, recomendamos armazenar
.tfstate
arquivos no S3 ativando o Terraform Remote State , que enviará / extrairá automaticamente os arquivos mais recentes sempre que você executar o Terraform. Certifique-se de habilitar o controle de versão em seu balde S3 para que você possa reverter para.tfstate
arquivos mais antigos no caso de de alguma forma corromper a versão mais recente. No entanto, uma observação importante: o Terraform não fornece bloqueio . Portanto, se dois membros da equipe executamterraform apply
ao mesmo tempo no mesmo.tfstate
arquivo, eles podem acabar substituindo as alterações um do outro.Para resolver esse problema, criamos uma ferramenta de código aberto chamada Terragrunt , que é um wrapper fino para Terraform que usa o Amazon DynamoDB para fornecer bloqueio (que deve ser totalmente gratuito para a maioria das equipes). Confira Adicionar bloqueio automático de estado remoto e configuração ao Terraform com Terragrunt para obter mais informações.
Leitura adicional
Acabamos de começar uma série de postagens no blog chamada A Comprehensive Guide to Terraform que descreve em detalhes todas as melhores práticas que aprendemos para usar o Terraform no mundo real.
Atualização: a série de postagens do blog Guia abrangente para o Terraform se tornou tão popular que a expandimos em um livro chamado Terraform: Up & Running !
fonte
remote config
se acabou de verificar as configurações do Terraform ou se deseja alterar uma configuração remota anterior. O Terraform 0.9 apresentará o conceito debackends
, o que simplificará muito isso. Veja este PR para mais detalhes.remote config
comando para apontar para o estado de produção. Supondo um estado diferente por ambiente. Isso está certo? Estou ansioso para v0.9..tf
arquivos em dois ambientes diferentes, sim, você precisaria executarremote config
cada vez que alternasse. Obviamente, isso é muito sujeito a erros, portanto, não recomendo o uso dessa técnica. Em vez disso, verifique o layout do arquivo Terraform recomendado nesta postagem do blog, juntamente com como usar os módulos do Terraform nesta postagem do blog .remote config
Permitido anteriormente, mas agora foi substituído por " backends ", então o terraform remote não está mais disponível.Veja a documentação para detalhes.
fonte
Abordado com mais detalhes por @Yevgeny Brikman, mas respondendo especificamente às perguntas do OP:
Use git para arquivos TF. Mas não verifique os arquivos de estado em (ou seja, tfstate). Em vez disso, use
Terragrunt
para sincronização / bloqueio de arquivos de estado para S3.Não.
sim
fonte
Eu sei que há muitas respostas aqui, mas minha abordagem é bem diferente.
Módulos
Gestão ambiental
IaC tornou o processo SDLC relevante para o gerenciamento de infraestrutura e não é normal esperar ter infraestrutura de desenvolvimento, bem como ambientes de aplicativos de desenvolvimento.
Separação de deveres
Se você estiver em uma pequena organização ou administrando uma infraestrutura pessoal, isso não se aplica realmente, mas o ajudará a gerenciar suas operações.
Isso também ajuda com as questões de liberação, pois você descobrirá que alguns recursos raramente mudam, enquanto outros mudam o tempo todo. A separação remove o risco e a complexidade.
Essa estratégia traça paralelos com a estratégia de várias contas da AWS. Leia para mais informações.
CI / CD
Este é um tópico à parte, mas o Terraform funciona muito bem dentro de um bom pipeline. O erro mais comum aqui é tratar o IC como uma solução mágica. Tecnicamente, o Terraform deve provisionar infraestrutura apenas durante os estágios de um pipeline de montagem. Isso seria diferente do que acontece nos estágios de CI, onde normalmente se valida e testa os modelos.
NB escrito no celular, desculpe quaisquer erros.
fonte
Recomendações comuns para estruturar código
É mais fácil e rápido trabalhar com menor número de recursos:
terraform plan
e oterraform
apply fazem chamadas de API em nuvem para verificar o status dos recursos.O raio da explosão é menor com menos recursos:
Comece seu projeto usando o estado remoto:
tfstate
arquivo no git é um pesadelo.Tente praticar uma estrutura consistente e convenção de nomenclatura:
Mantenha os módulos de recursos o mais simples possível.
Não codifique valores que podem ser passados como variáveis ou descobertos usando fontes de dados.
Use
data
fontes e,terraform_remote_state
especificamente, como uma cola entre os módulos de infraestrutura dentro da composição.( artigo de referência: https://www.terraform-best-practices.com/code-structure )
Exemplo:
NOTA: apenas como referência não deve ser seguida à risca visto que cada projeto possui características próprias
fonte
Acredito que haja poucas práticas recomendadas a serem seguidas ao usar o terraform para orquestrar a infraestrutura
Lidar com vários ambientes
Na maioria das vezes, a forma recomendada é usar o 'espaço de trabalho' do terraform para lidar com vários ambientes, mas acredito que o uso do espaço de trabalho pode variar de acordo com a forma de trabalho em uma organização. Outra é armazenar o código do Terraform para cada um de seus ambientes (por exemplo, stage, prod, QA) para separar os estados do ambiente. No entanto, neste caso, estamos apenas copiando o mesmo código em muitos lugares.
Eu segui uma abordagem diferente para lidar e evitar a duplicação do mesmo código de terraform, mantendo em cada pasta de ambiente, pois acredito que na maioria das vezes todos os ambientes seriam 90% iguais.
Configuração relacionada a ambientes
Mantenha a configuração e os parâmetros relacionados ao ambiente separados em um arquivo de variável e passe esse valor para configurar a infraestrutura. por exemplo, como abaixo
dev.backend.tfvar
dev.variable.tfvar
Ignorando condicionalmente a parte da infraestrutura
Crie uma configuração em um arquivo de variável específico de env e com base nessa variável decida criar ou pular essa parte. Desta forma, com base na necessidade, a parte específica da infraestrutura pode ser ignorada.
O comando abaixo é necessário para inicializar e executar as mudanças de infra para cada ambiente, cd para a pasta de ambiente necessária.
fonte
Não gosto da ideia de subpastas porque isso resultará em fontes diferentes por ambiente e isso tende a se desviar.
A melhor abordagem é ter uma única pilha para todos os ambientes (digamos dev, preprod e prod). Para trabalhar em um único ambiente de uso
terraform workspace
.Isso cria um novo espaço de trabalho. Isso inclui um arquivo de estado dedicado e a variável que
terraform.workspace
você pode usar em seu código.Desta forma, você obterá baldes chamados
depois de se inscrever nas áreas de trabalho acima (use
terraform workspace select <WORKSPACE>
para alterar ambientes). Para tornar o código ainda à prova de multirregiões, faça assim:obter (para a região us-east-1)
fonte
Algumas práticas recomendadas do Terraform a serem seguidas:
Evite a codificação permanente: às vezes, os desenvolvedores criam recursos manualmente de maneira direta. Você precisa marcar esses recursos e usar a importação de terreno para incluí-los nos códigos. Uma amostra:
account_number = “123456789012" account_alias = "mycompany"
Execute o Terraform de um contêiner do Docker: o Terraform lança um contêiner oficial do Docker que permite controlar facilmente qual versão pode ser executada.
É recomendado executar o contêiner Terraform Docker ao definir seu trabalho de compilação no pipeline de CI / CD.
Para obter mais informações, consulte meu blog: https://medium.com/tech-darwinbox/how-darwinbox-manages-infrastructure-at-scale-with-terraform-371e2c5f04d3
fonte
Eu gostaria de contribuir com este tópico.
Em alguns casos especiais, será necessário acesso manual aos arquivos de estado do Terraform. Coisas como refatorar, interromper alterações ou corrigir defeitos exigirão a execução de operações de estado do Terraform pelo pessoal de operações. Para tais ocasiões, planeje um acesso controlado extraordinário ao estado do Terraform usando o host bastião, VPN etc.
Verifique um blog de práticas recomendadas mais longo que cobre isso em detalhes, incluindo diretrizes para pipelines de CI / CD.
fonte
Se você ainda estiver procurando por uma solução melhor, dê uma olhada nos espaços de trabalho que podem substituir a manutenção de uma estrutura de pasta de ambiente diferente que pode ter variáveis específicas do espaço de trabalho.
Como Yevgeniy Brikman mencionou , é melhor ter uma estrutura de módulos.
fonte
Use a nuvem terraform para gerenciar e salvar estados, juntamente com os conselhos acima.
fonte