====== Tmux, bastion, ssh a agent-forwarding ======
===== Tmux =====
Tmux je terminálový multiplexer pro Unix, který umožňuje vytvořit více pseudoterminálů v jednom přihlášeném okně (terminálu).
Tmux je vhodný pro uživatele, kteří stráví více času v terminálovém okně a využijí více současně otevřených obrazovek. Toto umožňují i ssh klienti s podporou záložek (tabs), např. Bitvise SSH client či Solar-Putty.
Tmux obvykle běží na serveru, kde uživatel otevře více obrazovek pro aplikace a spojení na další servery. Uživatel se může od serveru odpojit aniž by spuštěné aplikace skončily, časově náročné akce dál pokračují. K otevřeným obrazovkách se lze poté připojit i z jiného počítače.
Více informací:
* [[https://www.root.cz/clanky/okna-v-terminalu-pomoci-tmux/| Okna v terminálu pomocí tmux]]
* [[https://www.redhat.com/en/blog/introduction-tmux-linux|A beginner's guide to tmux ]]
* [[https://www.linuxtrainingacademy.com/tmux-tutorial/|Tmux Tutorial: Mastering the Basics]]
* [[https://github.com/tmux/tmux/wiki | Tmux documentation]]
===== Tmux a ssh =====
Z notebooku se přihlásíte pomocí ssh na server (**bastion**), zde spustíte tmux a z něho děláte ssh spojení na další servery.
{{:ruzne:tmux_1.png?direct|}}
Na notebooku máte privátní klíč v agentovi (pageant, ssh-agent), na další servery se chcete hlásit také pomocí klíče. Máte dvě možnosti:
* na bastionu máte uložen privátní klíč pro přihlášení na další servery,
* privátní klíč máte na notebooku a ve spojení na bastion máte zapnut **ssh agent forwarding** - pokud je na bastionu požadavek na operaci s privátním klíčem, tak se přepošle na agentovi na notebooku.
Obě řešení předpokládají, že plně důvěřujete správci bastionu. Starší, ale stále platný popis pro ssh agent forwarding je v článku [[http://www.unixwiz.net/techtips/ssh-agent-forwarding.html#sec | Security Issues With Key Agents ]].\\
Na bastion se nehlaste jako root - pod tímto uživatelem byste nikdy neměli spouštět tmux či mít pod ním aktivní ssh agent forwarding.
==== Privátní klíč na bastionu ====
{{ :ruzne:tmux_3.png?direct |}}
S privátním klíčem na bastionu je potřeba zajistit, aby na každé obrazovce v aplikaci tmux byl odkaz na stejnou instanci ssh-agent, aby se nespustili dvě instance ssh-agent. Nejjednodušším řešením je využít aplikaci [[https://www.funtoo.org/Funtoo:Keychain | keychain]], konkrétně do ''.bashrc'' v domovském adresáři doplnit řádek s odkazem na dostupný klíč, např.:
eval $(keychain --quick --eval id_ed25519)
Při přihlášení se zobrazí dotaz na heslo k privátnímu klíči.
{{ :ruzne:2024-12-25_165819.png?direct |}}
Privátní klíč na bastionu by měl být odlišný od privátního klíče na notebooku. Nezapomeňte, že musíte zajistit bezpečné zálohování obou privátních klíčů (na notebooku a na bastionu).
==== Ssh agent forwarding ====
{{ :ruzne:tmux_4.png?direct |}}
Agent forwarding se musí zapnout před vytvořením spojení. V PuTTY nejlépe nadefinovat a uložit příslušné sezení (session):
{{ :ruzne:2024-12-25_123754.png?direct |}}
Na MacOS či Unixu nadefinovat v .ssh/config
Host bastion
ForwardAgent yes
UpdateHostKeys yes
Unixové aplikace komunikují s agentem přes [[https://cs.wikipedia.org/wiki/Unix_domain_socket|socket]], na který odkazuje proměnná ''SSH_AUTH_SOCK''. Pokud je povolen agent forwarding, tak součástí připojení na bastion je vytvoření speciálního socketu, odkaz na něj uloží do proměnné (pokaždé jiný socket):
SSH_AUTH_SOCK=/tmp/ssh-XXXX9eHVSY/agent.15123
Z bastionu se poté můžete hlásit na další servery pomocí privátního klíče na notebooku, na bastionu můžete podepsat commit pro git, pomocí ssh můžete komunikovat s git serverem.
===== Tmux, agent forwarding a obnovení spojení =====
SSH spojení pomocí agent forwarding lze používat i z tmux - na bastionu vytvoříte novou obrazovku, z ní se připojíte na server.
Na problémy narazíte v situaci, kdy začnete využívat možnost odpojení se od terminálu a nového připojení k němu. Při vytvoření nového ssh spojení na bastion se vytvoří nový socket, ale již vytvořené obrazovky v tmux mají nastavenu proměnnou ''SSH_AUTH_SOCK'' na socket z předchozího spojení - nepřihlásíte se na jiný server. Jednoduché ale nepohodlné řešení je ukončit obrazovky (tmux) a znovu ho spustit.
Jiné řešení je do souboru **.bashrc** v domovského adresáři vložit následující řádky:
function prompt_command() {
if [ -n "${TMUX}" ]; then
eval "$(tmux show-environment -s)"
fi
}
PROMPT_COMMAND=prompt_command
Příkaz ''tmux show-environment -s'' vypíše vybrané proměnné, které se nastavily při spojení, mezi nimi i ''SSH_AUTH_SOCK''. eval znamená, že se proměnné mají nastavit.
Při opětovném připojení jsou již nějaké obrazovky vytvořeny, v nich je spuštěn bash. Speciální proměnná ''PROMPT_COMMAND'' obsahuje odkaz na funkci, která se má provést při zobrazení promptu. V ''.bashrc'' do ní nastavíme námi nadefinovanou funkci ''prompt_command''. Tj. v existujících oknech se aktualizuje proměnná ''SSH_AUTH_SOCK'', stačí stisknout klávesu enter. A nastaví se i při vytvoření nové obrazovky v tmu.
Další informace:
* [[https://www.johntobin.ie/blog/updating_environment_variables_from_tmux/ | Updating environment variables from tmux ]]
* [[https://without-brains.net/2020/08/05/tmux-and-ssh-agent-forwarding/ | Tmux and SSH agent forwarding]] (zsh)
===== Git na jiném serveru =====
Z bastionu se hlásíte na server vyvoj a na něm chcete používat git - komunikovat přes ssh s úložištěm, podepisovat commity pomocí svého ssh klíče. Aplikace git umí používat ssh-agent včetně agent forwarding.
Máte následující možná řešení:
- další privátní klíč na serveru vyvoj
- použít ssh agent forwarding a přesměrovat na privátní klíč na bastionu
- použít ssh agent forwarding a přesměrovat požadavky na privátní klíč na notebooku (řetězení agent forwarding)
Všechny varianty předpokládají, že důvěřujete administrátorovi na serveru vyvoj.
První varianta zvyšuje problémy se správou rozrůstajícího se počtu klíčů, s jejich zálohováním.
Ve druhé i ve třetí variantě je potřeba na bastionu nastavit agent forwarding v konfiguračním souboru ''.ssh/config'', např.:
Host vyvoj
ForwardAgent yes
Ve třetí variantě je potřeba ještě zajistit přepnutí na nový socket pro již otevřené spojení. Tj. pro situaci:
* přihlásíte se na bastion, z bastionu se v tmux přihlásíte na server vyvoj,
* ukončíte spojení na bastion, spojení z bastionu na server vyvoj zůstává aktivní,
* znovu se připojíte na bastion, vytvoří se nový socket,
* přepnete se na obrazovku se spojením na server vyvoj a zde zadáte příkaz git. Program ssh zajišťující spojení mezi bastionem a serverem vyvoj neví o tom, že se na bastionu změnil socket, přes který má požádat o operaci s privátním klíčem umístěném na notebooku.
{{ :ruzne:tmux_5.png?direct |}}
V článku [[https://blogsystem5.substack.com/p/ssh-agent-forwarding-and-tmux-done | SSH agent forwarding and tmux done right ]] jsou popsány problémy. Autor nabízí i možné řešení - aplikaci [[https://github.com/jmmv/ssh-agent-switcher | ssh-agent-switcher]]. \\
Řešení pomoc ssh-agent-switcher **není dostatečně stabilní** např. v situaci, kdy pomocí ansible chci udělat úpravu na 100 serverech - často ssh agent přestane ansible odpovídat po několika desítkách serverů. Mohu killnout příslušné ssh procesy, poté se připojí na další servery.
===== Změna titulku okna v tmux pro ssh =====
Když zadám v tmux příkaz
ssh abcdef.vse.cz
tak bych uvítal, aby se titulek obrazovky v tmux přejmenoval na abcdef.vse.cz či abcdef.
Nenašel jsem správné řešení. Základem by mohla být úprava popsaná v článku [[ https://medium.com/alas-test/auto-tmux-ssh-hostname-window-title-that-actually-works-feebab3524d3 | Auto tmux ssh hostname window title that actually works]]. Jenže nefunguje pro ssh s parametry, např.:
ssh -l test99 bis.vse.cz
Bylo by potřeba parsovat parametry příkazu ssh.