BOUNDARY, OU L’ART DE GÉRER L’ACCÈS À VOS RESSOURCES PRIVÉES

Rédigé en collaboration avec Clément LECHEVALLIER.

BOUNDARY, C’EST QUOI ?

DÉFINITION

Boundary est un outil développé par Hashicorp, éditeur de Terraform. Il permet de mettre en place une gestion des droits sur l’accès à des ressources inaccessibles depuis internet, comme des bases de données par exemple. Boundary permet de remplacer des bastions existants.

Dans le cas où on utilise un bastion (une instance dans un sous réseau public pour faire un rebond vers un sous-réseau privé), on pourrait ne pas vouloir que n’importe qui passant par le bastion puisse se connecter à toutes les ressources présentes dans le réseau privé. Pour faire cela, il serait possible de rajouter un firewall dans le réseau pour limiter les accès des utilisateurs connectés par le bastion.

UTILISATION D’UN BASTION

alt_text

Dans ce cas-là, beaucoup de ressources sont mises en place et l’utilisateur a besoin d’avoir beaucoup d’informations à disposition : connexion VPN ou SSH, IP ou Hostname de la machine à atteindre et credentials à utiliser dans la base de données.

Devoir donner un accès VPN ou SSH unique à chaque personne qui vient dans l’entreprise ou l’enlever à chaque personne qui part demande une bonne gestion surtout si on fait de la key rotation. L’IP et hôte ne sont pas forcément statiques dans un cas réel donc il faut que l’utilisateur puisse connaître la nouvelle IP ou le nouvel hôte à chaque changement. En donnant les credentials de la base de données aux utilisateurs, on expose donc les données de la BDD car il y a une possibilité de fuite de ces identifiants.

Cette infrastructure ne peut donc pas fonctionner dans un modèle d'infrastructure dynamique utilisant l’autoscaling.

UTILISATION DE BOUNDARY

alt_text

Dans ce cas-là, l’utilisateur ne se connecte plus avec un VPN ou en SSH, il se connecte par SSO (Single Sign-On) en utilisant un provider d’identité de son choix parmi Auth0, Okta et Azure. Ensuite, des politiques sont mises en place de manière logique (service logique important pour ne pas dépendre des IP) pour permettre ou restreindre l’accès aux ressources en fonction de la personne définie sur le service SSO.

Pour se connecter, l’utilisateur utilise la commande boundary connect sur sa CLI (Command Line Interface) et un agent se lance en arrière-plan pour connecter automatiquement l’utilisateur à la base de données. Ensuite, l’utilisateur communique avec l’agent lorsqu’il exécute des commandes au travers de la console et l’agent les envoie jusqu’à la base de données. Dans cette configuration, l’utilisateur ne peut pas accéder à une autre ressource que la base de données car il n’a pas le rôle nécessaire et qu’il n’est pas dans le réseau privé, il est dans l’internet publique.

Ici pour ajouter un utilisateur, il suffit de l’ajouter au provider d’identité, il y a suppression du ssh ou du vpn. Les règles logiques de policy et de RBAC (Role Based Access Control) permettent de ne plus se préoccuper des IP. En ne laissant pas directement l’utilisateur accéder au réseau privé, on est dans un modèle zero-trust. Cela signifie que par défaut, l’utilisateur n’a aucun droit. Il est donc impossible pour un utilisateur d’accéder à une ressource particulière si aucune politique ne lui permet d’y accéder. En ayant directement la gateway qui accède aux ressources, il est possible de ne plus donner les credentials à tous les utilisateurs. En effet, en connectant la gateway à vault, un autre outil hashicorp (ou n’importe quel gestionnaire de mots de passe), il est possible de permettre à la gateway de récupérer les informations de connexion d’un utilisateur particulier dans un vault et de l’authentifier automatiquement sans que les credentials transitent hors de Boundary.

WORKER / CONTROLLER C’EST QUOI ?

Le fonctionnement de base de Boundary se fait avec 2 types de machines virtuelles, les workers et les controllers. Le controller héberge la plateforme web et permet de définir les droits d’accès ainsi que les hôtes pouvant être accédés. Aucune donnée n’est sauvegardée dans le controller ou le worker mais dans une base de données Postgres, ce qui permet d'augmenter le nombre de controller ou de worker en fonction de la charge vu qu’ils ont tous accès aux mêmes données. Le worker permet ensuite d’établir la connexion entre l’ordinateur de l’utilisateur et l’hôte. Le controller permet de donner des ordres au worker via des appels API sur le port 9201 pour ouvrir des connexions entre l’utilisateur et la ressource dans le sous-réseau privé.

POURQUOI L’UTILISER ?

ARCHITECTURE RESILIENTE

Dans les infrastructures qui contiennent un nombre important de ressources et qui ont beaucoup d’utilisateurs qui se connectent simultanément, il est intéressant d’avoir plusieurs controller et worker pour supporter la charge. Pour cela, il faut externaliser la base de données Postgres sur une RDS (sur AWS par exemple). On peut utiliser un gestionnaire de secrets comme AKS pour gérer l’accès aux ressources privées. Ensuite on crée 2 autoscaling group pour les worker et les controller que l’on positionne derrière un load balancer. Cette architecture résiliente est disponible sur le schéma ci-dessous et est disponible sur le dépôt github de la source du schéma :

alt_text

Source : https://github.com/hashicorp/boundary-reference-architecture

GESTION

Un des plus gros atouts de Boundary est la gestion des droits d’accès, soit RBAC. En effet, lors de la mise en place d’un bastion classique, l’accès SSH est utilisé pour pouvoir se connecter au Bastion. Il suffit donc d’avoir la clé privée pour se connecter. Sur Boundary, il y a une gestion des utilisateurs avec une gestion des droits. Il est possible de donner accès à un groupe de machines A pour l’utilisateur 1 et un accès aux groupes de machines A et B pour l’utilisateur 2.

Tous ces droits peuvent être définis par un administrateur via l’interface utilisateur ou via Terraform lors du déploiement de Boundary.

La gestion des droits et des utilisateurs nécessitent une administration plus importante comparé à un bastion classique.

DÉPLOIEMENT ET UTILISATION

Pour déployer Boundary, il existe 2 méthodes. La première consiste à créer un service linux pour le worker et un service pour le controller qui auront chacun des fichiers de configuration spéciaux. La deuxième méthode consiste à utiliser des images docker spécifiques qui contiennent boundary et permettent d’interpréter les fichiers de configurations du controller et du worker. Pour configurer Boundary, il existe plusieurs méthodes. Terraform peut être utilisé avec un provider spécifique. Il suffit de saisir toutes les ressources Boundary dedans et le déploiement est automatique. La configuration peut être effectuée avec la CLI ou l’interface Web. L’interface Web a quelques limitations par rapport à Terraform ou la CLI. Finalement, le déploiement de Boundary est plus contraignant que celui d’un bastion. Il faut donc prendre cela en compte et s’assurer que Boundary est un outil qui correspond à la taille du projet. On peut également utiliser la CLI ou l’interface web pour configurer les différentes ressources.

Au niveau de l’utilisation, Boundary desktop peut être utilisé pour se connecter aux machines distantes. Avec notre expérience, l’application ne fonctionne pas parfaitement sur Windows. La CLI peut être utilisée et c’est le moyen le plus simple pour utiliser Boundary. Le point négatif est qu’il est nécessaire d’installer le binaire utilisé pour se connecter aux ressources privées. Par exemple, si on veut accéder à une base de données mysql, il est nécessaire d’avoir mysql sur le client. Sur un bastion, on se serait connecter en SSH au bastion et mysql aurait été présent sur le bastion pour pouvoir se connecter à la base de données. En contrepartie, cela apporte de la sécurité de ne pas avoir l’utilisateur directement à l’intérieur du réseau privé.

Pour tester des configurations et utilisations de Boundary, il est possible de démarrer facilement un environnement de développement avec la commande : “boundary dev”. Cet environnement s’exécute en local et nécessite docker pour déployer la base de données postgres.

Avantages : Inconvénients :
👍 Gestion de session avancée 👎 Mise en place plus compliquée
👍 Plus de sécurité 👎 Nécessite maintenance
👍 Facilité de gestion
👍 Grande disponibilité

LES DIFFÉRENTES RESSOURCES SUR BOUNDARY

alt_text

_Source : Hashicorp Learn _

Voici l’architecture de gestion de l’interface web de Boundary. Cette architecture est séparée en Projets au sein d’une organisation.

Les utilisateurs sont liés à l’organisation, il y est défini une Auth Method, une méthode d’authentification comme un sso par exemple. Il y a donc une liste d’utilisateurs et des rôles que l’on peut donner à chaque utilisateur pour gérer son accès aux différents projets. Il est aussi possible de répartir les utilisateurs dans des groupes et donner des rôles à ces groupes, rôles qui seront hérités par les fils présents dans les groupes.

Au sein de chaque projet, on trouve un Host catalog. Dans cet Host catalog, se trouve un ou plusieurs Host set permettant d’accéder à des ressources au travers d’un ou plusieurs Host. Un **Host **représente une adresse permettant d’accéder à la ressource. Un Host set quant à lui est un groupe de Host considérés comme équivalents pour accéder à la même ressource.

ACCÉDER À UN ENVIRONNEMENT DE DEV SUR SON PC

MISE EN PLACE DE L’ENVIRONNEMENT

L’objectif de ce tutoriel est de lancer un premier environnement de dev et de se connecter en ssh à sa propre machine locale en passant par Boundary.

Tout d’abord, il faut s’assurer d’avoir docker et boundary installés. Ensuite, il faut exécuter dans un terminal la commande qui permet de lancer Boundary en mode développement :

❯ boundary dev

Vous devriez obtenir quelque chose qui ressemble à ça :

❯ boundary dev
==> Boundary server configuration:

        [Controller] AEAD Key Bytes: BzB4O6vmja/h7wIgLA9v1C8fuzeJt2dP
          [Recovery] AEAD Key Bytes: tAvlOl47ur23/uUW/y0as1KyUxdWWUfr
       [Worker-Auth] AEAD Key Bytes: YW+vkVrlhC1PlkiAl9qYiwj5PvqyS2Hs
               [Recovery] AEAD Type: aes-gcm
                   [Root] AEAD Type: aes-gcm
    [Worker-Auth-Storage] AEAD Type: aes-gcm
            [Worker-Auth] AEAD Type: aes-gcm
                                Cgo: disabled
     Controller Public Cluster Addr: 127.0.0.1:9201
             Dev Database Container: vibrant_liskov
                   Dev Database Url: postgres://postgres:password@localhost:49153/boundary?sslmode=disable
         Generated Admin Login Name: admin
           Generated Admin Password: password
          Generated Host Catalog Id: hcst_1234567890
                  Generated Host Id: hst_1234567890
              Generated Host Set Id: hsst_1234567890
      Generated Oidc Auth Method Id: amoidc_1234567890
             Generated Org Scope Id: o_1234567890
  Generated Password Auth Method Id: ampw_1234567890
         Generated Project Scope Id: p_1234567890
                Generated Target Id: ttcp_1234567890
  Generated Unprivileged Login Name: user

Ensuite, il faut paramétrer des variables d’environnement pour choisir la méthode d’authentification par mot de passe (celle par défaut) et l’ID de la cible sur laquelle on va se connecter, qui a été créée automatiquement et qui correspond au localhost de votre PC. C’est pourquoi il faut que le serveur ssh tourne en local pour accepter les connexions entrantes.

❯ export AUTH_ID=ampw_1234567890
❯ export TARGET_ID=ttcp_1234567890

Vous allez ensuite vous authentifier avec la commande :

❯ boundary authenticate password -auth-method-id=$AUTH_ID -login-name=admin

Il faut saisir le mot de passe : password (oui c’est pas très sécurisé mais on est uniquement en local donc pas de problème)

Il faut saisir le token obtenu dans la variable d’environnement BOUNDARY_TOKEN.

❯ export BOUNDARY_TOKEN=${VOTRE_TOKEN}

A partir de maintenant, la CLI est authentifiée. Vous vous connecterez en ssh sur votre PC par la suite.

Vous pouvez accéder à l’interface web via le lien http://localhost:9200. Il faut saisir les credentials (admin et password). Vous pouvez naviguer entre les options de l’interface, qui est minimaliste et assez claire.

alt_text

Vous pouvez observer sur cette image que l’hôte saisit en variable d’environnement précédemment est bien sur localhost. Ce qui signifie que lorsqu’on va indiquer à Boundary que l’on veut s’y connecter, il cherchera à l’adresse localhost.

Revenons sur la CLI. Pour se connecter, il faut utiliser cette commande :

❯ boundary connect ssh -target-id $TARGET_ID

Après le connect, il faut spécifier la commande à exécuter en local pour se connecter à la machine distante. Ici vous utilisez ssh mais si la machine distante est une base de données postgres, il faudra utiliser la commande :

❯ boundary connect postgres -target-id $TARGET_ID

Si l’exécutable n’est pas géré par la CLI de boundary, il est possible d’utiliser l'argument -exec pour exécuter une autre commande qui est installée sur votre PC comme mysql ou redis-cli. Voici un exemple avec redis-cli :

❯ boundary connect -target-id ${TARGET_ID} -exec redis-cli -- -h 127.0.0.1 -p {{boundary.port}} KEYS \*

Revenons au SSH en local, le mot de passe de votre session vous est demandé. Ensuite vous avez un accès à votre machine. Ce cas est inutile et à titre d’exemple mais on peut imaginer que la machine distante peut être un serveur dans un sous-réseau privé.

Vous pouvez observer la connexion entre votre pc et l’hôte depuis l’interface WEB comme vous pouvez le voir ci-dessous :

alt_text

Vous pouvez observer toutes les informations sur la session et il est possible de la supprimer avec le bouton Cancel pour déconnecter l’utilisateur.

POUR CONTINUER

Boundary est un outil puissant et complet que nous avons très peu détaillé ici. Voici un lien vers la documentation et des tutoriels pour apprendre à l’utiliser de la manière la plus complète possible : https://learn.hashicorp.com/boundary