Sécurité de l'image - Amazon EKS

Les traductions sont fournies par des outils de traduction automatique. En cas de conflit entre le contenu d'une traduction et celui de la version originale en anglais, la version anglaise prévaudra.

Sécurité de l'image

Vous devez considérer l'image du conteneur comme la première ligne de défense contre une attaque. Une image peu sécurisée et mal construite peut permettre à un attaquant d'échapper aux limites du conteneur et d'accéder à l'hôte. Une fois sur l'hôte, un attaquant peut accéder à des informations sensibles ou se déplacer latéralement au sein du cluster ou avec votre compte AWS. Les meilleures pratiques suivantes aideront à atténuer le risque que cela se produise.

Recommandations

Créez un minimum d'images

Commencez par retirer tous les fichiers binaires superflus de l'image de conteneur. Si vous utilisez une image inconnue provenant de Dockerhub, inspectez-la à l'aide d'une application telle que Dive qui peut vous montrer le contenu de chacune des couches du conteneur. Supprimez tous les fichiers binaires contenant les bits SETUID et SETGID, car ils peuvent être utilisés pour augmenter les privilèges, et envisagez de supprimer tous les shells et utilitaires tels que nc et curl qui peuvent être utilisés à des fins malveillantes. Vous pouvez trouver les fichiers contenant les bits SETUID et SETGID à l'aide de la commande suivante :

find / -perm /6000 -type f -exec ls -ld {} \;

Pour supprimer les autorisations spéciales associées à ces fichiers, ajoutez la directive suivante à votre image de conteneur :

RUN find / -xdev -perm /6000 -type f -exec chmod a-s {} \; || true

C'est ce que l'on appelle familièrement la modification de votre image.

Utilisez des versions en plusieurs étapes

L'utilisation de builds en plusieurs étapes est un moyen de créer des images minimales. Souvent, des versions en plusieurs étapes sont utilisées pour automatiser certaines parties du cycle d'intégration continue. Par exemple, les versions en plusieurs étapes peuvent être utilisées pour affiner votre code source ou effectuer une analyse de code statique. Cela permet aux développeurs d'obtenir des commentaires quasi immédiats au lieu d'attendre l'exécution d'un pipeline. Les builds en plusieurs étapes sont intéressants du point de vue de la sécurité car ils vous permettent de minimiser la taille de l'image finale envoyée à votre registre de conteneurs. Les images de conteneur dépourvues d'outils de construction et d'autres fichiers binaires superflus améliorent votre niveau de sécurité en réduisant la surface d'attaque de l'image. Pour plus d'informations sur les versions en plusieurs étapes, consultez la documentation des versions en plusieurs étapes de Docker.

Créez une nomenclature logicielle (SBOMs) pour l'image de votre conteneur

Une « nomenclature logicielle » (SBOM) est un inventaire imbriqué des artefacts logiciels qui constituent l'image de votre conteneur. Le SBOM est un élément clé de la sécurité logicielle et de la gestion des risques liés à la chaîne d'approvisionnement logicielle. La génération, le stockage des SBOM dans un référentiel central et l'analyse SBOMs des vulnérabilités permettent de résoudre les problèmes suivants :

  • Visibilité : déterminez quels composants constituent l'image de votre conteneur. Le stockage dans un référentiel central permet d'être audité et scanné SBOMs à tout moment, même après le déploiement, afin de détecter les nouvelles vulnérabilités telles que les vulnérabilités de type « jour zéro » et d'y répondre.

  • Vérification de la provenance : assurance que les hypothèses existantes concernant l'origine et la provenance d'un artefact sont vraies et que l'artefact ou les métadonnées qui l'accompagnent n'ont pas été falsifiés pendant les processus de construction ou de livraison.

  • Fiabilité : assurance que l'on peut faire confiance à un artefact donné et à son contenu pour faire ce qu'il est censé faire, c'est-à-dire qu'ils sont adaptés à un objectif précis. Cela implique de déterminer si le code peut être exécuté en toute sécurité et de prendre des décisions éclairées quant aux risques associés à l'exécution du code. La fiabilité est garantie en créant un rapport d'exécution du pipeline attesté ainsi qu'un rapport de scan SBOM attesté et CVE attesté pour garantir aux consommateurs de l'image que cette image est en fait créée par des moyens sécurisés (pipeline) avec des composants sécurisés.

  • Vérification de la confiance dans les dépendances : vérification récursive de l'arbre de dépendances d'un artefact pour vérifier la fiabilité et la provenance des artefacts qu'il utilise. Drift in SBOMs peut aider à détecter les activités malveillantes, notamment les dépendances non autorisées et non fiables et les tentatives d'infiltration.

Les outils suivants peuvent être utilisés pour générer des SBOM :

  • Amazon Inspector peut être utilisé pour créer et exporter SBOMs.

  • Syft d'Anchore peut également être utilisé pour la génération de SBOM. Pour accélérer les analyses de vulnérabilité, le SBOM généré pour une image de conteneur peut être utilisé comme entrée pour le scan. Le SBOM et le rapport de numérisation sont ensuite attestés et joints à l'image avant de transférer l'image vers un référentiel OCI central tel qu'Amazon ECR à des fins de révision et d'audit.

Pour en savoir plus sur la sécurisation de votre chaîne d'approvisionnement logicielle, consultez le guide des meilleures pratiques de la chaîne d'approvisionnement logicielle de la CNCF.

Scannez régulièrement les images pour détecter les vulnérabilités

Comme leurs homologues de machines virtuelles, les images de conteneur peuvent contenir des fichiers binaires et des bibliothèques d'applications présentant des vulnérabilités ou développer des vulnérabilités au fil du temps. Le meilleur moyen de se prémunir contre les attaques est d'analyser régulièrement vos images à l'aide d'un analyseur d'images. Les images stockées dans Amazon ECR peuvent être numérisées en mode push ou à la demande (une fois par période de 24 heures). L'ECR prend actuellement en charge deux types de numérisation : de base et améliorée. La numérisation de base tire parti de Clair, une solution de numérisation d'images open source gratuite. Le scan amélioré utilise Amazon Inspector pour fournir des scans continus automatiques moyennant des frais supplémentaires. Une fois qu'une image est numérisée, les résultats sont enregistrés dans EventBridge le flux d'événements pour être intégrés à l'ECR. Vous pouvez également consulter les résultats d'un scan depuis la console ECR. Les images présentant une vulnérabilité ÉLEVÉE ou CRITIQUE doivent être supprimées ou reconstruites. Si une image déployée développe une vulnérabilité, elle doit être remplacée dès que possible.

Il est essentiel de savoir où les images présentant des vulnérabilités ont été déployées pour garantir la sécurité de votre environnement. Bien que vous puissiez créer vous-même une solution de suivi d'images, il existe déjà plusieurs offres commerciales qui offrent cette fonctionnalité et d'autres fonctionnalités avancées prêtes à l'emploi, notamment :

Un webhook de validation Kubernetes pourrait également être utilisé pour vérifier que les images sont exemptes de vulnérabilités critiques. Les webhooks de validation sont invoqués avant l'API Kubernetes. Ils sont généralement utilisés pour rejeter les demandes non conformes aux critères de validation définis dans le webhook. Voici un exemple de webhook sans serveur qui appelle l'API ECR Findings describeImageScan pour déterminer si un pod extrait une image présentant des vulnérabilités critiques. Si des vulnérabilités sont détectées, le pod est rejeté et un message contenant la liste des CVEs est renvoyé sous forme d'événement.

Utiliser des attestations pour valider l'intégrité des artefacts

Une attestation est une « déclaration » signée cryptographiquement qui affirme que quelque chose (un « prédicat », par exemple un pipeline, le SBOM ou le rapport d'analyse des vulnérabilités) est vrai sur un autre point : un « sujet », c'est-à-dire l'image du conteneur.

Les attestations aident les utilisateurs à valider qu'un artefact provient d'une source fiable de la chaîne d'approvisionnement logicielle. Par exemple, nous pouvons utiliser une image de conteneur sans connaître tous les composants logiciels ou dépendances inclus dans cette image. Cependant, si nous faisons confiance à ce que dit le producteur de l'image du conteneur à propos du logiciel présent, nous pouvons utiliser l'attestation du producteur pour nous fier à cet artefact. Cela signifie que nous pouvons utiliser l'artefact en toute sécurité dans notre flux de travail au lieu d'avoir effectué l'analyse nous-mêmes.

  • Les attestations peuvent être créées à l'aide d'AWS Signer ou de Sigstore cosign.

  • Les contrôleurs d'admission Kubernetes tels que Kyverno peuvent être utilisés pour vérifier les attestations.

  • Consultez cet atelier pour en savoir plus sur les meilleures pratiques de gestion de la chaîne d'approvisionnement logicielle sur AWS à l'aide d'outils open source, avec des sujets tels que la création et le rattachement d'attestations à une image de conteneur.

Création de politiques IAM pour les référentiels ECR

De nos jours, il n'est pas rare qu'une organisation dispose de plusieurs équipes de développement travaillant indépendamment au sein d'un compte AWS partagé. Si ces équipes n'ont pas besoin de partager des ressources, vous pouvez créer un ensemble de politiques IAM qui limitent l'accès aux référentiels avec lesquels chaque équipe peut interagir. Un bon moyen de l'implémenter est d'utiliser les espaces de noms ECR. Les espaces de noms permettent de regrouper des référentiels similaires. Par exemple, tous les registres de l'équipe A peuvent être préfacés avec le préfixe team-a/ tandis que ceux de l'équipe B peuvent utiliser le préfixe team-b/. La politique visant à restreindre l'accès peut ressembler à ce qui suit :

{ "Version": "2012-10-17", "Statement": [ { "Sid": "AllowPushPull", "Effect": "Allow", "Action": [ "ecr:GetDownloadUrlForLayer", "ecr:BatchGetImage", "ecr:BatchCheckLayerAvailability", "ecr:PutImage", "ecr:InitiateLayerUpload", "ecr:UploadLayerPart", "ecr:CompleteLayerUpload" ], "Resource": [ "arn:aws:ecr:<region>:<account_id>:repository/team-a/*" ] } ] }

Envisagez d'utiliser des points de terminaison privés ECR

L'API ECR possède un point de terminaison public. Par conséquent, les registres ECR sont accessibles depuis Internet tant que la demande a été authentifiée et autorisée par IAM. Pour ceux qui doivent opérer dans un environnement sandbox où le VPC du cluster ne dispose pas d'une passerelle Internet (IGW), vous pouvez configurer un point de terminaison privé pour l'ECR. La création d'un point de terminaison privé vous permet d'accéder de manière privée à l'API ECR via une adresse IP privée au lieu de router le trafic sur Internet. Pour plus d'informations sur ce sujet, consultez la section Points de terminaison VPC de l'interface Amazon ECR.

Mettre en œuvre des politiques relatives aux terminaux pour l'ECR

La politique de point de terminaison par défaut pour autorise l'accès à tous les référentiels ECR d'une région. Cela peut permettre attacker/insider à an d'exfiltrer des données en les empaquetant sous forme d'image de conteneur et en les transférant vers un registre d'un autre compte AWS. Pour atténuer ce risque, il faut créer une politique de point de terminaison qui limite l'accès des API aux référentiels ECR. Par exemple, la politique suivante permet à tous les principes AWS de votre compte d'effectuer toutes les actions sur vos référentiels ECR et uniquement sur vos référentiels ECR :

{ "Statement": [ { "Sid": "LimitECRAccess", "Principal": "*", "Action": "*", "Effect": "Allow", "Resource": "arn:aws:ecr:<region>:<account_id>:repository/*" } ] }

Vous pouvez encore améliorer cela en définissant une condition qui utilise le nouvel PrincipalOrgID attribut qui empêchera la diffusion pushing/pulling d'images selon un principe IAM ne faisant pas partie de votre organisation AWS. Voir aws : PrincipalOrg ID pour plus de détails. Nous avons recommandé d'appliquer la même politique aux points de terminaison com.amazonaws.<region>.ecr.dkr et com.amazonaws.<region>.ecr.api. Comme EKS extrait des images pour kube-proxy, coredns et aws-node depuis ECR, vous devez ajouter l'ID de compte du registre, par exemple 602401143452.dkr.ecr.us-west-2.amazonaws.com/ à la liste des ressources dans la politique des terminaux ou modifier la politique pour autoriser les extractions depuis et limiter les push vers votre identifiant de compte. Le tableau ci-dessous indique le mappage entre les comptes AWS à partir desquels les images EKS sont vendues et la région du cluster.

Numéro du compte Région

602401143452

Toutes les régions commerciales, à l'exception de celles répertoriées ci-dessous

800184023465

ap-east-1 - Asie-Pacifique (Hong Kong)

558608220178

me-south-1 - Moyen-Orient (Bahreïn)

918309763551

cn-north-1 - Chine (Pékin)

961992271922

cn-northwest-1 - Chine (Ningxia)

Pour plus d'informations sur l'utilisation des politiques de point de terminaison, consultez la section Utilisation des politiques de point de terminaison VPC pour contrôler l'accès à Amazon ECR.

Mettre en œuvre des politiques de cycle de vie pour l'ECR

Le guide de sécurité des conteneurs d'applications du NIST met en garde contre le risque d' « images périmées dans les registres », en notant qu'au fil du temps, out-of-date les anciennes images présentant des vulnérabilités doivent être supprimées pour éviter tout déploiement ou exposition accidentels. Chaque référentiel ECR peut avoir une politique de cycle de vie qui définit des règles relatives à l'expiration des images. La documentation officielle d'AWS décrit comment configurer des règles de test, les évaluer puis les appliquer. Les documents officiels contiennent plusieurs exemples de politique de cycle de vie qui montrent différentes manières de filtrer les images d'un référentiel :

  • Filtrage par âge ou nombre d'images

  • Filtrage par images balisées ou non étiquetées

  • Filtrage par balises d'image, selon plusieurs règles ou une seule règle

? ? ? + avertissement Si l'image d'une application de longue durée est purgée de l'ECR, cela peut provoquer des erreurs d'extraction d'image lorsque l'application est redéployée ou redimensionnée horizontalement. Lorsque vous utilisez des politiques de cycle de vie des images, veillez à mettre en place de bonnes CI/CD pratiques pour maintenir les déploiements et les images auxquelles ils font référence à jour et créez toujours des règles d'expiration [des images] qui tiennent compte de la fréquence à laquelle vous effectuez des publiations/déploiements.

Créez un ensemble d'images sélectionnées

Plutôt que de permettre aux développeurs de créer leurs propres images, envisagez de créer un ensemble d'images validées pour les différentes piles d'applications de votre organisation. Ce faisant, les développeurs peuvent renoncer à apprendre à composer des Dockerfiles et se concentrer sur l'écriture de code. Lorsque les modifications sont fusionnées dans Master, un CI/CD pipeline peut automatiquement compiler l'actif, le stocker dans un référentiel d'artefacts et copier l'artefact dans l'image appropriée avant de le transférer vers un registre Docker tel que ECR. À tout le moins, vous devez créer un ensemble d'images de base à partir desquelles les développeurs pourront créer leurs propres Dockerfiles. Idéalement, vous devez éviter d'extraire des images de Dockerhub car 1/ vous ne savez pas toujours ce qu'elle contient et 2/ environ un cinquième des 1 000 meilleures images présentent des vulnérabilités. Une liste de ces images et de leurs vulnérabilités se trouve ici.

Ajoutez la directive USER à vos Dockerfiles pour l'exécuter en tant qu'utilisateur non root

Comme indiqué dans la section relative à la sécurité du pod, vous devez éviter d'exécuter le conteneur en tant que root. Bien que vous puissiez le configurer dans le cadre du PodSpec, c'est une bonne habitude d'utiliser la USER directive dans vos Dockerfiles. La USER directive définit l'UID à utiliser lors de l'exécution RUNENTRYPOINT, ou CMD l'instruction qui apparaît après la directive USER.

Lint vos Dockerfiles

Le linting peut être utilisé pour vérifier que vos Dockerfiles respectent un ensemble de directives prédéfinies, par exemple l'inclusion de la USER directive ou l'exigence selon laquelle toutes les images doivent être étiquetées. dockerfile_lint est un projet open source RedHat qui vérifie les meilleures pratiques courantes et inclut un moteur de règles que vous pouvez utiliser pour créer vos propres règles pour le linting de Dockerfiles. Il peut être intégré à un pipeline CI, dans la mesure où les builds contenant des Dockerfiles qui enfreignent une règle échoueront automatiquement.

Créez des images à partir de zéro

La réduction de la surface d'attaque de vos images de conteneurs doit être l'objectif principal lors de la création d'images. Le moyen idéal pour ce faire est de créer des images minimales dépourvues de fichiers binaires pouvant être utilisés pour exploiter les vulnérabilités. Heureusement, Docker dispose d'un mécanisme permettant de créer des images à partir de scratch. Avec des langages tels que Go, vous pouvez créer un binaire lié statique et le référencer dans votre Dockerfile comme dans cet exemple :

############################ # STEP 1 build executable binary ############################ FROM golang:alpine AS builder# Install git. # Git is required for fetching the dependencies. RUN apk update && apk add --no-cache gitWORKDIR $GOPATH/src/mypackage/myapp/COPY . . # Fetch dependencies. # Using go get. RUN go get -d -v# Build the binary. RUN go build -o /go/bin/hello ############################ # STEP 2 build a small image ############################ FROM scratch# Copy our static executable. COPY --from=builder /go/bin/hello /go/bin/hello# Run the hello binary. ENTRYPOINT ["/go/bin/hello"]

Cela crée une image de conteneur composée de votre application et de rien d'autre, ce qui la rend extrêmement sécurisée.

Utiliser des balises immuables avec ECR

Les balises immuables vous obligent à mettre à jour la balise d'image à chaque transfert vers le référentiel d'images. Cela peut empêcher un attaquant de remplacer une image par une version malveillante sans modifier les balises de l'image. De plus, il vous permet d'identifier facilement et de manière unique une image.

Signez vos images SBOMs, vos cycles de pipeline et vos rapports de vulnérabilité

Lorsque Docker a été introduit pour la première fois, il n'existait aucun modèle cryptographique permettant de vérifier les images des conteneurs. Avec la version v2, Docker a ajouté des résumés au manifeste de l'image. Cela a permis de hacher la configuration d'une image et d'utiliser le hachage pour générer un identifiant pour l'image. Lorsque la signature d'image est activée, le moteur Docker vérifie la signature du manifeste, garantissant ainsi que le contenu a été produit à partir d'une source fiable et qu'aucune altération n'a eu lieu. Après le téléchargement de chaque couche, le moteur vérifie le condensé de la couche, en s'assurant que le contenu correspond au contenu spécifié dans le manifeste. La signature d'image vous permet de créer efficacement une chaîne d'approvisionnement sécurisée, grâce à la vérification des signatures numériques associées à l'image.

Nous pouvons utiliser AWS Signer ou Sigstore Cosign pour signer des images de conteneurs, créer des attestations, des rapports d'analyse des SBOMs vulnérabilités et des rapports d'exécution du pipeline. Ces attestations garantissent la fiabilité et l'intégrité de l'image, qu'elle est effectivement créée par le pipeline sécurisé sans aucune interférence ni altération, et qu'elle ne contient que les composants logiciels documentés (dans le SBOM) vérifiés et approuvés par l'éditeur de l'image. Ces attestations peuvent être jointes à l'image du conteneur et transmises au référentiel.

Dans la section suivante, nous verrons comment utiliser les artefacts attestés pour les audits et les vérifications du contrôleur des admissions.

Vérification de l'intégrité de l'image à l'aide du contrôleur d'admission Kubernetes

Nous pouvons vérifier les signatures d'image et les artefacts attestés de manière automatisée avant de déployer l'image sur le cluster Kubernetes cible à l'aide du contrôleur d'admission dynamique et n'admettre les déploiements que lorsque les métadonnées de sécurité des artefacts sont conformes aux politiques du contrôleur d'admission.

Par exemple, nous pouvons rédiger une politique qui vérifie cryptographiquement la signature d'une image, d'un SBOM attesté, d'un rapport d'exécution du pipeline ou d'un rapport de scan CVE attesté. Nous pouvons écrire des conditions dans la politique pour vérifier les données du rapport, par exemple, un scan CVE ne doit pas comporter de critiqueCVEs. Le déploiement n'est autorisé que pour les images qui répondent à ces conditions et tous les autres déploiements seront rejetés par le contrôleur des admissions.

Parmi les exemples de contrôleur d'admission, on peut citer :

Mettez à jour les packages dans les images de vos conteneurs

Vous devez inclure RUN apt-get update && apt-get upgrade dans vos Dockerfiles pour mettre à jour les packages de vos images. Bien que la mise à niveau nécessite que vous l'exécutiez en tant que root, cela se produit pendant la phase de création de l'image. L'application n'a pas besoin de s'exécuter en tant que root. Vous pouvez installer les mises à jour, puis passer à un autre utilisateur avec la directive USER. Si votre image de base est exécutée en tant qu'utilisateur non root, passez en mode root et inversement ; ne vous fiez pas uniquement aux responsables de l'image de base pour installer les dernières mises à jour de sécurité.

Exécutez apt-get clean pour supprimer les fichiers du programme d'installation de/var/cache/apt/archives/. Vous pouvez également exécuter rm -rf /var/lib/apt/lists/* après l'installation des packages. Cela supprime les fichiers d'index ou les listes de packages disponibles pour l'installation. Sachez que ces commandes peuvent être différentes pour chaque gestionnaire de packages. Par exemple :

RUN apt-get update && apt-get install -y \ curl \ git \ libsqlite3-dev \ && apt-get clean && rm -rf /var/lib/apt/lists/*

Outils et ressources

  • Atelier d'immersion sur la sécurité Amazon EKS - Image Security

  • docker-slim Créez des images minimales sécurisées

  • dockle Vérifie que votre Dockerfile est conforme aux meilleures pratiques en matière de création d'images sécurisées

  • dockerfile-lint Linter basé sur des règles pour Dockerfiles

  • hadolint Un linter de fichiers Docker intelligent

  • Gatekeeper et OPA Un contrôleur d'admission basé sur des politiques

  • Kyverno Un moteur de politiques natif de Kubernetes

  • in-toto Permet à l'utilisateur de vérifier si une étape de la chaîne d'approvisionnement était censée être réalisée et si l'étape a été réalisée par le bon acteur

  • Notaire Un projet pour signer des images de conteneurs

  • Notaire v2

  • Grafeas Une API ouverte de métadonnées d'artefacts pour auditer et gérer votre chaîne d'approvisionnement logicielle

  • NeuVector de SUSE Open Source, plate-forme de sécurité des conteneurs Zero-Trust, permet d'analyser les conteneurs, les images et les registres pour détecter les vulnérabilités, les secrets et la conformité.