22déc. 2009
Emacs : accéder à des fichiers distants avec TRAMP
14:53 - Par Olivier - emacs - 5 commentaires
TRAMP c'est quoi ?
TRAMP (Transparent Remote (file) Access, Multiple Protocol) est une extension pour Emacs permettant d'accéder à des machines distantes comme si leurs ressources étaient disponibles en local. De façon générale, cela permet d'ouvrir des fichiers distants, de naviguer dans l'arborescence des fichiers avec dired, d'exécuter des commandes shells, ... Les plus habitués à Emacs auront de suite compris l'intérêt : toutes ses possibilités sont donc accessibles sur les machines distantes ! Pour cela, il suffit de pouvoir s'y connecter via rsh, rlogin, telnet, ssh ou toute autre méthode de connexion similaire (par exemple sudo). Le transfert de fichiers sera effectué au choix parmi les commandes rcp, rsync, scp ou pscp (sous Windows).
TRAMP est livré avec Emacs depuis la version 22. Pour les versions précédentes, il suffit de le télécharger ici : ftp://ftp.gnu.org/gnu/tramp/.
Configuration générale
Syntaxe TRAMP
La syntaxe par défaut pour accéder à un fichier distant est /machine:localname. Personnellement je trouve que cette syntaxe manque de clarté et puis je suis habitué à la norme URL/URI. J'ai donc activé la syntaxe URL de TRAMP ce qui donne ceci : /protocol://machine:port/localname. Voici les commandes à rajouter dans votre .emacs afin d'activer cette fonction :
; use /protocol://host[:port]/path/to/file (setq tramp-syntax 'url) (require 'tramp)
Backups
À moins d'avoir une bonne connexion à Internet, il est souvent préférable d'enregistrer les fichiers temporaires et les backups des fichiers distants localement :
; turn off backup-directory-alist for tramp (add-to-list 'backup-directory-alist (cons tramp-file-name-regexp nil)) ; set a dedicated auto-save directory (setq tramp-auto-save-directory "~/.emacs.d/tramp-autosave")
Protocoles par défaut
On peut configurer le protocole à utiliser (si non spécifié) en général ou par machine. Par exemple, pour qu'emacs utilise SSH par défaut pour toutes les machines sauf pour root@localhost, cas dans lequel il doit utiliser sudo :
; default method to SSH (setq tramp-default-method "ssh") ; use sudo for root@localhost (add-to-list 'tramp-default-method-alist '("\\`localhost\\'" "\\`root\\'" "sudo"))
Rebonds
Une fonctionnalité très pratique de TRAMP est sa gestion des rebonds. Par exemple si vous ne pouvez accéder à la machine web1 qu'en passant par example.com, il suffit de rajouter ceci à la configuration .emacs :
; when web[0-9] is requested, connect to example.com first (add-to-list 'tramp-default-proxies-alist '("\\`web[0-9]\\'" nil "/ssh://example.com") )
Ainsi, lorsqu'emacs devra se connecter à web1, il ouvrira d'abord une connection ssh à example.com puis sur cette machine lancera une nouvelle connection ssh à web1. Cette fonctionnalité permet donc d'accéder à n'importe quelle machine à laquelle vous avez accès, quelque que soit le nombre de rebonds nécessaires.
Exemple de configuration
Un bon exemple vaut mieux qu'un long discours, voici donc ma configuration TRAMP :
; use /[protocol:]//host[:port]/path/to/file (setq tramp-syntax 'url) (require 'tramp) ; enable partial completion mode (partial-completion-mode 1) ; turn off backup-directory-alist for tramp (add-to-list 'backup-directory-alist (cons tramp-file-name-regexp nil)) ; set a dedicated auto-save directory (setq tramp-auto-save-directory "~/.emacs.d/tramp-autosave") ; default method to SSH (setq tramp-default-method "ssh") ; use sudo for root@localhost (add-to-list 'tramp-default-method-alist '("\\`localhost\\'" "\\`root\\'" "sudo")) ; set the prompt pattern (setq tramp-shell-prompt-pattern "[^>$#]?[>$#] *") (setq shell-prompt-pattern "[^>$#]?[>$#] *") ; make sure terminal is defined to dumb (setq tramp-terminal-type "dumb") ; when web[0-9] is requested, connect to example.com first (add-to-list 'tramp-default-proxies-alist '("\\`web[0-9]\\'" nil "/ssh://example.com") )
Utilisation avancée
Éditer des fichiers distants est bien pratique mais il y a encore mieux : naviguer dans les dossiers via dired, exécuter des shells distants via shell', des terminaux distants via term'', bref tout ce que votre emacs vous permet. Pour cela, rien de plus facile : il suffit que le répertoire courant soit sur la machine distante pour que toutes les commandes shells soient exécutées sur cette machine.
Par exemple, si vous ouvrez le dossier /mon/dossier sur la machine example.com via /ssh://example.com/mon/dossier, toutes les commandes exécutées depuis ce buffer auront lieu sur example.com dans le dossier /mon/dossier. Voici les commandes les plus pratiques :
* M-x shell => ouvre un shell simple * M-x term => ouvre un terminal complet * M-! => exécute n'importe quelle commande shell
Il est donc très facile de créer des macros à lancer sur des machines distantes pour réaliser des commandes répétitives. Grâce à la puissance de TRAMP et la souplesse d'Emacs et de ses macros, on peut donc réaliser tout un jeu de commandes pour réaliser toutes les tâches répétitives quelque soit la machine concernée. La seule limite étant d'y avoir accès !
5 commentaires
Bonjour,
article bien intéressant! Aussi les dernières commandes, M-!, M-x term ne sont pas exécutées dans la machine ssh. Y a t'il une config pour cela?
Je me demande également si il est possible de se connecter en sudo dans le ssh afin de pouvoir éditer un fichier dont je n'ai pas les droits avec l'user générique?
Merci!
Il faut être sûr que la touche Meta est correctement affectée. Tout dépend du terminal qui execute emacs
En ce qui concerne sudo, il faut utiliser la capacité de rebond de tramp via la variable
Merci.
La touche Meta fonctionne mais le terminal qui s'ouvre dans emacs s'ouvre en local et non depuis la machine distante.
Pour sudo, la doc utilise l'exemple:
(add-to-list 'tramp-default-proxies-alist
'("\\.your\\.domain\\'" "\\`root\\'" "/ssh:%h:"))
qui ne fonctionne pas non plus! (avec emacs23)
Si tu as une idée, je suis preneuse!
Pour sudo, je n'ai jamais essayé de le faire en distant mais je dirais un truc comme ça :
Sinon pour ton emacs local c'est étrange qu'il n'accepte pas tes commandes M-!, sûrement un problème de configuration clavier, à chercher par là doncer de l'ouSi tu veux essayer de l'ouvrir dans ton terminal, tu peux essayer :
J'ai résolu le problème des commandes en supprimant l'option (setq tramp-terminal-type "dumb")
Ce n'est pas la commande en elle-même qui ne fonctionnait pas mais sont action n'était pas celle attendue!