Jak mogę uruchomić polecenie w folderze bez zmiany w nim mojego bieżącego katalogu?

18

może ci się to wydawać dziwne, ale chcę uruchomić polecenie w określonym folderze bez zmiany bieżącego folderu w powłoce. Przykład - zwykle tak robię:

~$ cd .folder
~/.folder$ command --key
~/.folder$ cd ..
~$ another_command --key

Chociaż chcę coś takiego:

~$ .folder command --key
~$ another_command --key

Czy to możliwe?

Timur Fajzrakhmanov
źródło
Nie można zrobić ~/.folder/command --key? Czy commandwymaga to twojego aktualnego katalogu ~/.folder?
glenn jackman

Odpowiedzi:

46

Jeśli chcesz uniknąć drugiego cd, możesz użyć

(cd .folder && command --key)
another_command --key
Florian Diesch
źródło
Bardzo szybka odpowiedź! Nawet nie mogę tego zaakceptować, ponieważ system mi nie pozwala))
Timur Fayzrakhmanov
1
magiczny nawias! Jak to działa? +1
precyzyjnie
Polecenia w nawiasach są uruchamiane w nowym procesie powłoki, więc zmiana katalogu, ustawienie zmiennych środowiskowych itp. W nawiasie nie wpływa na powłokę nadrzędną, która uruchamia inne polecenia.
Florian Diesch
9
Chciałbym zmienić ;TO &&środek na dobre. Jeśli cd nie powiedzie się (np. Ponieważ wpisałeś nazwę katalogu), prawdopodobnie nie chcesz uruchomić polecenia.
geirha
+1 za komentarz @ geirha. To bardzo ważny punkt. OP, czy rozważysz edycję?
jaybee,
8

Bez cd... ani razu. Znalazłem dwa sposoby:

# Save where you are and cd to other dir
pushd .folder
command --key
# Get back where you were at the beginning.
popd
another_command --key

i drugi:

find . -maxdepth 1 -type d -name ".folder" -execdir command --key \;
another_command --key
Radu Rădeanu
źródło
1

Prosta funkcja bash do uruchomienia polecenia w określonym katalogu:

# Run a command in specific directory
run_within_dir() {
    target_dir="$1"
    previous_dir=$(pwd)
    shift
    cd $target_dir && "$@"
    cd $previous_dir
}

Stosowanie:

$ cd ~
$ run_within_dir /tmp ls -l  # change into `/tmp` dir before running `ls -al`
$ pwd  # still at home dir
cud
źródło
0

Musiałem to zrobić w bezproblemowy sposób i zdziwiłem się, że nie ma narzędzia (podobnego do env(1)lub sudo(1)uruchamiającego polecenie w zmodyfikowanym katalogu roboczym. Napisałem więc prosty program w C, który to robi:

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>

char ENV_PATH[8192] = "PWD=";

int main(int argc, char** argv) {
    if(argc < 3) {
        fprintf(stderr, "Usage: in <dir> <cmd> [<args>...]\n");
        return 1;
    }

    if(chdir(argv[1])) {
        fprintf(stderr, "Error setting working directory to \"%s\"\n", argv[1]);
        return 2;
    }

    if(!getcwd(ENV_PATH + 4, 8192-4)) {
        fprintf(stderr, "Error getting the full path to the working directory \"%s\"\n", argv[1]);
        return 3;
    }

    if(putenv(ENV_PATH)) {
        fprintf(stderr, "Error setting the environment variable \"%s\"\n", ENV_PATH);
        return 4;
    }

    execvp(argv[2], argv+2);
}

Użycie jest takie:

$ in /path/to/directory command --key
Lucretiel
źródło