Évitez le « Cone of Shame » en sécurisant les pipelines de livraison d'applications dès le jour 0
2021-08-01
Machine-translated — the English original is authoritative.
TL;DR
Utilisez HashiCorp Packer v1.7.x avec les nouveaux modèles HCL2 pour construire, configurer et tester de manière cohérente et sécurisée les images de pipeline pour l'écosystème VMware, VMware ESXi 7.x & vCentre Server Appliance 7.x. Les mêmes principes utilisés avec VMware dans cet exemple peuvent être ajustés pour d'autres plateformes cloud telles qu'AWS, GCP, Azure, AliCloud, Oracle Cloud et Vagrant, pour n'en citer que quelques-unes.
Points clés à retenir
- Désactivez toujours l'accès par nom d'utilisateur/mot de passe via le réseau au début de votre pipeline par défaut et assurez-vous d'utiliser ssh avec des paires de clés secrètes comme minimum.
Injectez une clé ssh publique pour votre compte de création d'images au moment de la création de l'image et désactivez l'authentification réseau via l'accès par mot de passe – à partir du fichier preseed.cfg dans ce dépôt, la configuration ressemble à ceci
d-i preseed/late_command string \
in-target sed -i 's/^%sudo.*$/%sudo ALL=(ALL:ALL) NOPASSWD: ALL/g' /etc/sudoers; \
in-target /bin/sh -c "echo 'Defaults env_keep += \"SSH_AUTH_SOCK\"' >> /etc/sudoers"; \
in-target mkdir -p /home/iac4me/.ssh; \
in-target /bin/sh -c "echo 'ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQDDVB4JUB5/wUI0Y5THvquV8suuyLhjHNc/mkyerCZNJi4ZHTDk41wmaNhVcJWAbPKowAVTCchdM19EBPUykFPjnoXxcZS6qFFylAsxP6U0W5b4S5lon7+7d+ZwltgpWuuCdTkcJlDblZRWA8IdReh8mlSR6f8m7ngzgjGtppsxNXPzl7e/s3+CWLPOurb+0ZQvhdNU5Hcaxo/Vd9mW+RRy0ncroQrQ8SPg3xdFuZ+tsYDigoqXh9Jyg3KxvkM91HigHHsl0F03gq7MbniasYRwntzVbdydNkCFsNg0eDyz3hzXW6gXZRoj9TYilgAKmuLPRpiyN0rs8fQBMTVDO9P9yizVP7kB2uzGNOsoE3KhBotAzWM3Ht7rGsQlc+bhmkCsiz1C/c4gkSgIhdwHIvMVBJqGRDQAmf2XWV8XptSpBkQB2Mz9EiBILSSJjNTwod9FTxwn84KEXEsPc8neWcce3P0WE5f0TGyRDTRvy956gXaJSgm7CtxqU/Pwzv6+U41UUMoB0np0prFey7AFovx/IoBTAGwT1j19DNg/LlFKt53UhUURpdlRDXxz6yxoPobo49gyLN/YIWu4LgIvB+b9EKu+5Nfv/2iAntbVWoa/vaocSrHqlw5CQvyHBLZ3VH6EopST2twcrLkpMTmKicHxwRf03LggiiHXu0pX7z5ZTw== iac4me-BASTIONUSER-USER-KEY' >> /home/iac4me/.ssh/authorized_keys"; \
in-target chown -R iac4me:iac4me /home/iac4me/; \
in-target chmod -R go-rwx /home/iac4me/.ssh/authorized_keys; \
in-target sed -i 's/PermitRootLogin yes/PermitRootLogin no/g' /etc/ssh/sshd_config; \
in-target sed -i 's/#PasswordAuthentication yes/PasswordAuthentication no/g' /etc/ssh/sshd_config;
Ces informations de configuration varieront en fonction du système d'exploitation (OS) installé – il utilise l'installateur natif de l'OS, dans ce cas c'est Ubuntu 18.x
N'oubliez pas de mettre à jour les identifiants de connexion utilisés par Packer pendant le processus de build dans le fichier HCL – example.pkr.hcl
ssh_private_key_file = "/Users/grazzer/.ssh/iac4me-id_rsa"
ssh_username = "iac4me"
Note : Si vous travaillez à grande échelle et que vous préférez éviter la surcharge de la gestion des clés ssh, envisagez de passer à une authentification basée sur les certificats, discutée précédemment dans cet article de blog
- Testez les images de base pour la conformité au fur et à mesure de leur création – pourquoi attendre d'être en production pour vérifier les vulnérabilités et la non-conformité – ne les laissez pas s'échapper dès le départ.
État d'esprit `Shift left` pour la sécurité et la conformité – impliquez ces équipes tôt en intégrant la conformité et la gouvernance dans votre pipeline dès le début.
Introduction
Il est presque quotidien d'apprendre qu'une autre grande violation de données a eu lieu, avec des millions de détails d'utilisateurs accidentellement divulgués ou volés.
Nous ne sommes plus surpris par ces événements, cependant cela ne signifie pas que nous devrions laisser la complaisance s'installer. Les gouvernements commencent à se concentrer sur ces violations de données, fournissant des recommandations et des conseils de bonnes pratiques dans certains cas, mais dans tous les cas les amendes et pénalités augmentent également de manière significative.
Malheureusement, c'est ce dernier point qui tend à favoriser un bon comportement dans les entreprises. Je me souviens d'avoir assisté à une réunion de direction avec une multinationale à la fin des années 90 à Londres, démontrant un logiciel de conformité. Lorsque la discussion commerciale a commencé, le client a utilisé la taille de l'amende pour non-conformité, pondérée par la probabilité d'être effectivement découvert en premier lieu, comme critère de décision clé pour savoir s'il investirait ou non dans le logiciel.
L'attaque récente de la chaîne d'approvisionnement SolarWinds, rendue publique en octobre 2020, qui, au moment de la rédaction de cet article en août 2021, continue d'affecter de nombreuses entreprises, est un autre exemple de pourquoi le modèle classique `Castle and Moate` (Château et Fossé), utilisé par les entreprises pour protéger leurs environnements informatiques, est devenu sérieusement défectueux. Nous nous appuyons toujours principalement sur des pare-feu et des VPN pour protéger les périmètres de nos data centers, puis supposons que tous ceux qui se trouvent à l'intérieur de ce cercle de confiance sont de bons citoyens ! Ne me mal interprétez pas ici, les pare-feu, les VPN, etc. ont tous un rôle à jouer, mais nous pouvons faire beaucoup plus aujourd'hui.
Cet article se concentre sur le début d'un flux de travail de livraison d'applications plus moderne – le processus de build phénix pour un pipeline immuable. Beaucoup de mots qui se résument essentiellement à construire, configurer et tester les images de base au début de votre pipeline de livraison d'applications plutôt que de reconfigurer et de mettre à jour les applications existantes. Si vous avez encore du mal à trouver une fenêtre de temps pour appliquer le dernier round de correctifs à votre environnement de production, il est temps de commencer à examiner ces nouveaux modèles. Il ne faut que quelques minutes pour qu'une vulnérabilité zero-day publiée soit armée et ciblée vers ces fermes de serveurs héritées. Pourquoi fonctionnons-nous encore de cette façon !
Lorsqu'un correctif de système d'exploitation doit être livré, ou qu'une version d'application déployée, ces modifications sont implémentées via une nouvelle image de base, cette image passe ensuite par les tests de développement et d'acceptation utilisateur, et une fois réussis, elle sera finalement déployée en Production. Les planificateurs modernes comme Kubernetes ou Nomad fournissent des flux de travail de livraison d'applications avancés qui aident à maintenir la disponibilité des applications lors du remplacement de l'ancienne application et de la mise en ligne de la nouvelle application. Le rollback peut également être rapide, si nécessaire, grâce à l'approche immuable de ce pipeline de livraison.
HashiCorp propose un outil open source très puissant et utile appelé Packer, qui est conçu pour être utilisé au début de ce flux de travail de livraison d'applications moderne. Il peut être utilisé pour construire automatiquement et de manière cohérente des images de base répétitives qui peuvent ensuite être consommées par la phase suivante du flux de travail de l'application. Une grande partie de l'industrie cloud native a déjà adopté Packer comme outil de facto pour ce processus. Cependant, je vois souvent des pipelines où la sécurité a été omise par commodité au début de ce processus. Le reste de cet article aura pour but de fournir quelques astuces et conseils sur le déploiement de nouvelles images en utilisant des clés ssh plutôt que des mots de passe, ainsi que l'ajout de tests à l'image de base pour aider à piloter la conformité. Il est beaucoup moins cher de corriger un bug au début de ce pipeline que lorsqu'il est en production. Tout ce qui est mentionné ici est inclus dans Packer – il suffit juste que les équipes ne l'implémentent pas toujours.
J'ai reconstruit la plateforme de test VMware ce week-end et partagerai une tentative warts and all (avec tous ses défauts) de construction d'une image que j'avais fait fonctionner en janvier. Tout ce que je montre ici sur VMware peut être facilement adapté pour AWS, Azure, GCP, etc. Si le temps le permet, je déposerai d'autres exemples dans ce dépôt à une date ultérieure.
J'ai utilisé la version 1.7.4 de Packer dans cet exemple.
Les étapes que j'ai suivies
- Installons rapidement HashiCorp Packer, j'utilise MacOS (basé sur Intel) pour la démo
- D'abord, je m'assure que le tap Homebrew de HashiCorp est installé, ce tap inclut tous les produits HashiCorp et pas seulement Packer.
$ brew tap hashicorp/tap
- Installez Packer sur MacOS. Veuillez consulter le site web HashiCorp Learn pour des détails plus complets.
$ brew install hashicorp/tap/packer
==> Installing packer from hashicorp/tap
==> Downloading https://releases.hashicorp.com/packer/1.7.4/packer_1.7.4_darwin_amd64.zip
######################################################################## 100.0%
🍺 /usr/local/Cellar/packer/1.7.4: 3 files, 161.4MB, built in 6 seconds
- Vérifiez que Packer a été installé comme suit
$ packer version
Packer v1.7.4
- Récupérez le dépôt ici si vous souhaitez suivre ce tutoriel
$ git clone git@github.com:allthingsclowd/packer-vsphere.git
Cloning into 'packer-vsphere'...
remote: Enumerating objects: 133, done.
remote: Counting objects: 100% (133/133), done.
remote: Compressing objects: 100% (64/64), done.
remote: Total 133 (delta 59), reused 116 (delta 44), pack-reused 0
Receiving objects: 100% (133/133), 22.56 KiB | 2.51 MiB/s, done.
Resolving deltas: 100% (59/59), done.
$ cd packer-vsphere/
- Vérifions rapidement que j'ai créé un fichier de modèle Packer HCL valide
$ packer validate example.pkr.hcl
Error: Unset variable "webpagecounter_frontend_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vagrant_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "terraform_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "env_consul_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "secretid_service_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "waypoint_entrypoint_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "boundary_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "boundary_desktop_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "packer_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vault_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "nomad_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "golang_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vcentre_host"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "esx_host"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vcentre_password"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "envoy_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "webpagecounter_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "consul_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "nomad_autoscaler_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "consul_template_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "waypoint_version"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vcentre_user"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
- Oups, n'oubliez pas de charger vos variables d'environnement une fois que vous les avez correctement configurées pour correspondre à votre configuration environnementale. Assurez-vous de modifier les valeurs par défaut dans le fichier
var.env. Nous y voilà de nouveau..
$ source var.env
$ packer validate example.pkr.hcl
Error: Unset variable "vcentre_password"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vcentre_host"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "esx_host"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
Error: Unset variable "vcentre_user"
A used variable must be set or have a default value; see
https://packer.io/docs/templates/hcl_templates/syntax for details.
- Vous n'avez vraiment pas pensé que j'aurais les mots de passe dans le fichier
var.envde mon repo github – si ? Je dois les récupérer en tant que variables d'environnement également. Vous devrez également configurer ces variables d'environnement secrètes pour qu'elles correspondent à votre environnement, veuillez ne pas les mettre dans votre repo, ce n'est pas une bonne pratique. (Nous proposons HashiCorp Vault pour gérer ce type de matériel secret, mais cet article est pour une autre fois)
En dehors de ce dépôt, j'ai le fichier de secrets suivant qui est également sourced pour configurer les variables d'environnement requises…
# vCenter Setup
export PKR_VAR_vcentre_user="@vsphere.local"
export PKR_VAR_vcentre_password=""
export PKR_VAR_vcentre_host="vCentre IP Address"
export PKR_VAR_esx_host="ESX IP Address"
- Une fois que le fichier
var.envet le fichiersecretsont tous deux été chargés (toutes les variables d'environnement requises définies en mémoire), la validation de packer réussira… ennuyeusement sans aucune notification comme suit
$ packer validate example.pkr.hcl
$
- Alors, allons-y !
- La configuration a passé sa validation Packer, donc c'est bon, non ?
- 1, 2, 3 et on y va…
$ packer build example.pkr.hcl

- Faux 😦
==> vsphere-iso.example: Provisioning with Inspec...
==> vsphere-iso.example: Executing Inspec: inspec exec test/ImageBuild-Packer-Test --backend ssh --host 127.0.0.1 --user grazzer --key-files /var/folders/qq/8hmjq2xj23qcgjj7c5dbnvzm0000gn/T/packer-provisioner-inspec.994691541.key --port 64111 --input-file /var/folders/qq/8hmjq2xj23qcgjj7c5dbnvzm0000gn/T/packer-provisioner-inspec.367916336.yml
==> vsphere-iso.example: read |0: file already closed
==> vsphere-iso.example: Provisioning step had errors: Running the cleanup provisioner, if present...
==> vsphere-iso.example: Clear boot order...
==> vsphere-iso.example: Power off VM...
==> vsphere-iso.example: Deleting Floppy image ...
==> vsphere-iso.example: Destroying VM...
Build 'vsphere-iso.example' errored after 20 minutes 26 seconds: Error executing Inspec: exec: "inspec": executable file not found in $PATH
==> Wait completed after 20 minutes 26 seconds
==> Some builds didn't complete successfully and had errors:
--> vsphere-iso.example: Error executing Inspec: exec: "inspec": executable file not found in $PATH
==> Builds finished but no artifacts were created.
- Packer a été configuré pour utiliser Inspec de Chef pour tester mon processus de build packer, mais un récent défi Zoom a forcé une reconstruction de l'ordinateur portable pendant une session de débogage frustrante et je n'ai pas automatisé mon processus de reconstruction de l'ordinateur portable. Je dois réinstaller Chef car les tests Inspec s'exécutent depuis le serveur de build (mon ordinateur portable)
$ curl https://omnitruck.chef.io/install.sh | sudo bash -s -- -P inspec
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 23409 100 23409 0 0 198k 0 --:--:-- --:--:-- --:--:-- 198k
Password:
mac_os_x 11.4 x86_64
Getting information for inspec stable for mac_os_x...
downloading https://omnitruck.chef.io/stable/inspec/metadata?v=&p=mac_os_x&pv=11.4&m=x86_64
to file /tmp/install.sh.10782/metadata.txt
trying curl...
sha1 11e08ab78ce2971b7f129a2306e0a1636039b7f0
sha256 bc5772b1db8e13f2766390e995dbda1651813d1b1737c88af47b8f217acb03b0
url https://packages.chef.io/files/stable/inspec/4.38.9/mac_os_x/11/inspec-4.38.9-1.x86_64.dmg
version 4.38.9
downloaded metadata file looks valid...
downloading https://packages.chef.io/files/stable/inspec/4.38.9/mac_os_x/11/inspec-4.38.9-1.x86_64.dmg
to file /tmp/install.sh.10782/inspec-4.38.9-1.x86_64.dmg
trying curl...
Comparing checksum with shasum...
WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
You are installing a package without a version pin. If you are installing
on production servers via an automated process this is DANGEROUS and you will
be upgraded without warning on new releases, even to new major releases.
Letting the version float is only appropriate in desktop, test, development or
CI/CD environments.
WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
Installing inspec
installing dmg file...
Checksumming Protective Master Boot Record (MBR : 0)…
Protective Master Boot Record (MBR :: verified CRC32 $A63E199D
Checksumming GPT Header (Primary GPT Header : 1)…
GPT Header (Primary GPT Header : 1): verified CRC32 $554DB84C
Checksumming GPT Partition Data (Primary GPT Table : 2)…
GPT Partition Data (Primary GPT Tabl: verified CRC32 $9451B1CA
Checksumming (Apple_Free : 3)…
(Apple_Free : 3): verified CRC32 $00000000
Checksumming disk image (Apple_HFS : 4)…
....................................................................................................................
disk image (Apple_HFS : 4): verified CRC32 $CE3F8BAF
Checksumming (Apple_Free : 5)…
(Apple_Free : 5): verified CRC32 $00000000
Checksumming GPT Partition Data (Backup GPT Table : 6)…
GPT Partition Data (Backup GPT Table: verified CRC32 $9451B1CA
Checksumming GPT Header (Backup GPT Header : 7)…
GPT Header (Backup GPT Header : 7): verified CRC32 $CA80E7E2
verified CRC32 $9E68E33F
/dev/disk3 GUID_partition_scheme
/dev/disk3s1 Apple_HFS /Volumes/chef_software
installer: Package name is InSpec
installer: Installing at base path /
installer: The install was successful.
"disk3" ejected.
- Et on y va de nouveau…
$ packer build example.pkr.hcl
vsphere-iso.example: output will be in this color.
==> vsphere-iso.example: File /Users/grazzer/repos/packer-vsphere/packer_cache/a37af95ab12e665ba168128cde2f3662740b21a2.iso already uploaded; continuing
==> vsphere-iso.example: File [IntelDS2] packer_cache//a37af95ab12e665ba168128cde2f3662740b21a2.iso already exists; skipping upload.
==> vsphere-iso.example: Creating VM...
==> vsphere-iso.example: Customizing hardware...
==> vsphere-iso.example: Mounting ISO images...
==> vsphere-iso.example: Adding configuration parameters...
==> vsphere-iso.example: Creating floppy disk...
vsphere-iso.example: Copying files flatly from floppy_files
vsphere-iso.example: Copying file: ./http/preseed.cfg
vsphere-iso.example: Done copying files from floppy_files
vsphere-iso.example: Collecting paths from floppy_dirs
vsphere-iso.example: Resulting paths from floppy_dirs : []
vsphere-iso.example: Done copying paths from floppy_dirs
==> vsphere-iso.example: Uploading created floppy image
==> vsphere-iso.example: Adding generated Floppy...
==> vsphere-iso.example: Set boot order temporary...
==> vsphere-iso.example: Power on VM...
==> vsphere-iso.example: Waiting 10s for boot...

==> vsphere-iso.example: Provisioning with Inspec...
==> vsphere-iso.example: Executing Inspec: inspec exec test/ImageBuild-Packer-Test --backend ssh --host 127.0.0.1 --user grazzer --key-files /var/folders/qq/8hmjq2xj23qcgjj7c5dbnvzm0000gn/T/packer-provisioner-inspec.131501239.key --port 55207 --input-file /var/folders/qq/8hmjq2xj23qcgjj7c5dbnvzm0000gn/T/packer-provisioner-inspec.069478570.yml
vsphere-iso.example: [2021-07-31T20:53:28+01:00] ERROR: Chef InSpec cannot execute without accepting the license
==> vsphere-iso.example: Provisioning step had errors: Running the cleanup provisioner, if present...
==> vsphere-iso.example: Clear boot order...
==> vsphere-iso.example: Power off VM...
==> vsphere-iso.example: Deleting Floppy image ...
==> vsphere-iso.example: Destroying VM...
Build 'vsphere-iso.example' errored after 10 minutes 34 seconds: Error executing Inspec: Inspec exited with unexpected exit status: 172. Expected exit codes are: [0 101]
==> Wait completed after 10 minutes 34 seconds
==> Some builds didn't complete successfully and had errors:
--> vsphere-iso.example: Error executing Inspec: Inspec exited with unexpected exit status: 172. Expected exit codes are: [0 101]
==> Builds finished but no artifacts were created.
- Inspec vous oblige à accepter leur licence avant de pouvoir utiliser leur logiciel, c'est juste – pas que j'ai lu tout le jargon juridique
$ inspec --chef-license=accept
+---------------------------------------------+
✔ 1 product license accepted.
+---------------------------------------------+
Commands:
inspec archive PATH # archive a profile to tar.gz (default) or zip
inspec check PATH # verify all tests at the specified PATH
inspec clear_cache # clears the InSpec cache. Useful for debugging.
inspec detect # detect the target OS
inspec env # Output shell-appropriate completion configuration
inspec exec LOCATIONS # Run all tests at LOCATIONS.
inspec help [COMMAND] # Describe available commands or one specific command
inspec json PATH # read all tests in PATH and generate a JSON summary
inspec shell # open an interactive debugging shell
inspec supermarket SUBCOMMAND ... # Supermarket commands
inspec vendor PATH # Download all dependencies and generate a lockfile in a `vendor` directory
inspec version # prints the version of this tool
Options:
l, [--log-level=LOG_LEVEL] # Set the log level: info (default), debug, warn, error
[--log-location=LOG_LOCATION] # Location to send diagnostic log messages to. (default: $stdout or Inspec::Log.error)
[--diagnose], [--no-diagnose] # Show diagnostics (versions, configurations)
[--color], [--no-color] # Use colors in output.
[--interactive], [--no-interactive] # Allow or disable user interaction
[--disable-user-plugins] # Disable loading all plugins that the user installed.
[--enable-telemetry], [--no-enable-telemetry] # Allow or disable telemetry
[--chef-license=CHEF_LICENSE] # Accept the license for this product and any contained products: accept, accept-no-persist, accept-silent
About Chef InSpec:
Patents: chef.io/patents
- Et nous y voilà de nouveau, la troisième fois est la bonne…

- D'accord, restez avec moi – cette erreur est plus pertinente. Une fois l'image construite, Packer a ensuite lancé les tests Inspec pour s'assurer que la construction de l'image est conforme. Ce n'est pas le cas ! Il s'avère que l'équipe Envoy Proxy peut avoir changé la façon dont leur logiciel peut être déployé depuis ma dernière exécution de leur script d'installation.
vsphere-iso.example: ✔ golang-version-1.0: golang version check
vsphere-iso.example: ✔ Command: `/usr/local/go/bin/go version` stdout is expected to match "1.16"
vsphere-iso.example: × envoy-exists-1.0: envoy software exists
vsphere-iso.example: × File /usr/local/bin/envoy is expected to exist
vsphere-iso.example: expected File /usr/local/bin/envoy to exist
vsphere-iso.example: × envoy-version-1.0: envoy version check
vsphere-iso.example: × Command: `/usr/local/bin/envoy --version` stdout is expected to match "1.17.0"
vsphere-iso.example: expected "" to match "1.17.0"
vsphere-iso.example:
vsphere-iso.example:
vsphere-iso.example: Profile Summary: 25 successful controls, 2 control failures, 0 controls skipped
vsphere-iso.example: Test Summary: 32 successful, 2 failures, 0 skipped
==> vsphere-iso.example: Provisioning step had errors: Running the cleanup provisioner, if present...
==> vsphere-iso.example: Clear boot order...
==> vsphere-iso.example: Power off VM...
==> vsphere-iso.example: Deleting Floppy image ...
==> vsphere-iso.example: Destroying VM...
Build 'vsphere-iso.example' errored after 10 minutes 54 seconds: Error executing Inspec: Inspec exited with unexpected exit status: 100. Expected exit codes are: [0 101]
==> Wait completed after 10 minutes 54 seconds
==> Some builds didn't complete successfully and had errors:
- En gros, ce qui se passe maintenant, c'est que mes tests post-build, faisant partie intégrante du processus de build packer, ont détecté une erreur avec l'un des binaires qui devrait se trouver sur cette image, il manque !!! C'est exactement pourquoi nous utilisons des builds éphémères et testons avant même d'entrer en production – il est beaucoup moins cher pour les entreprises de faire ces erreurs plus tôt dans le processus de livraison.
- Il semble que le processus d'installation d'envoyproxy ait changé depuis que ce build a été exécuté avec succès en janvier
==> vsphere-iso.example: /tmp/script_4250.sh: line 128: getenvoy: command not found
==> vsphere-iso.example: chmod: cannot access '/usr/local/bin/getenvoy': No such file or directory
==> vsphere-iso.example: /tmp/script_4250.sh: line 130: /usr/local/bin/getenvoy: No such file or directory
==> vsphere-iso.example: cp: cannot stat '/usr/local/bin/builds/standard/1.17.0/linux_glibc/bin/envoy': No such file or directory
==> vsphere-iso.example: chmod: cannot access '/usr/local/bin/envoy': No such file or directory
==> vsphere-iso.example: /tmp/script_4250.sh: line 133: /usr/local/bin/envoy: No such file or directory
- Donc, j'ai un peu triché ici dans l'intérêt du temps et j'ai supprimé le test du binaire envoy proxy du fichier
vmware_example_image.rbjusqu'à ce que j'aie l'occasion de déboguer son script d'installation.
# control 'envoy-exists-1.0' do
# impact 1.0
# title 'envoy software exists'
# desc 'verify that envoy is installed'
# describe file('/usr/local/bin/envoy') do
# it { should exist }
# end
# end
# control 'envoy-version-1.0' do
# impact 1.0
# title 'envoy version check'
# desc 'verify that envoy is the correct version'
# describe command('/usr/local/bin/envoy --version') do
# its('stdout') { should match envoy_version }
# end
# end
- Et on y va de nouveau…

- Au milieu de mes changements, cela se produit…
$ git push
Enumerating objects: 35, done.
Counting objects: 100% (35/35), done.
Delta compression using up to 8 threads
Compressing objects: 100% (19/19), done.
Writing objects: 100% (26/26), 933.16 MiB | 1.92 MiB/s, done.
Total 26 (delta 8), reused 2 (delta 0), pack-reused 0
remote: Resolving deltas: 100% (8/8), completed with 3 local objects.
remote: error: GH001: Large files detected. You may want to try Git Large File Storage - https://git-lfs.github.com.
remote: error: Trace: 58ba6c71facaeb026b51d562c13d6bfd54da57cdd13ef128e97c5ee43c426bd8
remote: error: See http://git.io/iEPt8g for more information.
remote: error: File packer_cache/a37af95ab12e665ba168128cde2f3662740b21a2.iso is 951.00 MB; this exceeds GitHub's file size limit of 100.00 MB
To github.com:allthingsclowd/packer-vsphere.git
! [remote rejected] update -> update (pre-receive hook declined)
error: failed to push some refs to 'github.com:allthingsclowd/packer-vsphere.git'
- En gros, une autre queue prudente lors du travail avec Packer et les dépôts Git… configurez votre fichier
.gitignoreavant de commiter quoi que ce soit. Lorsque Packer s'exécute, il met en cache les images que vous appelez dans votre fichier de configuration. Nous ne voulons pas de ces images dans notre dépôt git (généralement). - Pour éviter cette erreur, n'oubliez pas de créer et de configurer un fichier
.gitignoreau début de votre processus de construction d'images et placez au minimum le répertoirepacker_cachededans. - Pour résoudre ce problème, j'utilise un outil pratique appelé BFG comme suit
$ java -jar ~/Downloads/bfg-1.14.0.jar --strip-blobs-bigger-than 100M packer-vsphere/
Using repo : /Users/grazzer/repos/packer-vsphere/.git
Scanning packfile for large blobs: 134
Scanning packfile for large blobs completed in 23 ms.
Found 1 blob ids for large blobs - biggest=997195776 smallest=997195776
Total size (unpacked)=997195776
Found 11 objects to protect
Found 7 commit-pointing refs : HEAD, refs/heads/grazzer, refs/heads/update, ...
Protected commits
-----------------
These are your protected commits, and so their contents will NOT be altered:
* commit 97d7665f (protected by 'HEAD')
Cleaning
--------
Found 26 commits
Cleaning commits: 100% (26/26)
Cleaning commits completed in 95 ms.
Updating 1 Ref
--------------
Ref Before After
---------------------------------------
refs/heads/update | 97d7665f | cc8b9271
Updating references: 100% (1/1)
...Ref update completed in 21 ms.
Commit Tree-Dirt History
------------------------
Earliest Latest
| |
.....................DDDmm
D = dirty commits (file tree fixed)
m = modified commits (commit message or parents changed)
. = clean commits (no changes to file tree)
Before After
-------------------------------------------
First modified commit | cfcd2a9c | 6528e27
Last dirty commit | 23747e6c | 3f891d80
Deleted files
-------------
Filename Git id
------------------------------------------------------------------
a37af95ab12e665ba168128cde2f3662740b21a2.iso | 1a5de3fe (951.0 MB)
In total, 9 object ids were changed. Full details are logged here:
/Users/grazzer/repos/packer-vsphere.bfg-report/2021-08-01/09-35-21
BFG run is complete! When ready, run: git reflog expire --expire=now --all && git gc --prune=now --aggressive
$ cd packer-vsphere
$ git reflog expire --expire=now --all && git gc --prune=now --aggressive
Enumerating objects: 164, done.
Counting objects: 100% (164/164), done.
Delta compression using up to 8 threads
Compressing objects: 131/131), done.
Writing objects: 100% (164/164), done.
Total 164 (delta 71), reused 61 (delta 0), pack-reused 0
grazzer@Grahams-MacBook-Pro ~/r/packer-vsphere (update)> git push
Enumerating objects: 41, done.
Counting objects: 100% (41/41), done.
Delta compression using up to 8 threads
Compressing objects: 100% (16/16), done.
Writing objects: 100% (32/32), 10.83 KiB | 10.83 MiB/s, done.
Total 32 (delta 10), reused 29 (delta 7), pack-reused 0
remote: Resolving deltas: 100% (10/10), completed with 3 local objects.
To github.com:allthingsclowd/packer-vsphere.git
8acc2bb..cc8b927 update -> update
$
- Donc, j'ai réparé le dépôt que j'ai cassé, repartons…

$ packer build -on-error=abort example.pkr.hcl
vsphere-iso.example: output will be in this color.
==> vsphere-iso.example: File /Users/grazzer/repos/packer-vsphere/packer_cache/a37af95ab12e665ba168128cde2f3662740b21a2.iso already uploaded; continuing
==> vsphere-iso.example: File [IntelDS2] packer_cache//a37af95ab12e665ba168128cde2f3662740b21a2.iso already exists; skipping upload.
==> vsphere-iso.example: packer_templates/example already exists, you can use -force flag to destroy it: <nil>
==> vsphere-iso.example: Step "StepCreateVM" failed, aborting...
==> vsphere-iso.example: aborted: skipping cleanup of step "StepRemoteUpload"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepCreateCD"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepDownload"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepConnect"
Build 'vsphere-iso.example' errored after 462 milliseconds 605 microseconds: packer_templates/example already exists, you can use -force flag to destroy it: <nil>
==> Wait completed after 462 milliseconds 786 microseconds
==> Some builds didn't complete successfully and had errors:
--> vsphere-iso.example: packer_templates/example already exists, you can use -force flag to destroy it: <nil>
==> Builds finished but no artifacts were created.
- Par défaut, Packer se nettoie après lui-même lorsqu'il lance une erreur. Cependant, lors du débogage d'un script d'installation (envoy proxy ci-dessus), il est souvent utile d'empêcher cette opération de nettoyage afin que nous puissions nous connecter au serveur et enquêter manuellement.
- Ce mode de fonctionnement est invoqué en utilisant le drapeau
-on-errorcomme suit
$ packer build -on-error=abort example.pkr.hcl
- Cependant, nous avons obtenu l'erreur précédente lors du redémarrage du build car Packer a rapidement détecté que l'exécution précédente n'avait pas été nettoyée correctement.
- Nous pouvons contourner cela en utilisant le drapeau
-force - Et maintenant, nous sommes de nouveau sur la bonne voie…
packer build -on-error=abort -force example.pkr.hcl
vsphere-iso.example: output will be in this color.
==> vsphere-iso.example: File /Users/grazzer/repos/packer-vsphere/packer_cache/a37af95ab12e665ba168128cde2f3662740b21a2.iso already uploaded; continuing
==> vsphere-iso.example: File [IntelDS2] packer_cache//a37af95ab12e665ba168128cde2f3662740b21a2.iso already exists; skipping upload.
==> vsphere-iso.example: the vm/template packer_templates/example already exists, but deleting it due to -force flag
==> vsphere-iso.example: Creating VM...
==> vsphere-iso.example: Customizing hardware...
==> vsphere-iso.example: Mounting ISO images...
==> vsphere-iso.example: Adding configuration parameters...
==> vsphere-iso.example: Creating floppy disk...
vsphere-iso.example: Copying files flatly from floppy_files
vsphere-iso.example: Copying file: ./http/preseed.cfg
vsphere-iso.example: Done copying files from floppy_files
vsphere-iso.example: Collecting paths from floppy_dirs
vsphere-iso.example: Resulting paths from floppy_dirs : []
vsphere-iso.example: Done copying paths from floppy_dirs
==> vsphere-iso.example: Uploading created floppy image
==> vsphere-iso.example: Adding generated Floppy...
==> vsphere-iso.example: Set boot order temporary...
==> vsphere-iso.example: Power on VM...
. . .
==> vsphere-iso.example: Shutting down VM...
==> vsphere-iso.example: Cannot shut down VM: ServerFaultCode: Cannot complete operation because VMware Tools is not running in this virtual machine.
==> vsphere-iso.example: Step "StepShutdown" failed, aborting...
==> vsphere-iso.example: aborted: skipping cleanup of step "StepProvision"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepConnect"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepWaitForIp"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepBootCommand"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepRun"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepHTTPServer"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepHTTPIPDiscover"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepAddFloppy"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepCreateFloppy"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepConfigParams"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepAddCDRom"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepConfigureHardware"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepCreateVM"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepRemoteUpload"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepCreateCD"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepDownload"
==> vsphere-iso.example: aborted: skipping cleanup of step "StepConnect"
Build 'vsphere-iso.example' errored after 10 minutes 48 seconds: Cannot shut down VM: ServerFaultCode: Cannot complete operation because VMware Tools is not running in this virtual machine.
==> Wait completed after 10 minutes 48 seconds
==> Some builds didn't complete successfully and had errors:
--> vsphere-iso.example: Cannot shut down VM: ServerFaultCode: Cannot complete operation because VMware Tools is not running in this virtual machine.
==> Builds finished but no artifacts were created.

- Quoi ?
- Pas Waaaaaaaay !
- Waaaaay !
- Manque de VMware Tools !!! C'est une surprise, la dernière fois que j'ai regardé, je suis sûr qu'il était installé.
- La correction rapide ici est de simplement s'assurer que VMware Tools est ajouté aux prérequis dans le script d'installation
packer_install_base_packages.sh
sudo apt-get install -y -q wget tmux unzip git redis-server nginx lynx jq curl net-tools open-vm-tools
- Et n'oubliez pas de le tester, bien sûr, en ajoutant ce qui suit au fichier de test Inspec
describe package('open-vm-tools') do
it {should be_installed}
end
- Et enfin, nous obtenons un nouveau template déployé sur mon hôte ESX
vsphere-iso.example: ✔ golang-exists-1.0: golang exists
vsphere-iso.example: ✔ File /usr/local/go/bin/go is expected to exist
vsphere-iso.example: ✔ golang-version-1.0: golang version check
vsphere-iso.example: ✔ Command: `/usr/local/go/bin/go version` stdout is expected to match "1.16"
vsphere-iso.example:
vsphere-iso.example:
vsphere-iso.example: Profile Summary: 22 successful controls, 0 control failures, 0 controls skipped
vsphere-iso.example: Test Summary: 30 successful, 0 failures, 0 skipped
==> vsphere-iso.example: Shutting down VM...
==> vsphere-iso.example: Deleting Floppy drives...
==> vsphere-iso.example: Deleting Floppy image...
==> vsphere-iso.example: Eject CD-ROM drives...
==> vsphere-iso.example: Convert VM into template...
==> vsphere-iso.example: Clear boot order...
Build 'vsphere-iso.example' finished after 10 minutes 43 seconds.
==> Wait completed after 10 minutes 43 seconds
==> Builds finished. The artifacts of successful builds are:
--> vsphere-iso.example: example

- J'espère que ce dépôt et ce readme seront utiles à quelqu'un d'autre sur cette chose interweb.
Heureux d'automatiser, Graz
À faire
- Ajouter plus d'exemples de plateformes d'images
- Corriger le déploiement des binaires de base d'envoyproxy
- Éventuellement ajouter des tests Travis également, voir ce que je peux faire juste dans le cloud sans Macbook local requis
Originally published on allthingscloud.eu (2021-08-01).