Uruchamianie procesu bash w tle w systemie Windows 10 bez otwartego terminalu

13

Zwykle używam podsystemu linux, gdy programuję coś na Windows 10, więc wszystkie moje ścieżki są względne ~. Mam skrypt Pythona, który działa wiecznie w tle, dopóki nie zabiję procesu. Jak mam to zrobić na Windows 10 bez otwartego terminalu?

Rzeczy, których próbowałem:

  • bash -c "python3 script.py z Run.
  • nohup python3 -u script.py następnie zamykając terminal.
  • setsid python3 script.py następnie zamykając terminal.

Żaden z nich nie działał. Czy jest na to sposób? Alternatywnie, czy istnieje sposób na zmianę ścieżek, aby działały, jeśli uruchomię skrypt z W10 ORAZ bash bez konieczności przełączania ich za każdym razem?

Popiół
źródło

Odpowiedzi:

7

Niedawny dodatek do WSL pozwala na uruchamianie poleceń WSL bezpośrednio z menu „Uruchom” lub Start. Do polecenia możesz dołączyć znak „ampersand” (normalne zachowanie powłoki), co powoduje bashnatychmiastowe zniknięcie terminala, ale polecenie jest kontynuowane.

Przykłady w ramach Start »Uruchom :

wsl sleep 20 &
wsl python -c 'import time; time.sleep(20);' &

Jeśli przejdziesz do Menedżera zadań Windows, wyświetli się komenda Sleeplub Python2uruchomiona przez 20 sekund, a następnie automatycznie się wyczyści.

Odkryłem, że zmienne środowiskowe nie są dostępne. Na przykład, DISPLAYjeśli jest ustawiony w normalnej metodzie systemu Windows, nie jest przekazywany do WSL. W tym celu musi istnieć sposób na przekazanie tych zmiennych. Nawet jeśli polecenie nie obsługuje ustawiania potrzebnej zmiennej za pomocą argumentu wiersza poleceń, można to zrobić za pomocą bashsamego:

# direct, command-dependent
wsl emacs --display=:0 &

# indirect, more flexible
wsl bash -c "DISPLAY=:0 emacs" &

Uwaga: obecnie używam Win10_64, wersja 1709 (kompilacja systemu operacyjnego 16299.64).

r2evans
źródło
13

Aktualizacja

Microsoft zajął się tym. Procesy działające w tle / demona mogą teraz działać nawet po bash.exezamknięciu (lub innym procesie uruchamiania programu WSL). Wymagana jest najnowsza wersja Win10 (wiosna 2018 dla wersji publicznych, kompilacja 17046 lub wyższa).

Poniżej zachowano dla potomności.


Niestety / absurdalnie nie ma na to sposobu. W swojej nieskończonej mądrości Microsoft zdecydował, że WSL (Windows Subsystem for Linux) będzie działał tylko wtedy, gdy bash.exeproces będzie otwarty. Zamknij ostatnie (a może nawet zamknij ostatnie okno ; nie jestem pewien, czy toleruje uruchamianie bez głowy) i WSL zamyka się, zabijając wszystkie jego procesy.

Uzasadnieniem tego było „oszczędzanie zasobów”, co jest absurdalne na kilku różnych poziomach, ale przede wszystkim dlatego, że cholera, mój komputer ma te zasoby i można z nich korzystać! Jeśli chcę uruchomić proces, powinien on zostać uruchomiony; jeśli nie chcę, żeby działał, mogę go zabić. W przypadku czegoś wyraźnie przeznaczonego jako narzędzie programistyczne czasami wydaje się, że WSL nadaje się tylko do zabawy i nie można ufać użytkownikom, że wiedzą, co robią.

W każdym razie, jeśli chcesz to naprawić, głosuj na Rozważ włączenie zadań cron, demonów i zadań w tle na stronie UserVoice . Jest to obecnie drugie najczęściej głosowane żądanie i „zaległe”.

CBHacking
źródło
„przede wszystkim dlatego, że cholera, mój komputer ma te zasoby i można z nich korzystać”. to naprawdę denerwuje umysł ...
nalot
Mam kompilację 17134 i nie mogę mieć pracy w tle bez okna bash.
John Pick,
@JohnPick Nie uruchomią się automatycznie po ponownym uruchomieniu, ale powinny pozostać uruchomione, gdy okno jest zamknięte (o ile oczywiście nie są do niego przywiązane).
CBHacking
@CBHacking Aby być bardziej szczegółowym, jeśli uruchomię serwer Node.js w tle, będzie to zarówno zadanie ( jobs), jak i proces ( ps aux). Mogę użyć, fgaby przenieść go na pierwszy plan. Ale po zamknięciu ostatniego okna bash i otwarciu nowego okna bash zadanie zniknęło, proces nadal działa i nie mogę przenieść go na pierwszy plan. Przepraszam, jeśli moja terminologia jest wyłączona.
John Pick
@JohnPick Ach, to zupełnie inna kwestia - to pytanie dotyczy procesów, a nie zarządzania zadaniami powłoki - i powinno być zadawane gdzie indziej, ale odpowiedź jest dość prosta, dam to tutaj: uruchom proces pod tmuxlub w screencelu wsparcia ponowne podłączenie do innego terminala. Maszyny z systemem Linux (i inne * nix) działające natywnie mają te same ograniczenia.
CBHacking
2

Tak, w tej chwili jest to „niemożliwe”.

Ale możliwe jest, że „pojawi się” jak proces w tle z pewnymi sztuczkami. Sam bardzo chciałem tej funkcji, więc po kilku godzinach wpadłem na gówniane, ale działające rozwiązanie.

Chodzi przede wszystkim o stworzenie niewidzialnej powłoki, do której uruchamiasz WSL Bash za pomocą VBScript. Możesz wtedy uruchomić ten skrypt podczas uruchamiania. Właściwe planowanie zadań nie działało z jakiegoś dziwnego powodu.

Po stronie Linux, aby umożliwić demony, możesz mieć swój podstawowy system uruchamiania, który na przykład nadużywa .bashrc.

Proces jest szczegółowo opisany tutaj w tym dokumencie, który napisałem https://emil.fi/bashwin . Nie wdrożyłem monitorowania zadań, ale jego rozszerzenie powinno być dość łatwe.

Emil
źródło
2

Wypróbowałeś to rozwiązanie?

Wykorzystuje pomocnika WSH do uruchamiania dowolnej ukrytej aplikacji.

Następnie możesz po prostu utworzyć nowe zadanie w Tak Scheduler, aby uruchomić polecenie po zalogowaniu. Coś jakwscript <path to runHidden.vbs> bash.exe -c "python script.py"

Magnus
źródło
2

Zajęło mi to wieczność, ale znalazłem głupio skomplikowany sposób (z pliku wsadowego):

start bash -c "DISPLAY=:0 [command] & (sleep 0.5 && kill -n 9 $$)"

Oto podział tego, co robi i dlaczego:

  • `start`: aby okno pliku wsadowego zniknęło
  • `bash -c`: pozwala uruchomić polecenie bash
  • `DISPLAY =: 0`: ustawia twój X-serwer
  • `[polecenie]`: twoje polecenie / polecenia (`[polecenie && [polecenie]`)
  • `&`: Uczynić następny bieg polecenia po to zaczyna , a nie kiedy to zrobić
  • `sleep 0.5`: aby upewnić się, że proces się rozpoczął
  • `` &&: uczynić następny bieg polecenia po to zrobić , a nie kiedy zacznie
  • `kill -n 9 $$`: zabija powłokę bash, więc jest to tylko aplikacja graficzna

Uwaga: DISPLAY=:0ustawia go na serwer X w :0. Aby zmienić na (np.) :1, Wykonaj DISPLAY=:1itp.

Uwaga: startjest wymagana tylko, jeśli pochodzi ze skryptu wsadowego. Jeśli pochodzi z terminala, nie potrzebujesz tego

Uwaga: sleepnależy ustawić inaczej dla każdej aplikacji. Być może będziesz musiał to pominąć.

Electroboss
źródło
0

Nie wiem, jak dobrze Windows Service Manager (SrvMan) z http://tools.sysprogs.org/srvman/ działałby dla ciebie, ale dla mnie działał dla innych programów. W rzeczywistości próbowałem uruchomić „bash.exe” jako usługę, aby sprawdzić, czy to zadziała, i sądzę, że muszę jeszcze trochę majstrować, aby LAMP rzeczywiście działał w tle.

Charles McDonald
źródło
1
Jak rozwiązuje to pytanie, jak uruchomić skrypt Pythona w tle?
Scott,