WebRTC a bien décoincé le monde de la visioconférence en permettant de partager des flux d'images directement dans un navigateur web sans devoir installer d'applications (avec des soucis de compatibilité, d'OS, de droits).
Une URL, et hop, c'est partagé.
Rapidement, en plus de la webcam, il a été possible de partager des fenêtres et même des écrans. Petit détail : il n'est pas rare d'avoir dans le groupe une personne avec un écran énorme, en haute définition. Pour l'instant, les browsers ne proposent pas de redimensionner la fenêtre, et ils envoient tous les pixels dans le tuyau, un flot avec des milliers de lignes de résolution. Si vous n'avez pas une jolie fibre, votre flot montant se fait engorger, et ça perturbe le flot descendant, le son devient saccadé, bref, vous avez tout cassé.
Si votre bande passante est suffisante, vous allez envoyer une image énorme, avec un texte tout petit, et donc des galères de scroll pour ceux qui ont des écrans de taille raisonnable.
Il est possible de faire plus simple et plus efficient.
Travailler en mode texte (et pas en mode image) reste le pilier de l'administration système. Même Windows s'y met, c'est dire si c'est une bonne idée.
Il est tellement trop simple d'envoyer du texte dans le tuyau et de l'afficher proprement de l'autre côté.
TTYd
ttyd est une passerelle temporelle entre les terminaux des années 70 et les websockets des années 10 (2010 hein), un pont d'à peu près 40 ans de large.
Techniquement, ttyd
expose un TTY, via une websocket, vers xterm.js avec ce qu'il faut d'HTML autour. xterm.js est utilisé par à peu près tous les terminaux en javascript, il est bien fini et gère tout ce dont on attend d'un terminal.
La sécurité de la connexion est celle des browsers webs : TLS et DNS.
Pour rendre service, ttyd
met à disposition du basic-auth, mais rien n'empêche de gérer en amont une authentification en OAuth2. Il est tout à fait imaginable de brancher Gitlab pour avoir de l'OAuth2 avec 2 facteurs, et un lien avec le projet pour y brancher un terminal.
Pour les vrais paranos, ttyd
propose l'option lecture seule, où l'on retire le clavier aux spectateurs.
Comme c'est un affichage en HTML, il sera possible de copier des bouts de texte et même de changer la taille de l'affichage, avec un bête [ctrl][+].
Ah oui, qui dit page web, dit URL, et donc un moyen simple de fournir l'adresse via un mail ou du tchat.
Tmux
ttyd
expose un terminal, mais ne le partage pas. Pour partager un terminal, on pourrait imaginer un bête miroir pour chacun (comme ce que l'on en a en visioconférence), mais cette question est résolue depuis longtemps avec tmux (pour Terminal MUltipleXeur). Tmux marche très bien en local, en ssh, et donc en ttyd
. Un bon partage de terminal commence par se caler sur le plus petit, histoire que personne n'ait à scroller, même avec un partage en lecture seule.
Tmux permet aussi de se détacher d'un terminal et de revenir plus tard, et pour les audacieux, de découper l'écran, pour afficher plusieurs trucs en même temps.
Docker
C'est juste une session que l'on souhaite exposer, pas une machine complète. Pour ça, il ne faut exposer que le nécessaire et donc utiliser les namespaces de Linux.
Docker fait ça très bien, et il va pouvoir gérer la grappe de service nécessaire à la présentation :
- ttyd
- un agent SSH avec LA clef utile pour la démo
- un bash dans un tmux, avec un accès à la socket de
ssh-agent
Là, l'objectif est de faire une présentation dans un terminal, à un groupe de personnes distantes. La présentation va utiliser SSH, pour expliquer comment gérer automatiquement un serveur distant.
Le plus simpliste est d'avoir un partage ttyd
en lecture seule, qui va s'attacher à une session tmux. Une session SSH qui va lancer la grappe de services et s'attacher au tty du conteneur tmux. Rien ne tourne en root et il est possible d'ajouter une clef SSH spécifique au projet, pour 1h, avec un conteneur temporaire.
Tout ça est bien rangé avec ce qu'il faut de Makefile et de scripts bash : https://github.com/factorysh/docker-ttyd
Sécurité
Donner un accès distant à une machine via une page web existe depuis longtemps, ça s'appelle un webshell , que nos amis de PHP craignent tant.
Il faut donc suivre scrupuleusement les consignes de sécurité et mettre en place une défense en profondeur. La Première règle est de fournir des droits minimums.
Dans notre cas, ça détermine les choix suivants :
- ttyd est lancé avec l'option lecture seule ;
- le tmux est dans un conteneur non privilégié, avec peu de paquets installés ;
- le ssh utilisé depuis la session a son ssh-agent dédié, et une clef dédiée qui n'est reconnue que par le serveur cible. La clef n'est dans la session que pour 1h ;
- chaque service a son conteneur et ne partage que le nécessaire avec les autres ;
- la VM est isolée des autres VMs, avec son propre sous réseau.
La deuxième règle est d'avoir des outils à jour, et dont on a confiance.
- Le web est confié à golang, avec Traefik qui va utiliser Let's Encrypt pour n'utiliser que du TLS ;
- Les conteneurs sont reconstruits avant chaque session ;
- la VM utilise la version stable de l'OS, avec un kernel à jour, ce qui est toujours mieux quand on utilise des conteneurs.
Normalement, on donne des limites à ses conteneurs, pour que ne pas qu'un conteneur qui devient amok entraîne les autres dans sa chute. Mais bon, là, la VM est tellement petite que ça ne changera pas grand chose. Cgroup, sans contraintes, reste pertinent pour remonter des données et afficher des informations dans ctop .
La partie audit n'est pas ultime. Il faudrait sortir les logs sur une autre VM, en utilisant le driver fluent de docker pour causer à un fluentbit qui écrit dans un fichier plat pour commencer. Il est très tentant de récupérer les bouts de code de teleport qui utilise ebpf pour avoir des logs précis de ce qui est fait dans le shell interactif. Le code est là , avec une license Apache2 permissive.
Pour bien faire, il faudrait lever la VM à la volée et tout bazarder une fois la session terminée (en conservant les logs distants, et un instantané de la home dans un stockage à la S3).
Aller plus loin
TTY c'est chouette, mais SSH n'est pas la réponse universelle pour un accès TTY distant. Il y a plein de choses à explorer avec OpenSSH (comme les clefs publiques que l'on va chercher dans Gitlab, ou les clefs signées, ou les clefs jetables, enfin, recyclables, avec une durée de validité), mais aussi les alternatives webs.
Mettre à disposition une session TTY, en interactif ou non, de manière temporaire, avec des droits fins, sur un service qui est quelque part, fait partie des tendances actuelles et va continuer de se répandre.
Comme vrais exemples, aller jeter un oeil sur Gitlab qui sait exposer une console pour déboguer une CI qui s'est coincée, mais surtout, teleport qui donne un accès distant et paranoïaque, avec une capacité d'audit très poussée.
Crédit Image DEC VT100 terminal