Uruchom program z dowolnego miejsca bez zmiany katalogu

9

Chcę utworzyć alias, który uruchamia program x, bez zmiany bieżącego katalogu, w którym jestem. Mam teraz:

alias x = "cd /home/path_to_x && ./x"

To działa, ale zmienia mój katalog. Chciałbym coś takiego:

alias x="./home/path_to_x/x

Ale wtedy nie otrzymuję takiego pliku ani katalogu. Czy ktoś zna obejście tego problemu?

Rybak
źródło
9
ustaw alias jak alias x='/home/path_to_x/x'. Nie używaj .wcześniej /home. .(kropka) oznacza bieżący katalog.
souravc
2
Czy xnaprawdę trzeba biec podczas pobytu /home/path_to_x? A może po prostu nie wiesz, jak uruchomić program znajdujący się w określonym katalogu?
Adaephon
Jeszcze jedno podobne pytanie askubuntu.com/questions/427818/…
c0rp

Odpowiedzi:

13

NIE CD, po prostu uruchom go przy użyciu absolutnej ścieżki

Ta wersja:

cd /home/path_to_x && ./x

zmienia katalog na ścieżkę bezwzględną (widzisz, jak /home/...zaczyna się w katalogu głównym), a następnie uruchamia plik wykonywalny w ścieżce względnej./x (to znaczy względem nowego katalogu roboczego).

Ta wersja:

./home/path_to_x/x

próbuje uruchomić plik wykonywalny na ścieżce względnej./home/path_to_x/x , co oznacza, niezależnie od tego, jaki jest teraz bieżący katalog roboczy . To wyjaśnia, dlaczego pojawia się błąd - ta ścieżka względna naprawdę nie istnieje.

Polecenie, które chcesz, to:

/home/path_to_x/x

używając ponownie ścieżki bezwzględnej (zaczynając od katalogu głównego /).

Aha, możesz też po prostu dodać /home/path_to_xdo swojego PATHzamiast tworzyć alias. Zobacz: Jak uruchamiać skrypty bez wpisywania pełnej ścieżki?

Nieprzydatny
źródło
To jest poprawna odpowiedź na postawione pytanie.
Wstrzymano do odwołania.
1
Byłoby to niepoprawne tylko wtedy, gdyby program musiał być uruchomiony w określonym katalogu, z którego pochodzipwd
Kaz Wolfe
@Whaaaaaat ma rację. /home/path_to_x/xnie jest funkcjonalnie równoważny z (cd /home/path_to_x && ./x); jeśli to działa, czy nie, zależy od aplikacji.
Rmano
Chociaż ogólnie masz rację, dla tego konkretnego pytania OP próbował wyraźnie uciec z absolutnej ścieżki (tylko z pomyłką jednego znaku). Jestem jednak pewien, że mogą wyjaśnić, czy katalog roboczy jest w tym przypadku ważny.
Bezużyteczne
8

Jeśli nie chcesz, cdaby trzymać po podstawieniu aliasu, użyj podpowłoce z (y ):

alias my_x="(cd /home/path_to_x && ./x)&" 

możesz to sprawdzić za pomocą

alias test_y="(cd /tmp && sleep 10 ) & "

Zauważ, że rozwiązanie

alias my_y="/home/path_to_x/x" 

nie jest dokładnie równoważne. W rzeczywistości, jeśli zostanie wywołany przez my_x, xprogram zostanie uruchomiony z bieżącym katalogiem /home/path_to_x/, natomiast jeśli zostanie wywołany przez my_y, xzostanie uruchomiony z bieżącym katalogiem, w którym my_ywydano polecenie . Może to być ważne lub nie, w zależności od tego, co xsię dzieje.

O rozwiązaniu OP działa w bash:

romano@RRyS:~$ pwd
/home/romano
romano@RRyS:~$ alias x="cd /bin && ./echo A >/dev/null  &"
romano@RRyS:~$ x
[1] 16611
romano@RRyS:~$ pwd
/home/romano

ale nie w zsh:

[romano:~] % pwd
/home/romano
[romano:~] % alias x="cd /bin && ./echo A >/dev/null &"
[romano:~] % x
[1] 16744
[1]  + 16744 done       ./echo A > /dev/null                                    
1& [romano:/bin] % pwd
/bin
[romano:/bin] % 

Wygląda na to, że bash i zsh wykonują listy na różne sposoby ... więc lepiej dodać jawny nawias ... dziękuję @EliahKagan za wskazanie go mi.

Rmano
źródło
1
Nadanie końcowemu &wyższemu pierwszeństwa, niż się &&wydaje, może być wyjątkowe zsh. Starałem sleep 5 && echo done &się zsh, bash, ksh, mksh, dash, i jeszcze jedna powłoka non-Bourne-style ( tcsh). zshOceniane tylko sleep 5na pierwszym planie; wszyscy pozostali wrócili natychmiast (a donepotem oczywiście wydrukowani pięć sekund później). Z drugiej strony, nawet jeśli jest to całkowicie osobliwość zsh, myślę, że dodanie wyraźnego ( )(lub { ;}) jest rozsądne, ponieważ przekazuje zamiar innym ludziom (lub sobie, czytając później scenariusz lub historię).
Eliah Kagan
4

Jeśli plik, który chcesz uruchomić, jest już wykonywalny, dlaczego nie dodasz go do zmiennej PATH?

Jeśli plik wykonywalny jest /home/user/aplication/appXpo prostu wprowadź

PATH=$PATH:/home/user/application

do twojego ~/.bashrclub~/.profile

Po ponownym uruchomieniu konsoli możesz uruchomić ją po prostu za pomocą appX

Myślę, że to najczystsze rozwiązanie.

0xAffe
źródło
3

Umieszczenie &na końcu wydaje się załatwić sprawę:

alias x = "cd /home/path_to_x && ./x &"
Rybak
źródło
2
Jesteś pewny? Po wykonaniu xjesteś w /home/path_to_x. Na &koniec wystarczy wysłać proces w tle.
Rmano
2
@Rmano To faktycznie działa. cds zadania w tle nie wpływają na rozmówcę (co ma sens - byłoby naprawdę dziwnie, gdyby tak zrobiły). Wynika to z faktu, że wykonywanie asynchroniczne korzysta z podpowłoki . Chociaż byłoby lepiej, gdyby wyjaśnił, dlaczego to działa i co &działa - i jak czasem działa w tle jest czasami niepożądane - jest to (już) poprawna odpowiedź. ( Wyraźnie tworzenie podpowłoki ze ( )składnią, jak sugerujesz , jest jednak prawdopodobnie lepszym rozwiązaniem przez większość czasu.)
Eliah Kagan
@EliahKagan masz rację. Sprawdziłem rozwiązanie zshi działa skutecznie, basha nie w zsh... musi być jakaś różnica w sposobie rozwijania aliasów.
Rmano
Zadane
Rmano
@Rmano czy włączyłeś ustawienia związane z pushdw zsh(mam setopt autopushd pushdsilent pushdtohome, i pamięta mój cwd.)
muru
0

Uzyskaj kopię zapasową bieżącego pwd, a po uruchomieniu polecenia cofnij ostatnie pwd.

alias x='dwp=$(pwd) && cd /home/path_to_x && ./x && cd $dwp'
αғsнιη
źródło
Źle zrozumiałeś efekt aliasu tego Rmano. Wiersz poleceń nie jest zablokowany. Po prostu dane wyjściowe aliasu ( test) przesunęły kursor do następnego wiersza. Nadal możesz robić, co chcesz (w tym nacisnąć klawisz Enter, aby otworzyć nowy monit).
muru
tak, tak, poprawne. @mure: |
αғsнιη
Zauważ, że ponieważ używasz podwójnych cudzysłowów, zmienna będzie zawierać bieżący katalog w momencie zdefiniowania aliasu . Użyj pojedynczych cudzysłowów, aby odroczyć ocenę, dopóki alias nie zostanie rozwinięty. Jednak pushdi popdrób to, co robi twoja odpowiedź. alias x='pushd /home/path_to_x && ./x && popd'
Wstrzymano do odwołania.