Ich bin auch in der Lage, die vorhandene AWS-Infrastruktur auf Terraform zu migrieren. Daher werde ich versuchen, die Antwort während meiner Entwicklung zu aktualisieren.
Ich habe mich stark auf die offiziellen Terraform- Beispiele und das mehrfache Ausprobieren verlassen, um Bereiche zu konkretisieren, in denen ich unsicher war.
.tfstate
Dateien
Die Terraform-Konfiguration kann verwendet werden, um viele Boxen in unterschiedlichen Infrastrukturen bereitzustellen, von denen jede einen anderen Status haben kann. Da dieser Status auch von mehreren Personen ausgeführt werden kann, sollte er sich an einem zentralen Ort (wie S3) befinden, jedoch nicht an Git.
Dies kann anhand der Terraform bestätigt werden .gitignore
.
Entwicklersteuerung
Unser Ziel ist es, Entwicklern eine bessere Kontrolle über die Infrastruktur zu bieten und gleichzeitig ein vollständiges Audit (Git-Protokoll) und die Möglichkeit zur Überprüfung von Änderungen (Pull-Anforderungen) aufrechtzuerhalten. Vor diesem Hintergrund strebe ich einen neuen Infrastruktur-Workflow an:
- Basisgrundlage für gängige AMIs, die wiederverwendbare Module enthalten, z. B. Marionetten.
- Von DevOps mithilfe von Terraform bereitgestellte Kerninfrastruktur.
- Entwickler ändern die Terraform-Konfiguration in Git nach Bedarf (Anzahl der Instanzen; neue VPC; Hinzufügen einer Region / Verfügbarkeitszone usw.).
- Die Git-Konfiguration wurde gepusht und eine Pull-Anfrage wurde von einem Mitglied des DevOps-Teams auf ihre Richtigkeit überprüft.
- Wenn dies genehmigt wird, ruft Webhook zum Erstellen und Bereitstellen von CI auf (unsicher, wie mehrere Umgebungen zu diesem Zeitpunkt partitioniert werden sollen).
Bearbeiten 1 - Aktueller Status aktualisieren
Seit ich mit dieser Antwort angefangen habe, habe ich viel TF-Code geschrieben und fühle mich in unserem Zustand wohler. Wir haben auf dem Weg Fehler und Einschränkungen festgestellt, aber ich akzeptiere, dass dies ein Merkmal der Verwendung neuer, sich schnell ändernder Software ist.
Layout
Wir haben eine komplizierte AWS-Infrastruktur mit mehreren VPCs mit jeweils mehreren Subnetzen. Der Schlüssel zur einfachen Verwaltung bestand darin, eine flexible Taxonomie zu definieren, die Region, Umgebung, Service und Eigentümer umfasst und mit der wir unseren Infrastrukturcode (sowohl Terraform als auch Marionette) organisieren können.
Module
Der nächste Schritt bestand darin, ein einzelnes Git-Repository zum Speichern unserer Terraform-Module zu erstellen. Unsere oberste Verzeichnisstruktur für die Module sieht folgendermaßen aus:
tree -L 1 .
Ergebnis:
├── README.md
├── aws-asg
├── aws-ec2
├── aws-elb
├── aws-rds
├── aws-sg
├── aws-vpc
└── templates
Jeder legt einige vernünftige Standardeinstellungen fest, macht sie jedoch als Variablen verfügbar, die von unserem "Kleber" überschrieben werden können.
Kleben
Wir haben ein zweites Repository mit unserem glue
, das die oben genannten Module verwendet. Es ist in Übereinstimmung mit unserem Taxonomiedokument angelegt:
.
├── 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
Innerhalb der Client-Ebene verfügen wir über AWS-kontospezifische .tf
Dateien, die globale Ressourcen bereitstellen (z. B. IAM-Rollen). Als nächstes folgt die Regionsebene mit öffentlichen EC2-SSH-Schlüsseln. Schließlich in unserer Umgebung ( dev
, stg
, prod
usw.) sind unsere VPC - Setups, zB Erstellung und Peering - Verbindungen usw. gespeichert sind.
Randnotiz: Wie Sie sehen können, widerspreche ich meinem eigenen Rat, wenn ich mich terraform.tfstate
an Git halte. Dies ist eine vorübergehende Maßnahme, bis ich zu S3 wechsle, passt aber zu mir, da ich derzeit der einzige Entwickler bin.
Nächste Schritte
Dies ist immer noch ein manueller Prozess und noch nicht in Jenkins, aber wir portieren eine ziemlich große, komplizierte Infrastruktur und bisher so gut. Wie gesagt, ein paar Bugs, aber es läuft gut!
Bearbeiten 2 - Änderungen
Es ist fast ein Jahr her, seit ich diese erste Antwort geschrieben habe, und der Zustand von Terraform und mir hat sich erheblich verändert. Ich bin jetzt an einer neuen Position und verwende Terraform zum Verwalten eines Azure-Clusters. Terraform ist jetzt v0.10.7
.
Zustand
Die Leute haben mir wiederholt gesagt, dass der Staat nicht in Git gehen soll - und sie sind korrekt. Wir haben dies als Zwischenmaßnahme für ein Zwei-Personen-Team verwendet, das sich auf die Kommunikation und Disziplin der Entwickler stützte. Mit einem größeren, verteilten Team nutzen wir jetzt den Remote-Status in S3 vollständig mit Sperren, die von DynamoDB bereitgestellt werden. Im Idealfall wird dies auf Consul migriert, jetzt ist es Version 1.0, um Cloud-übergreifende Anbieter zu kürzen.
Module
Zuvor haben wir interne Module erstellt und verwendet. Dies ist immer noch der Fall, aber mit dem Aufkommen und Wachstum der Terraform-Registrierung versuchen wir, diese zumindest als Basis zu verwenden.
Dateistruktur
Die neue Position hat eine viel einfachere Taxonomie mit nur zwei Infx-Umgebungen - dev
und prod
. Jedes hat seine eigenen Variablen und Ausgänge, wobei unsere oben erstellten Module wiederverwendet werden. Der remote_state
Anbieter hilft auch beim Teilen von Ausgaben erstellter Ressourcen zwischen Umgebungen. In unserem Szenario handelt es sich um Subdomänen in verschiedenen Azure-Ressourcengruppen zu einer global verwalteten TLD.
├── main.tf
├── dev
│ ├── main.tf
│ ├── output.tf
│ └── variables.tf
└── prod
├── main.tf
├── output.tf
└── variables.tf
Planung
Mit den zusätzlichen Herausforderungen eines verteilten Teams speichern wir jetzt immer unsere Ausgabe des terraform plan
Befehls. Wir können überprüfen und wissen, was ausgeführt wird, ohne dass das Risiko von Änderungen zwischen der plan
und der apply
Bühne besteht (obwohl das Sperren dabei hilft). Denken Sie daran, diese Plandatei zu löschen, da sie möglicherweise "geheime" Variablen im Klartext enthalten kann.
Insgesamt sind wir sehr zufrieden mit Terraform und lernen und verbessern uns weiter mit den neuen Funktionen.
Wir verwenden Terraform häufig und empfehlen folgende Einstellungen:
Dateilayout
Wir empfehlen dringend, den Terraform-Code für jede Ihrer Umgebungen (z. B. Stage, Prod, QA) in separaten Vorlagensätzen (und daher in separaten
.tfstate
Dateien) zu speichern. Dies ist wichtig, damit Ihre separaten Umgebungen beim Vornehmen von Änderungen tatsächlich voneinander isoliert sind. Andernfalls ist es zu einfach, etwas in Prod in die Luft zu jagen, während Sie beim Staging mit Code herumspielen. Unter Terraform, VPC und warum Sie eine tfstate-Datei pro env benötigen, finden Sie eine farbenfrohe Diskussion darüber, warum.Daher sieht unser typisches Dateilayout folgendermaßen aus:
Der gesamte Terraform-Code für die Stage-VPC wird in den
stage
Ordner verschoben , der gesamte Code für die Produkt-VPC wird in denprod
Ordner verschoben , und der gesamte Code, der außerhalb einer VPC gespeichert ist (z. B. IAM-Benutzer, SNS-Themen, S3-Buckets), wird in denglobal
Ordner verschoben .Beachten Sie, dass wir unseren Terraform-Code normalerweise in drei Dateien aufteilen:
vars.tf
: Eingangsvariablen.outputs.tf
: Ausgabevariablen.main.tf
: Die tatsächlichen Ressourcen.Module
Normalerweise definieren wir unsere Infrastruktur in zwei Ordnern:
infrastructure-modules
: Dieser Ordner enthält kleine, wiederverwendbare, versionierte Module. Stellen Sie sich jedes Modul als Blaupause für die Erstellung einer einzelnen Infrastruktur vor, z. B. einer VPC oder einer Datenbank.infrastructure-live
: Dieser Ordner enthält die aktuelle Live-Infrastruktur, die durch Kombinieren der Module erstellt wirdinfrastructure-modules
. Stellen Sie sich den Code in diesem Ordner als die tatsächlichen Häuser vor, die Sie aus Ihren Bauplänen gebaut haben.Ein Terraform-Modul ist nur ein beliebiger Satz von Terraform-Vorlagen in einem Ordner. Zum Beispiel könnten wir einen Ordner mit dem Namen haben
vpc
ininfrastructure-modules
dem definiert , all Routing - Tabellen, Subnetzen, Gateways, ACLs, etc. für einen einzelnen VPC:Wir können dieses Modul dann in
infrastructure-live/stage
und verwendeninfrastructure-live/prod
, um die Stage- und Prod-VPCs zu erstellen. Soinfrastructure-live/stage/main.tf
könnte beispielsweise aussehen:Um ein Modul zu verwenden, verwenden Sie die
module
Ressource und verweisen ihrsource
Feld entweder auf einen lokalen Pfad auf Ihrer Festplatte (z. B.source = "../infrastructure-modules/vpc"
) oder, wie im obigen Beispiel, auf eine Git-URL (siehe Modulquellen ). Der Vorteil der Git-URL ist, dass wir ein bestimmtes git sha1 oder tag (ref=v0.0.4
) angeben können . Jetzt definieren wir unsere Infrastruktur nicht nur als eine Reihe kleiner Module, sondern können diese Module auch versionieren und bei Bedarf sorgfältig aktualisieren oder zurücksetzen.Wir haben eine Reihe wiederverwendbarer, getesteter und dokumentierter Infrastrukturpakete zum Erstellen von VPCs, Docker-Clustern, Datenbanken usw. erstellt. Unter der Haube sind die meisten nur versionierte Terraform-Module.
Zustand
Wenn Sie Terraform zum Erstellen von Ressourcen verwenden (z. B. EC2-Instanzen, Datenbanken, VPCs), werden Informationen darüber aufgezeichnet, was in einer
.tfstate
Datei erstellt wurde. Um Änderungen an diesen Ressourcen vorzunehmen, muss jeder in Ihrem Team auf dieselbe.tfstate
Datei zugreifen. Sie sollten sie jedoch NICHT in Git einchecken ( eine Erklärung finden Sie hier ).Stattdessen empfehlen wir,
.tfstate
Dateien in S3 zu speichern , indem Sie Terraform Remote State aktivieren , das bei jedem Ausführen von Terraform automatisch die neuesten Dateien pusht / zieht. Stellen Sie sicher, dass die Versionierung in Ihrem S3-Bucket aktiviert ist, damit Sie auf ältere.tfstate
Dateien zurückgreifen können, falls Sie die neueste Version irgendwie beschädigen. Ein wichtiger Hinweis: Terraform bietet keine Verriegelung . Wenn also zwei Teammitgliederterraform apply
gleichzeitig in derselben.tfstate
Datei ausgeführt werden, überschreiben sie möglicherweise die Änderungen des jeweils anderen.Um dieses Problem zu lösen, haben wir ein Open-Source-Tool namens Terragrunt erstellt , ein Thin Wrapper für Terraform, der Amazon DynamoDB verwendet, um Sperren bereitzustellen (was für die meisten Teams völlig kostenlos sein sollte). Weitere Informationen finden Sie unter Hinzufügen einer automatischen Remote-Status-Sperre und -Konfiguration zu Terraform mit Terragrunt .
Weiterführende Literatur
Wir haben gerade eine Reihe von Blog-Posts mit dem Titel " Ein umfassender Leitfaden für Terraform" gestartet , in denen alle Best Practices, die wir für die Verwendung von Terraform in der realen Welt gelernt haben, ausführlich beschrieben werden.
Update: Der umfassende Leitfaden zu Terraform-Blogpostserien wurde so populär, dass wir ihn zu einem Buch namens Terraform: Up & Running !
quelle
remote config
wenn Sie gerade Ihre Terraform-Konfigurationen ausgecheckt haben oder wenn Sie eine vorherige Remote-Konfiguration ändern möchten. Terraform 0.9 wird das Konzept von einführenbackends
, das vieles davon vereinfacht. Weitere Informationen finden Sie in dieser PR .remote config
Befehl erneut ausführen , um auf den Prod-Status zu zeigen. Unter der Annahme eines unterschiedlichen Zustands pro Umgebung. Ist das richtig? Ich freue mich auf v0.9..tf
Dateisatz in zwei verschiedenen Umgebungen bereitstellen möchten, müssen Sie ihn beiremote config
jedem Wechsel ausführen . Dies ist offensichtlich sehr fehleranfällig, daher empfehle ich nicht, diese Technik tatsächlich zu verwenden. Lesen Sie stattdessen das empfohlene Terraform-Dateilayout in diesem Blog-Beitrag sowie die Verwendung von Terraform-Modulen in diesem Blog-Beitrag .Früher
remote config
erlaubt, jetzt aber durch " Backends " ersetzt, so dass Terraform Remote nicht mehr verfügbar ist.Einzelheiten finden Sie in den Dokumenten .
quelle
Ausführlicher von @Yevgeny Brikman behandelt, aber speziell auf die Fragen des OP geantwortet:
Verwenden Sie git für TF-Dateien. Aber checken Sie keine Statusdateien ein (dh tfstate). Verwenden Sie stattdessen
Terragrunt
zum Synchronisieren / Sperren von Statusdateien mit S3.Nein.
Ja
quelle
Ich weiß, dass es hier viele Antworten gibt, aber mein Ansatz ist ganz anders.
Module
Umweltmanagement
IaC hat den SDLC-Prozess für das Infrastrukturmanagement relevant gemacht, und es ist nicht normal, dass sowohl Entwicklungsinfrastruktur als auch Entwicklungsanwendungsumgebungen vorhanden sind.
Aufgabentrennung
Wenn Sie sich in einer kleinen Organisation befinden oder eine persönliche Infrastruktur betreiben, trifft dies nicht wirklich zu, hilft Ihnen jedoch bei der Verwaltung Ihrer Vorgänge.
Dies hilft auch bei Release-Problemen, da sich einige Ressourcen selten ändern, während sich andere ständig ändern. Durch die Trennung werden Risiken und Komplexität beseitigt.
Diese Strategie weist Parallelen zur Multi-Account-Strategie von AWS auf. Lesen Sie für weitere Informationen.
CI / CD
Dies ist ein eigenes Thema, aber Terraform funktioniert sehr gut in einer guten Pipeline. Der häufigste Fehler besteht darin, CI als Silberkugel zu behandeln. Technisch gesehen sollte Terraform die Infrastruktur nur in Phasen einer Montagepipeline bereitstellen. Dies würde sich von dem unterscheiden, was in CI-Phasen geschieht, in denen die Vorlagen normalerweise validiert und getestet werden.
NB Geschrieben auf dem Handy, entschuldigen Sie bitte alle Fehler.
quelle
Allgemeine Empfehlungen zur Strukturierung von Code
Es ist einfacher und schneller, mit einer geringeren Anzahl von Ressourcen zu arbeiten:
terraform plan
undterraform
apply führen beide Cloud-API-Aufrufe durch, um den Status der Ressourcen zu überprüfen.Der Explosionsradius ist mit weniger Ressourcen kleiner:
Starten Sie Ihr Projekt mit dem Remote-Status:
tfstate
Datei in Git ist ein Albtraum.Versuchen Sie, eine konsistente Struktur- und Namenskonvention zu üben:
Halten Sie Ressourcenmodule so einfach wie möglich.
Nicht schwer Code Werte , die als Variablen übergeben werden können oder entdeckt Datenquellen.
Verwenden Sie
data
Quellen undterraform_remote_state
insbesondere als Klebstoff zwischen Infrastrukturmodulen innerhalb der Komposition.( siehe Artikel: https://www.terraform-best-practices.com/code-structure )
Beispiel:
HINWEIS: Nur als Referenz, die nicht unbedingt befolgt werden muss, da jedes Projekt seine eigenen spezifischen Merkmale aufweist
quelle
Ich glaube, es gibt nur wenige Best Practices, die bei der Verwendung von Terraform für die Orchestrierung der Infrastruktur befolgt werden müssen
Behandeln Sie mehrere Umgebungen
In den meisten Fällen wird empfohlen, den Terraform-Arbeitsbereich für die verschiedenen Umgebungen zu verwenden. Ich glaube jedoch, dass die Verwendung des Arbeitsbereichs je nach Arbeitsweise in einer Organisation variieren kann. Andere speichern den Terraform-Code für jede Ihrer Umgebungen (z. B. Stufe, Produkt, Qualitätssicherung), um die Umgebungszustände zu trennen. In diesem Fall kopieren wir jedoch nur an vielen Stellen denselben Code.
Ich verfolgte einen anderen Ansatz, um das Duplizieren desselben Terraform-Codes zu handhaben und zu vermeiden, indem ich in jedem Umgebungsordner behielt, da ich glaube, dass die gesamte Umgebung zu 90% gleich ist.
Konfiguration in Bezug auf Umgebungen
Halten Sie die umgebungsbezogene Konfiguration und Parameter in einer variablen Datei getrennt und übergeben Sie diesen Wert, um die Infrastruktur zu konfigurieren. zB wie unten
dev.backend.tfvar
dev.variable.tfvar
Bedingtes Überspringen des Infrastrukturteils
Erstellen Sie eine Konfiguration in einer env-spezifischen Variablendatei und entscheiden Sie sich basierend auf dieser Variablen, diesen Teil zu erstellen oder zu überspringen. Auf diese Weise kann je nach Bedarf der spezifische Teil der Infrastruktur übersprungen werden.
Der folgende Befehl ist erforderlich, um die Infra-Änderungen für jede Umgebung zu initialisieren und auszuführen. CD in den erforderlichen Umgebungsordner.
quelle
Ich mag die Idee von Unterordnern nicht, da dies zu unterschiedlichen Quellen pro Umgebung führt und dazu neigt, zu driften.
Der bessere Ansatz besteht darin, einen einzigen Stapel für alle Umgebungen zu haben (sagen wir dev, preprod und prod). Verwenden Sie zum Arbeiten in einer einzelnen Umgebung
terraform workspace
.Dadurch wird ein neuer Arbeitsbereich erstellt. Dies umfasst eine dedizierte Statusdatei und die Variable, die
terraform.workspace
Sie in Ihrem Code verwenden können.Auf diese Weise erhalten Sie Eimer aufgerufen
nach dem Anwenden auf die oben genannten Arbeitsbereiche (
terraform workspace select <WORKSPACE>
zum Ändern von Umgebungen verwenden). Um den Code noch mehrregionssicher zu machen, gehen Sie folgendermaßen vor:zu bekommen (für uns-Ost-1 Region)
quelle
Einige bewährte Methoden für Terraform:
Vermeiden Sie harte Codierung: Manchmal haben Entwickler Ressourcen direkt manuell erstellt. Sie müssen diese Ressource markieren und den Terraform-Import verwenden, um sie in Codes aufzunehmen. Eine Probe:
account_number = "123456789012" account_alias = "mycompany"
Ausführen von Terraform aus einem Docker-Container: Terraform gibt einen offiziellen Docker-Container frei, mit dem Sie einfach steuern können, welche Version Sie ausführen können.
Es wird empfohlen, den Terraform Docker-Container auszuführen, wenn Sie Ihren Build-Job in der CI / CD-Pipeline festlegen.
Weitere Informationen finden Sie in meinem Blog: https://medium.com/tech-darwinbox/how-darwinbox-manages-infrastructure-at-scale-with-terraform-371e2c5f04d3
quelle
Ich möchte zu diesem Thread beitragen.
In einigen besonderen Fällen ist ein manueller Zugriff auf Terraform-Statusdateien erforderlich. Dinge wie Refactoring, Änderungen oder das Beheben von Fehlern erfordern die Ausführung von Terraform-Statusoperationen durch das Betriebspersonal. Planen Sie für solche Gelegenheiten einen außergewöhnlich kontrollierten Zugriff auf den Terraform-Status mithilfe von Bastion Host, VPN usw.
Überprüfen Sie ein längeres Best Practices-Blog , das dies ausführlich behandelt, einschließlich Richtlinien für CI / CD-Pipelines.
quelle
Wenn Sie immer noch nach der besseren Lösung suchen, werfen Sie einen Blick auf Arbeitsbereiche, die die Verwaltung unterschiedlicher Umgebungsordnerstrukturen ersetzen können und arbeitsbereichsspezifische Variablen enthalten können.
Wie Jewgenij Brikman erwähnte, ist es besser, eine Modulstruktur zu haben.
quelle
Verwenden Sie die Terraform Cloud zum Verwalten und Speichern von Status zusammen mit den oben genannten Hinweisen.
quelle