Esecuzione di un processo in background bash su Windows 10 senza un terminale aperto


13

Di solito uso il sottosistema Linux quando sto programmando qualcosa su Windows 10, quindi tutti i miei percorsi sono relativi ~. Ho uno script Python che funziona per sempre in background fino a quando non uccido il processo. Come lo farei su Windows 10 bash senza un terminale aperto?

Cose che ho provato:

  • bash -c "python3 script.py da Run.
  • nohup python3 -u script.py quindi chiudendo il terminale.
  • setsid python3 script.py quindi chiudendo il terminale.

Nessuno di questi ha funzionato. C'è un modo per fare questo? In alternativa, c'è un modo per modificare i percorsi in modo che funzionino se eseguo lo script da W10 AND bash senza doverli cambiare ogni volta?

Risposte:


7

Una recente aggiunta a WSL consente di avviare i comandi wsl direttamente dal menu "Esegui" o Start. È possibile aggiungere una e commerciale al comando (comportamento normale della shell), che si traduce in un bashterminale momentaneo che scompare immediatamente ma il comando continua.

Esempi, in Start »Esegui :

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

Se vai in Task Manager di Windows, mostrerà un Sleepo un Python2comando in esecuzione per 20 secondi, quindi autopulente.

Una cosa che ho scoperto è che le variabili di ambiente non sono disponibili. Ad esempio, DISPLAYse impostato nel metodo normale di Windows, non viene passato a WSL. Per questo, deve esserci un modo per passare queste variabili. Anche se il comando non supporta l'impostazione della variabile necessaria tramite un argomento della riga di comando, è possibile farlo usando bashse stesso:

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

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

NB: Attualmente sto eseguendo win10_64, versione 1709 (build del sistema operativo 16299.64).


13

Aggiornare

Microsoft ha risolto questo problema. I processi in background / daemon ora possono continuare a funzionare anche dopo la chiusura bash.exe(o altro processo di avvio WSL). È richiesta una versione recente di Win10 (primavera 2018 per le versioni pubbliche, build 17046 o successiva).

Il seguito è conservato per i posteri.


Purtroppo / assurdamente, non c'è modo di farlo. Microsoft, nella loro infinita saggezza, ha deciso che WSL (sottosistema Windows per Linux) verrà eseguito solo quando è bash.exeaperto un processo. Chiudi l'ultimo (o forse anche chiudi l'ultima finestra ; non sono sicuro che tollererà l'esecuzione senza testa) e WSL si spegne, uccidendo tutti i suoi processi.

La giustificazione per questo era "conservare le risorse", il che è assurdo su diversi livelli ma soprattutto perché, dannazione, il mio computer ha quelle risorse e sono lì per essere utilizzate! Se voglio eseguire un processo, dovrebbe essere eseguito; se non voglio che funzioni, posso ucciderlo. Per qualcosa di esplicitamente inteso come uno strumento di sviluppo, a volte sembra che WSL sia utilizzabile solo come giocattolo e ai suoi utenti non ci si possa fidare di sapere cosa stanno facendo.

Ad ogni modo, se vuoi che sia risolto, vota Considerare l'abilitazione di lavori cron, daemon e attività in background nella pagina UserVoice . Attualmente è la seconda richiesta più votata ed è "in arretrato".


"in particolare perché, dannazione, il mio computer ha quelle risorse e sono lì per essere utilizzate" molto ben messo! sconvolge davvero la mente ...
attacco aereo

Ho costruito 17134 e non posso avere un lavoro in background senza una finestra bash.
John Pick,

@JohnPick Non si avviano automaticamente dopo il riavvio, ma dovrebbero rimanere in esecuzione quando la finestra è chiusa (purché non siano collegati ad essa, ovviamente).
CBHacking

@CBHacking Per essere più specifici, se avvio un server Node.js in background, allora è sia un lavoro ( jobs) che un processo ( ps aux). Posso usarlo fgper portarlo in primo piano. Ma dopo aver chiuso l'ultima finestra bash e aver aperto una nuova finestra bash, il lavoro è finito, il processo è ancora in esecuzione e non riesco a spostare il processo in primo piano. Scusate se la mia terminologia è disattivata.
John Pick,

@JohnPick Ah, questo è un problema completamente diverso - questa domanda riguarda i processi, non sulla gestione dei lavori shell - e avrebbe dovuto essere posta altrove, ma la risposta è abbastanza semplice la darò qui: avvia il processo sotto tmuxo screenper supportare ricollegarsi a un altro terminale. Le macchine Linux (e altre * nix) eseguite nativamente hanno lo stesso limite.
CBHacking del

2

Sì, è "impossibile" al momento.

Ma è possibile vederlo "apparire" come un processo in background con qualche trucco. Anch'io volevo questa funzionalità piuttosto male, quindi dopo un paio d'ore ho trovato una soluzione di merda ma funzionante.

Il punto principale è creare una shell invisibile con cui si avvia WSL Bash con VBScript. È quindi possibile eseguire tale script all'avvio. La corretta pianificazione delle attività non ha funzionato per qualche strana ragione.

Lato Linux per abilitare i demoni puoi avere il tuo sistema di avvio rudimentale che abusa ad esempio di .bashrc.

Il processo è dettagliato qui in questo documento che ho scritto https://emil.fi/bashwin . Non ho implementato il monitoraggio delle attività, ma dovrebbe essere abbastanza facile da estendere.


2

Hai provato questa soluzione?

Utilizza un helper WSH per avviare qualsiasi applicazione nascosta.

Quindi puoi semplicemente creare una nuova attività in Tak Scheduler per avviare il comando quando accedi. Qualcosa di simile awscript <path to runHidden.vbs> bash.exe -c "python script.py"


2

Mi ci è voluto per sempre ma ho trovato un modo stupidamente complicato di farlo (da un file batch):

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

Ecco una ripartizione di ciò che fa e perché:

  • `start`: per far sparire la finestra del file batch
  • `bash -c`: ti permette di eseguire un comando bash
  • `DISPLAY =: 0`: imposta il tuo X-server
  • `[comando]`: il tuo comando / comandi (`[comando && [comando]`)
  • `&`: per eseguire il comando successivo dopo l' avvio e non al termine
  • `sleep 0,5`: per assicurarsi che il processo sia iniziato
  • `` &&: per rendere la prossima corsa di comando dopo che è fatto e non quando si inizia
  • `kill -n 9 $$`: per uccidere la shell bash quindi è solo l'applicazione grafica

Nota: lo DISPLAY=:0imposta sul server x all'indirizzo :0. Per cambiarlo in (es.) :1, Fare DISPLAY=:1ecc.

Nota: startè richiesto solo se proviene da uno script batch. Se viene dal terminale, non è necessario questo

Nota: sleepdeve essere impostato in modo diverso per ogni applicazione. Potrebbe anche essere necessario ometterlo.


0

Non so come funzionerebbe bene Windows Service Manager (SrvMan) da http://tools.sysprogs.org/srvman/ , ma ha funzionato per me per altri programmi. In effetti, ho provato a eseguire "bash.exe" come servizio per vedere se avrebbe funzionato, e immagino che dovrei armeggiare un po 'di più per far funzionare LAMP in background.


1
In che modo questo risolve la domanda su come eseguire uno script Python in background?
Scott,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.