5 étapes pour intégrer Istio avec OPA

L’authentification et l’autorisation constituent de grandes parties du puzzle de la sécurité qui doivent être résolues par les architectes cloud et les ingénieurs DevOps. Dans ce blog, nous examinerons spécifiquement comment réaliser l’autorisation/contrôle d’accès ; c’est-à-dire quelles actions l’entité authentifiée peut effectuer dans le réseau de services Istio. Elle aide à sécuriser l’infrastructure en prévenant les actions de nature malveillante.

L’autorisation dans un réseau de services peut être définie à l’aide de politiques OPA. L’OPA est un mécanisme qui aide les gens DevOps à définir et à appliquer des politiques d’autorisation pour les charges de travail Kubernetes. Dans cet article, nous verrons :

  • Qu’est-ce que l’OPA
  • Pourquoi vous devez intégrer l’OPA au réseau de services Istio
  • Comment Istio et l’OPA autorisent les demandes
  • Les étapes exactes que vous pouvez suivre pour intégrer l’OPA à Istio

Qu’est-ce que l’OPA ?

L’OPA (pour « Open Policy Agent ») est un moteur d’application ouvert source et polyvalent qui permet aux DevOps de définir les politiques en code en utilisant une langue déclarative de haut niveau appelée Rego. L’OPA permet de définir et d’appliquer des politiques de manière centralisée sur l’ensemble de l’infrastructure, en soulageant les développeurs de l’obligation deécrire des politiques d’autorisation dans le code de l’application. Voici comment l’OPA fonctionne (voir Figure 1) :

  1. L’application/service reçoit une demande.
  2. Le service envoie une demande d’autorisation JSON à l’OPA.
  3. L’OPA vérifie la demande en fonction des politiques d’autorisation définies.
  4. L’OPA prend la décision et retourne la réponse d’autorisation (ALLOW/DENY) au service au format JSON.

Figure 1 : Flux de demande d’autorisation avec OPA

Notez que ce n’est pas nécessairement une application écrite par un développeur qui envoie la demande d’autorisation : il peut s’agir d’Argo CD, de ressources de l’API du pontigateur Kubernetes, de Terraform, de Prometheus ou de quoi que ce soit d’autre car OPA est une plateforme polyvalente. (J’ai mentionné et dessiné une application dans un cluster Kubernetes pour des raisons de commodité et de meilleure compréhension.)

Pourquoi intégrer OPA à Istio ?

Istio dispose d’un mécanisme robuste d’autorisation. Cependant, avoir un moteur de mise en œuvre de politiques spécifique comme OPA en parallèle avec le réseau service Istio offre ses propres avantages :

  • Système de gestion centralisé pour définir et appliquer les politiques : OPA permet au DevOps de gérer centralisé les politiques d’autorisation pour l’ensemble de l’stack. Cela inclut les charges de travail enroulées dans le réseau, l’stack non enroulé et les vérifications d’autorisation (une politique qui empêche la déploiement le vendredi, par exemple).
  • Plus de flexibilité et de granularité dans la définition des politiques : Si vous examinez la table ci-dessous (Figure 2), il est clair que l’autorisation d’Istio peut faire beaucoup et correspondre à une demande en fonction d’une variété de champs issus de sources de données différentes. Cependant, la CRD AuthorizationPolicy d’Istio peut avoir des limitations dans la configuration du corps de la demande HTTP ou tout autre donnée contextuelle dans les champs, à laquelle peut s’avérer utile OPA. Contrairement à Istio, OPA peut utiliser n’importe quelle donnée pour l’évaluation des politiques.
  • Configuration simplifiée d’AuthZ : Il peut être fastidieux pour le DevOps de configurer des règles d’autorisation complexes dans Istio. OPA est configuré à l’aide de Rego, qui est plus proche d’une langue de programmation. Il est comparativement plus facile de définir des règles de politique basiques à complexes en utilisant Rego.

Figure 2 : Comparaison tabulaire entre l’autorisation d’Istio et d’OPA (source)

Comment Istio et OPA autorisent les demandes

Les DevOps peuvent déployer OPA en tant que service distinct ou en tant que conteneur sidecar en accompagnant le proxy Envoy et le conteneur de l’application dans un pod. L’approche du conteneur sidecar est préférable pour réduire la latence.

Les conteneurs sidecar d’OPA doivent être injectés dans le pod de l’application tout comme les conteneurs sidecar du proxy Envoy d’Istio. Nous pouvons configurer les conteneurs OPA injectés pour monter les ConfigMaps contenant les règles d’autorisation ; chaque conteneur sidecar OPA dans le namespace montera alors la même configuration et les mêmes règles AuthZ définies dans le ConfigMap.

Une fois que le conteneur sidecar OPA est injecté, le proxy Envoy enverra des demandes d’autorisation à OPA pour prendre des décisions d’autorisation lorsque le service reçoit une demande :

Figure 3 : Workflow d’autorisation Istio-OPA

Supposons que les DevOps ne veulent pas que chaque conteneur OPA injecté dans le même namespace suit les mêmes configurations et veulent imposer des règles différentes. Dans ce cas, ils devront faire l’une des actions suivantes :

  • Enlever le codage dur qui permet à la politique actuelle d’injection d’utiliser un ConfigMap spécifique
  • Configurer un webhook mutant et désactiver l’injection sidecar au niveau du pod.
  • Fournir des ensembles de politiques à partir d’un serveur HTTP distant
  • Déployer l’application et les sidecars dans un espace de noms différent avec un ConfigMap différent

Étapes pour intégrer OPA avec Istio : démonstration

L’idée ici est de faire de OPA l’autorisateur externe au lieu des sidecars du proxy Envoy — pour prendre les décisions d’autorisation d’accès.

Je vais utiliser la classique application Bookinfo des documents Istio pour la démonstration. Je configurerai OPA avec Istio pour l’autorisation d’accès et vérifierai si cela est appliqué en envoyant des demandes à bookinfo/productpage :

Figure 4 : Diagramme d’intégration Istio-OPA

Notez que /productpage est l’UI, qui fait des appels internes à d’autres services, tels que les services de critiques et de notes (diagramme). Je injecterai OPA dans chaque pod dans l’espace de noms bookinfo ; tous les conteneurs OPA montrent le même ConfigMap et ont les mêmes politiques d’autorisation en conséquence. Le comportement par défaut de l’application Bookinfo n’encamine aucune authentification HTTP, donc les appels internes échoueront l’authentification et donc l’autorisation.

Nous suivrons les étapes données dans l’ordre :

  1. Configurer l’injection de sidecar OPA
  2. Permettre la communication entre le proxy Istio et OPA
  3. Déployer la configuration d’OPA
  4. Appliquer la configuration Istio
  5. Déployer l’application et tester le dispositif d’autorisation Istio-OPA

La condition préalable pour la démonstration est d’avoir installé Istio v1.19+ dans votre cluster. J’utilise ici Istio v1.21.0.

OPA fournit un fichier quickstart.yaml pour une installation rapide. J’ai divisé le fichier YAML en trois parties pour une meilleure compréhension : le dépôt GitHub IMESH

Étape 1 : Configurer l’injection du sidecar OPA

Appliquer le fichier opa_controller.yaml :

YAML

 

kubectl apply -f opa_controller.yaml

Le fichier opa_controller.yaml déploie tout : les certificats TLS, le ConfigMap contenant la stratégie d’injection, le déploiement du contrôleur d’admission et la configuration du webhook mutant — dans le namespace opa-istio (voir le dessin 5) :

  1. Le contrôleur de webhook mutant (opa-istio-admission-controller) écoutera ensuite pour une étiquette particulière (opa-istio-injection) avec la valeur définie sur enabled.
  2. Le contrôleur webhook appelle l’admission-controller qui contient la politique d’injection.
  3. La politique d’injection indique à l’admission-controller comment injecter le conteneur sidecar OPA dans le pod.

Figure 5 : Configuration d’injection du sidecar OPA

Maintenant, avant de déployer l’application Bookinfo, nous créerons le namespace bookinfo et suivrons les autres étapes :

Créer le namespace bookinfo en appliquant bookinfo-ns.yaml :

YAML

 

kubectl apply -f bookinfo-ns.yaml

You can see the namespace has the label opa-istio-injection: enabled, to auto-inject OPA sidecars.

Étape 2 : Activer la communication entre le proxy Istio et OPA

Modifiez le ConfigMap Istio dans le namespace istio-system et ajoutez extensionProviders (opa-ext-authz-grpc), afin de permettre l’autorisation externe dans la toile :

  • Copiez extensionProviders de la note dans opa_controller.yaml.
  • Modifiez le ConfigMap Istio et ajoutez extensionProviders dans le champ toile.
  • Assurez-vous que l’indentation est correcte.
  • Enregistrez la configuration.

Cette étape permet au istio-proxy de communiquer avec le conteneur opa-istio du pod pour les demandes d’autorisation.

Si vous examinez les extensionProviders, c’est un filtre de type ExtAuthzGrpc dans Envoy avec une entrée de service et un port spécifiés :

YAML

 

...

extensionProviders:
- name: opa-ext-authz-grpc
envoyExtAuthzGrpc:
service: opa-ext-authz-grpc.local
       port: "9191"

...

Le nom, l’adresse du service et le port des extensionProviders doivent être les mêmes dans le opa_authz.yaml et le opa_config.yaml.

Étape 3 : Déployer la configuration d’OPA

Le opa_config.yaml définit les configurations relatives à la politique ouverte. Il contient les opa-istio-config et les opa-policy ConfigMaps — qui définissent respectivement l’implémentation du service gRPC (envoy_ext_authz_grpc) et les politiques d’autorisation actuelles.

Les politiques d’autorisation peuvent être divisées en deux parties : la première définit les conditions sous lesquelles l’autorisation est autorisée ou refusée ; la seconde définit les rôles des utilisateurs et les permissions pour chaque rôle.

Les politiques d’autorisation peuvent être un peu difficiles à adapter, car Rego n’utilise pas beaucoup de mots-clés ici. Activez une nouvelle version de Rego pour obtenir des mots-clés (par exemple, le mot-clé allow if condition).

Appliquez la configuration d’OPA dans l’espace de noms bookinfo, comme cela correspond à l’application :

YAML

 

kubectl apply -f opa_config.yaml -n bookinfo

Étape 4 : Appliquer la configuration d’Istio

Le fichier opa_authz.yaml contient des configurations Istio. Il contient une AuthorizationPolicy et un ServiceEntry. Notez que le fournisseur de politique d’autorisation est opa-ext-authz-grpc, qui est le extensionProvider que nous avons configuré dans le ConfigMap à l’étape 2.

De même, le nom d’hôte défini dans le ServiceEntry est le même que l’adresse du service fournie dans le extensionProvider (opa-ext-authz-grpc.local). Le service gRPC s’exécutera sur le port 9191 à l’adresse locale 127.0.0.1, ce que le ServiceEntry permet aux sidecars opa-istio d’accéder au pod par le biais du conteneur istio-proxy.

Déployez la configuration :

YAML

 

kubectl apply -f opa_authz.yaml -n bookinfo

Étape 5 : Déployer l’application et tester la configuration d’autorisation Istio-OPA

Déployez l’application Bookinfo et le gateway :

YAML

 

kubectl apply -f /your_Istio_directory/samples/bookinfo/platform/kube/bookinfo.yaml -n bookinfo
kubectl apply -f /your_Istio_directory/samples/bookinfo/networking/bookinfo-gateway.yaml -n bookinfo

Vérifiez les pods dans le namespace bookinfo :

YAML

 

kubectl get pods -n bookinfo

Vous pouvez voir que chaque pod contient 3 conteneurs en cours d’execution : l’application, le proxy Envoy (istio-proxy) et OPA (opa-istio).

Obtenez l’IP du gateway Istio pour accéder au service :

YAML

 

kubectl get svc -n istio-system

Maintenant, tout est prêt et nous sommes prêts à tester les politiques d’autorisation. Les politiques que nous avons définies dans opa_config.yaml sont les suivantes :

YAML

 

...

user_roles = {
"alice": ["guest"],
"bob": ["admin"]
}

role_perms = {
"guest": [
{"method": "GET", "path": "/productpage"},
],
"admin": [
{"method": "GET", "path": "/productpage"},
{"method": "GET", "path": "/api/v1/products"},
        ],

...

Alice est un utilisateur invité qui ne peut accéder qu’à /productpage ; Bob est un administrateur qui peut accéder aux chemins /productpage et /api/v1/products. Vérifions les politiques.

Tentez d’accéder à /api/v1/products depuis Alice :

YAML

 

curl -vvv your_istio_gateway_ip/api/v1/products -u alice:password

Vous pouvez voir que la réponse 403 Interdit depuis Alice n’a pas accès au chemin. Essayons le même chemin que Bob :

YAML

 

curl -vvv your_istio_gateway_ip/api/v1/products -u bob:password

Il affiche l’état HTTP 200 OK et le contenu de la page à la fin de la réponse.

Exemple de scénario pour le contrôle d’accès avec OPA

Vous pouvez utiliser la CRD AuthorizationPolicy d’Istio pour appliquer la politique montrée dans la démo ci-dessus. Vous n’avez pas besoin d’OPA. Cependant, il y a des cas où le contrôle d’autorisation d’Istio peut être limité, comme mentionné dans le tableau au début. Laissez-moi donner un exemple simple.

Supposons qu’il y ait une application BookReviews qui est un service GraphQL, où les critiques soumettent des avis, les éditeursédits et publient ces avis, et les utilisateurs lisent les avis publiés.

Lorsqu’un critique ajoute une critique de livre au service, la requête incluera le JWT du critique, contenant les groupes et rôles (critique ou éditeur) auxquels le critique appartient. Le corps de la requête contiendra également la requête de mutation GraphQL avec les données de critique nouvellement créées.

Disons que vous souhaitez s’assurer des conditions suivantes :

  • Seuls les critiques peuvent soumettre des avis.
  • Un éditeur ne peut éditer qu’une critique si elle est écrite par un critique qui appartient au même groupe géré par eux.
  • Seuls les éditeurs peuvent marquer une critique comme « prête à publier ».

Voici le diagramme incluant les politiques précédentes :

L’AuthorizationPolicy d’Istio aura du mal à enforcing les conditions précédentes. La raison est que Istio ne peut pas utiliser le corps de la requête GraphQL pour les vérifications d’autorisation, qui est un objet JSON en plus du JWT nécessaire pour l’évaluation de la politique.

OPA n’a pas de telles limitations. Il peut charger n’importe quelle donnée pour les vérifications de politiques, et les DevOps peuvent écrire ces règles de manière plus ergonomique en utilisant Rego.

Vidéo : démonstration en action

Si vous préférez observer la démonstration en action, veuillez consulter la vidéo ci-dessous :S

Support Enterprise pour l’intégration d’Istio

La plupart des entreprises utilisent OPA pour définir et en appliquer les politiques d’autorisation pour leur ensemble de logiciels. Disposer d’un mécanisme central de contrôle d’accès améliore la sécurité et l’agilité des équipes IT. Sinon, les développeurs perdront du temps en écrivant des politiques d’autorisation dans leur code application écrit dans une langue particulière, ce qui entrave la scalabilité et la mise en route plus rapide de la logique commerciale.

Source:
https://dzone.com/articles/5-steps-to-integrate-istio-with-opa