Comment puis-je ssh directement dans un répertoire particulier?

248

Je dois souvent me connecter à l'un des serveurs et aller dans l'un des répertoires de ces machines. Actuellement, je fais quelque chose de ce genre:

localhost ~] $ ssh somehost

Bienvenue chez somehost!

somehost ~] $ cd / certains / répertoire / quelque part / nommé / Foo
quelque chose Foo] $ 

J'ai des scripts qui peuvent déterminer dans quel hôte et dans quel répertoire je dois accéder, mais je ne peux pas trouver un moyen de le faire:

localhost ~] $ go_to_dir Foo

Bienvenue chez somehost!

quelque chose Foo] $

Existe-t-il un moyen simple, intelligent ou de le faire?

Glacial
la source

Réponses:

413

Vous pouvez effectuer les opérations suivantes:

ssh -t xxx.xxx.xxx.xxx "cd /directory_wanted ; bash"

De cette façon, vous obtiendrez un shell directement sur le directory_wanted.


Explication

-tForcer l'allocation pseudo-terminale. Cela peut être utilisé pour exécuter des programmes arbitraires sur écran sur une machine distante, ce qui peut être très utile, par exemple lors de la mise en œuvre de services de menu.

Plusieurs -toptions forcent l'allocation de tty, même si ssh n'a pas de tty local.

  • Si vous n'utilisez pas, -taucune invite n'apparaîtra.
  • Si vous n'ajoutez pas, ; bashla connexion sera fermée et reviendra au contrôle de votre machine locale
rogeriopvl
la source
21
dans mon cas -t la partie manquante
Mathieu
2
Lorsque vous utilisez cette approche, le .bash_profile n'est pas lu, quelqu'un sait pourquoi?
Filipe
8
Je devais faire ça: ssh -t xxx.xxx.xxx.xxx "cd /directory_wanted && exec \$SHELL"
guptron
40
Vous aurez généralement besoin d'un shell de connexion:ssh -t example.com "cd /foo/bar; exec \$SHELL -l"
christianbundy
10
Je voulais juste lier automatiquement le changement de répertoire lors de la connexion ssh - Erreur du serveur ; et à partir de là collez cette commande (qui est une version de celle de @christianbundy):ssh server -t "cd /my/remote/directory; bash --login"
sdaau
53

Vous pourriez ajouter

cd /some/directory/somewhere/named/Foo

à votre .bashrcfichier (ou .profilecomme vous l'appelez) sur l'autre hôte. De cette façon, peu importe ce que vous faites ou d'où vous venez ssh, chaque fois que vous vous connectez à ce serveur, il sera cddans le répertoire approprié pour vous, et tout ce que vous avez à faire est de l'utiliser sshcomme d'habitude.

Bien sûr, la solution de rogeriopvl fonctionne aussi, mais c'est un peu plus verbeux, et vous devez vous rappeler de le faire à chaque fois (à moins que vous ne fassiez un alias), donc cela semble un peu moins "amusant".

Chris Lutz
la source
1
+1, cela semble plus approprié si vous avez besoin d'un répertoire constant au lieu de prolonger la commande ssh en vous rappelant à chaque fois dans quel répertoire vous allez vous déplacer lorsque vous vous connectez à la machine X
Tebe
Ne convient pas lors d'un changement flexible
Lewis Chan
21

J'ai créé un outil pour SSH et CD dans un serveur consécutivement - bien nommé sshcd . Pour l'exemple que vous avez donné, vous utiliseriez simplement:

sshcd somehost:/some/directory/somewhere/named/Foo

Faites-moi savoir si vous avez des questions ou des problèmes!

christianbundy
la source
1
Ce serait cool si vous pouviez définir une nouvelle configuration dans ~ / .ssh / config et la lire à partir de là;)
Alexar
21

Mon approche préférée consiste à utiliser le fichier de configuration SSH (décrit ci-dessous), mais il existe quelques solutions possibles en fonction de vos utilisations.

Arguments de ligne de commande

Je pense que la meilleure réponse à cette approche est la réponse de christianbundy à la réponse acceptée:

ssh -t example.com "cd /foo/bar; exec \$SHELL -l"

L'utilisation de guillemets doubles vous permettra d'utiliser des variables de votre machine locale, à moins qu'elles ne soient échappées (comme $SHELLici). Alternativement, vous pouvez utiliser des guillemets simples, et toutes les variables que vous utilisez seront celles de la machine cible:

ssh -t example.com 'cd /foo/bar; exec $SHELL -l'

Fonction Bash

Vous pouvez simplifier la commande en l'enveloppant dans une fonction bash. Disons que vous voulez juste taper ceci:

sshcd example.com /foo/bar

Vous pouvez faire ce travail en l'ajoutant à votre ~/.bashrc:

sshcd () { ssh -t "$1" "cd \"$2\"; exec \$SHELL -l"; }

Si vous utilisez une variable qui existe sur la machine distante pour le répertoire, assurez-vous de l'échapper ou de la mettre entre guillemets simples. Par exemple, cela va cd dans le répertoire qui est stocké dans la JBOSS_HOMEvariable sur la machine distante:

sshcd example.com \$JBOSS_HOME

Fichier de configuration SSH

Si vous souhaitez voir ce comportement tout le temps pour des hôtes spécifiques (ou n'importe quel) avec la commande ssh normale sans avoir à utiliser des arguments de ligne de commande supplémentaires, vous pouvez définir les options RequestTTYet RemoteCommanddans votre fichier de configuration ssh.

Par exemple, je voudrais taper uniquement cette commande:

ssh qaapps18

mais je veux qu'il se comporte toujours comme cette commande:

ssh -t qaapps18 'cd $JBOSS_HOME; exec $SHELL'

J'ai donc ajouté ceci à mon ~/.ssh/configdossier:

Host *apps*
    RequestTTY yes
    RemoteCommand cd $JBOSS_HOME; exec $SHELL

Maintenant, cette règle s'applique à tout hôte avec "apps" dans son nom d'hôte.

Pour plus d'informations, voir http://man7.org/linux/man-pages/man5/ssh_config.5.html

A dessiné
la source
13

Sur la base des ajouts à la réponse de @ rogeriopvl, je suggère ce qui suit:

ssh -t xxx.xxx.xxx.xxx "cd /directory_wanted && bash"

En enchaînant les commandes par &&, la commande suivante ne s'exécutera que lorsque la précédente a réussi (par opposition à l'utilisation ;, qui exécute les commandes séquentiellement). Ceci est particulièrement utile lorsque vous avez besoin cdd'un répertoire exécutant la commande.

Imaginez faire ce qui suit:

/home/me$ cd /usr/share/teminal; rm -R *

Le répertoire teminaln'existe pas, ce qui vous oblige à rester dans le répertoire de base et à supprimer tous les fichiers qu'il contient avec la commande suivante.

Si vous utilisez &&:

/home/me$ cd /usr/share/teminal && rm -R *

La commande échouera après ne pas avoir trouvé le répertoire.

Bas Peeters
la source
1
Utilisé des guillemets simples et non des guillemets doubles avec une commande sans && une fois et ça m'a mordu dans le cul, mauvais ... j'ai appris ma leçon.
Gavin Pickin,
4

Dans mon cas très spécifique, je voulais juste exécuter une commande dans un hôte distant, à l'intérieur d'un répertoire spécifique d'une machine esclave Jenkins:

ssh myuser@mydomain
cd /home/myuser/somedir 
./commandThatMustBeRunInside_somedir
exit

Mais ma machine n'a pas pu exécuter le ssh (elle n'a pas pu allouer un pseudo-tty je suppose) et m'a continué à donner l'erreur suivante:

Pseudo-terminal will not be allocated because stdin is not a terminal

Je pourrais contourner ce problème en passant "cd à dir + ma commande" comme paramètre de la commande ssh (pour ne pas avoir à allouer un pseudo-terminal) et en passant l'option -T pour dire explicitement à la commande ssh que je n'ai pas fait pas besoin d'allocation pseudo-terminale.

ssh -T myuser@mydomain "cd /home/myuser/somedir; ./commandThatMustBeRunInside_somedir"
Mauricio Reis
la source
3

J'utilise la variable d'environnement CDPATH

Tourbillon
la source
Utile uniquement si j'étais intéressé par un répertoire par machine. J'ai besoin d'un moyen de transmettre des informations à la machine distante. La solution de Roger fait exactement cela.
Frosty
2

aller plus loin avec l' -tidée. Je garde un ensemble de scripts appelant celui-ci pour aller à des endroits spécifiques de mes hôtes fréquemment visités. Je les garde tous dedans ~/binet je garde ce répertoire sur mon chemin.

#!/bin/bash

# does ssh session switching to particular directory
# $1, hostname from config file 
# $2, directory to move to after login
# can save this as say 'con' then
# make another script calling this one, e.g.
# con myhost repos/i2c

ssh -t $1 "cd $2; exec \$SHELL --login"
DKebler
la source
1

Une autre façon d'accéder directement après la connexion est de créer un "Alias". Lorsque vous vous connectez à votre système, tapez simplement cet alias et vous serez dans ce répertoire.

Exemple: Alias ​​= mon dossier '/ var / www / Dossier'

Après vous être connecté à votre type de système, cet alias (cela fonctionne à partir de n'importe quelle partie du système),
cette commande si elle n'est pas dans bashrc, fonctionnera pour la session en cours. Vous pouvez donc également ajouter cet alias à bashrc pour l'utiliser à l'avenir

$ myfolder => vous emmène dans ce dossier

insomiaque
la source
-3

SSH lui-même fournit un moyen de communication, il ne sait rien des répertoires. Puisque vous pouvez spécifier la commande à distance à exécuter (c'est - par défaut - votre shell), je commencerais par là.

Jan Jungnickel
la source
4
Ceci est une réponse partielle, pas une solution.
AL
-7

modifiez simplement votre maison avec la commande: usermod -d /newhome username

Borja Moll
la source
1
Non conseillé. La modification de votre répertoire personnel entraînera probablement la rupture d'autres éléments.
bronson