AWS : Communiquer avec vos EC2 sans réseau – La liberté du design d’architecture sans contraintes

Le Cloud AWS propose des aspects fabuleusement intéressants pour s’affranchir de contraintes intrinsèques liées à l’infrastructure classique, alors même que celle-ci est sans doute le cœur de votre déploiement dans le Cloud. C’est cela la magie du Cloud, et j’en suis tout émerveillé à chaque fois que j’y pense, notamment durant l’apéro du vendredi soir.

 

Posons la situation

Vous disposez de plusieurs VPC, solution choisie sans doute dans votre architecture pour réaliser un isolement des EC2 qui sont contenues dans chacun d’eux.

Comment faire, par exemple, pour réaliser un accès console depuis une machine bastion qui ne peut pas avoir de « pattes » vers des EC2 se trouvant dans deux VPC différents, ou diffuser des commandes globales sur un parc de serveurs ? Éventuellement utiliser un outil comme Ansible qui doit communiquer par ssh avec des serveurs cibles situés dans des VPC différents ?

Architectures possibles :
En restant dans une solution purement infra, la seule solution qui s’offre à nous dans ce cas est la mise en relation de VPC entre eux avec un mécanisme comme le VPC pairing ou une Transit Gateway, pour réaliser des routages inter VPC. Mais l’isolation réseau par VPC voulue au départ va demander le rajout de règles de sécurité supplémentaires dans les security groups ou les network Acls. De plus, la communication inter VPC est facturée au tarif d’échange de données inter AZ.

 

La solution offerte par AWS

AWS nous offre, dans son service System Manager, des solutions pour communiquer avec des serveurs sans accès réseau, et c’est là qu’entre en jeu la magie du Cloud !
Par les ramifications internes au Cloud et le déploiement d’agent SSM sur les serveurs, il va être possible de communiquer avec des EC2 situées dans différents VPC sans passer par les connexions réseaux classiques. Parmi les solutions proposées par System Manager, en voici deux que j’ai retenues, ayant rapport avec la problématique de départ.

  • La première solution s’appelle Session Manager. J’ai déjà fait un article sur ce sujet : « AWS – Accès aux serveurs Linux et Windows sans connexion réseau grâce à Connection Manager »
    qui traitait de sa mise en œuvre à partir de la console. Maintenant nous allons voir une autre possibilité et non la moindre, c’est celle de se connecter en ssh « over Connection Manager ».
  • La deuxième solution s’appelle Run Command. Par un principe similaire, il sera possible de lancer des commandes sur un système distant Windows ou Linux sans passer par le réseau.

NB : il est possible aussi de mettre en place ces solutions avec des serveurs on-premise à partir du moment où ceux-ci ont un agent SSM déployé. Cependant « la magie » n’est pas la même puisque dans ce cas l’on passera quand même par le réseau IP.

 

Pré-requis d’installation pour les deux solutions

aws ssm describe-instance-information \
--query 'InstanceInformationList[*].[InstanceId,AgentVersion,PlatformName,PingStatus]' \
--filters "Key=PingStatus,Values=Online" --output text

Le résultat est le suivant :

i-01ec0d587a151f593     2.3.714.0       Amazon Linux    Online
i-033693dc8795ea757     2.3.714.0       Amazon Linux    Online

 

Session Manager

Utilisation de base

Une fois installé l’agent SSM sur les cibles et AWS Cli et le plugin sur le serveur central, il est possible de se connecter en mode console sur les instances EC2 candidates par la commande suivante :

$ aws ssm start-session --target i-01ec0d587a151f593

Le résultat est le suivant :

Starting session with SessionId: jpc-terraform-090baf85dd6f83f47
sh-4.2$
Connexion ssh « over Connection Manager »

L’optique est maintenant de se connecter sur l’EC2 mais via une connexion ssh sans passer par le réseau.

Nous allons procéder à une configuration particulière ssh de notre utilisateur de connexion en suivant la procédure suivante :

  • Dans le répertoire .ssh du user, créer un fichier nommé config avec les droits « 600 » :
    $ touch config
    $ chmod 600 config
  • Mettre le contenu suivant dans le fichier :
# SSH over Session Manager
host i-* mi-*
      ProxyCommand sh -c "aws ssm start-session --target %h --document-name AWS-StartSSHSession --parameters 'portNumber=%p'"

Il est maintenant possible de se connecter sur un serveur EC2 avec la syntaxe suivante, c’est à dire en utilisant l’instance id comme paramètre de connexion @adresse dans la chaine ssh :

ssh -i id_rsa ec2-user@i-033693dc8795ea757
Last login: Mon Mar 30 11:25:51 2020 from localhost

__| __|_ )
_| ( / Amazon Linux 2 AMI
___|\___|___|

https://aws.amazon.com/amazon-linux-2/
[ec2-user@ip-172-31-17-247 ~]$

Quelle utilisation faire de cela, l’utilisation semble identique à l’utilisation dite « de base » faite plus haut ?

Je vous laisse donner libre cours à votre imagination, avec deux pistes :

 

Run Command

Run Command va plus loin dans le sens où cet outil permet de lancer des commandes en mode asynchrone sur un ou plusieurs serveurs EC2 (ou on-premise), avec la possibilité d’utiliser des « documents » qui sont des commandes pré-écrites par AWS et contenues dans un catalogue. Un des documents récents fait référence à Ansible.

Nous pouvons bien sûr rajouter des commandes développées « à façon » dans le catalogue des documents. Je vais, pour ma part et à titre d’exemple, utiliser un document parmi les plus simples qui permet d’envoyer des commandes shell aux EC2. Mais il existe beaucoup de choix dans le catalogue, comme la possibilité de réaliser un forward ssh avec le document « AWS-StartPortForwardingSession ».

Voici différentes commandes comme exemples d’utilisation :

  • Obtenir des liste de documents ainsi que leurs contenus :
$ aws ssm list-documents
$ aws ssm describe-document --name "AWS-RunShellScript" --query "[Document.Name,Document.Description]"
$ aws ssm describe-document --name "AWS-RunShellScript" --query "Document.Parameters[*]"
  • Exemple de commandes exécutées :
$ aws ssm send-command --document-name "AWS-RunShellScript" --parameters commands="echo Hello" --instance-ids i-033693dc8795ea757
ou
$ aws ssm send-command --instance-ids "instance ID" --document-name "AWS-RunShellScript" --comment "IP config" --parameters commands=ifconfig --output text

  • Comme la commande lancée est asynchrone, il faut pouvoir récupérer le statut de retour. Pour cela on peut mettre en œuvre sous la forme :
$ sh_command_id=$(aws ssm send-command --instance-ids i-033693dc8795ea757 --document-name "AWS-RunShellScript" --comment "Demo run shell script on Linux Instance" --parameters commands=whoami --output text --query "Command.CommandId")

$ aws ssm list-command-invocations --command-id $sh_command_id --details
  • On peut aussi rechercher les commandes qui ont réussi, etc … :
$ aws ssm list-command-invocations --filters "key=Status,value=Success"

 

Conclusion

Le Cloud AWS met à notre disposition de nombreuses possibilités originales liées à la caractéristique du Cloud qui est d’être une plateforme managée, et ainsi modifie les concepts classiques d’une architecture d’infrastructure.

Il vous reste maintenant à donner libre cours à votre imagination pour concevoir des architectures qui seront, à n’en pas douter, de petites merveilles !

 
Et si vous souhaitez vous former sur Amazon Web Services, découvrez notre offre de formations AWS.