181 votes

Exécuter une commande depuis un autre répertoire en bash

Dites que je fais ça :

cd subdir
git init
cd ../

Existe-t-il un moyen de faire cela avec une seule commande, ou peut-être deux, plutôt que de devoir entrer et sortir d'un répertoire pour y exécuter une commande ?

(Je ne cherche pas une solution spécifique à git ; c'est juste un exemple).

290voto

givp Points 798

C'est souvent le meilleur moyen :

( cd dir ; git init )

oder

( cd dir && git init )

C'est assez court et facile à taper. Il démarre un sous-Shell, vous ne pouvez donc pas modifier votre environnement à partir de celui-ci, mais cela ne semble pas être un problème ici.

25voto

Luis Brenes Points 1

Je cherchais un moyen d'exécuter la commande git à partir d'un chemin, et d'apporter des modifications au dépôt dans un chemin différent. J'ai donc abouti à cette question ici.

Mais pour mes besoins spécifiques, ni la réponse acceptée ni aucune autre n'a été utile.

J'avais besoin d'exécuter des commandes git en utilisant sudo -u USER /usr/bin/git (un autre utilisateur qui l'exécute). Et comme vous le savez peut-être, sudo ne me permet pas de lancer l'application cd commande, donc je ne peux pas être dans le répertoire du référentiel.

Alors, je suis allé à la page de manuel de git . Et parmi les options, j'ai vu le --git-dir=<path> :

--git-dir=

Définir le chemin d'accès au référentiel. Ceci peut également être contrôlé en définissant la variable d'environnement GIT_DIR. Il peut s'agir d'un chemin absolu ou d'un chemin relatif au répertoire de travail actuel.

Ainsi, si cela peut aider quelqu'un, vous pouvez toujours utiliser git à partir d'un chemin et apporter des modifications à un dépôt "loin de vous". Il suffit d'utiliser :

git --git-dir=/path/to/repository GIT_COMMAND

ou, pour l'exécuter en tant qu'autre utilisateur, faites quelque chose comme :

echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir=/path/to/repository GIT_COMMAND

Également de La page de manuel de git-init :

Si la variable d'environnement $GIT_DIR est définie, elle spécifie un chemin à utiliser à la place de ./.git pour la base du référentiel.

Ainsi, si vous souhaitez initialiser le dépôt dans le dossier .git habituel, vous devrez le spécifier avec l'attribut --git-dir option. Par exemple :

echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir=/path/to/repository/.git init

Après avoir initialisé le référentiel sur /path/to/repo/.git toutes les autres commandes devraient avoir l'option --work-tree=<path> comme décrit dans la page de manuel de git :

--work-tree=

Définissez le chemin vers l'arbre de travail. Il peut s'agir d'un chemin absolu ou d'un chemin relatif au répertoire de travail actuel. Ceci peut également être contrôlé en définissant la variable d'environnement GIT_WORK_TREE et la variable de configuration core.worktree (voir core.worktree dans git-config(1) pour une discussion plus détaillée).

Donc, la bonne commande pour lancer git en tant qu'autre utilisateur, et initialiser un nouveau dépôt est :

echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir=/path/to/repository/.git init
echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir='/path/to/repository/.git' --work-tree='/path/to/repository' add /path/to/repository/*
echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir='/path/to/repository/.git' --work-tree='/path/to/repository' commit -m 'MESSAGE'
echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir='/path/to/repository/.git' --work-tree='/path/to/repository' remote add origin user@domain.com:path
echo USER_PASSWORD | sudo -u USER_LOGIN -S /usr/bin/git --git-dir='/path/to/repository/.git' --work-tree='/path/to/repository' push -u origin master

15voto

Lark Points 1640

Ce n'est pas exactement ce que vous demandez (vous avez de vraies réponses ci-dessus avec le sous-shell) mais regardez à pushd y popd

9voto

Wuffers Points 18372

Vous avez plusieurs options. Vous pouvez soit regrouper les commandes avec && o ; . Comme ça :

cd subdir && git init && cd ..

oder

cd subdir; git init; cd ..

La différence entre les deux est que dans le premier exemple, si l'une des commandes échoue, les autres ne seront pas exécutées. Dans le second exemple, toutes les commandes seront exécutées quoi qu'il arrive.

Une autre option serait de définir une fonction et de l'utiliser, par exemple :

function cdinit() {
    cd $1
    git init
    cd ..
}

Ensuite, vous pouvez exécuter la commande :

cdinit subdir

Et cela va automatiquement git init dans ce répertoire et en sortir.

Vous pouvez également réaliser une solution plus complexe en utilisant une fonction si vous avez un tas de répertoires et que vous voulez git init avec une seule commande.

function cdinit() {
    for arg in $@
    do
        cd $arg
        git init
        cd ..
    done
}

Vous pouvez ensuite l'exécuter avec :

cdinit subdir1 subdir2 subdir3

Et il le fera git init en subdir1 , subdir2 y subdir3 .

5voto

Mifeet Points 170

En cas de git (au moins dans la version 2.7.0), vous pouvez tirer parti de la fonction -C qui fait que git se comporte comme s'il avait été lancé dans le répertoire donné. Votre solution peut donc ressembler à ceci

> git -C subdir init
Initialized empty Git repository in /some/path/subdir/.git/

Citation de la documentation :

Run as if git was started in <path> instead of the current working directory. When multiple -C options are given, each subsequent non-absolute -C
<path> is interpreted relative to the preceding -C <path>.

This option affects options that expect path name like --git-dir and --work-tree in that their interpretations of the path names would be made
relative to the working directory caused by the -C option.

SistemesEz.com

SystemesEZ est une communauté de sysadmins où vous pouvez résoudre vos problèmes et vos doutes. Vous pouvez consulter les questions des autres sysadmins, poser vos propres questions ou résoudre celles des autres.

Powered by:

X