Выполнить команду в фоновом режиме с доступом к терминалу переднего плана

У меня есть функция, указанная ниже в моем ~ / .profile , по тем же причинам,

k(){
    { echo PERMS LINKS OWNER GROUP SIZE modMONTH modDATE modTIME NAME
    ls -l; } |
    column -t |
    grep -v "total"
}
6
30.03.2019, 15:15
3 ответа

Я добавил код, чтобы :

  • это работает для ваших трех примеров и
  • Взаимодействие предшествует ожиданию.
  • interact() {
        pid=$1
        ! ps -p $pid && return
        ls -ld /proc/$pid/fd/*
        sleep 5; kill -1 $pid   # TEST SIGNAL TO PARENT
    }
    
    run() {
        exec {in}<&0 {out}>&1 {err}>&2
        { coproc "$@" 0<&$in 1>&$out 2>&$err; } 2>/dev/null
        exec {in}<&- {out}>&- {err}>&-
        { interact $! <&- >/tmp/whatever.log 2>&1& } 2>/dev/null
        fg %1 >/dev/null 2>&1
        wait 2>/dev/null
    }
    

    fg %1будет работать для всех команд (изменить %1по мере необходимости для параллельных заданий )и при нормальных обстоятельствах произойдет одно из двух :

  • Если команда завершится немедленно, interact()немедленно вернется, так как делать нечего, и fgничего не сделает.
  • Если команда не завершается немедленно, interact()может взаимодействовать (, например. отправить HUP сопроцессу через 5 секунд ), и fgпереведет сопроцесс на передний план, используя тот же стандартный ввод/вывод/ошибку, с которым он был первоначально запущен (, вы можете проверить это с помощьюls -l /proc/<pid>/df).
  • Перенаправления на /dev/null в последних трех командах носят косметический характер. Они позволяют run <command>выглядеть точно так же, как если бы вы запустили commandотдельно.

    4
    27.01.2020, 20:27

    It fails, I presume, because Vim detects that it is a background process and doesn't have terminal access, so instead of popping up an edit window it suspends itself. I want to fix it so Vim behaves normally.

    На самом деле это не имеет ничего общего с передним или задним планом.

    Vim вызывает функцию isatty(), которая сообщает, что не подключена к терминалу. Единственный способ исправить это — подключить vim к терминалу. Есть два способа сделать это:

    • Не используйте какие-либо перенаправления для стандартного вывода. Если у вас есть перенаправление, даже если вы в конце концов перенаправитесь на терминал, isatty()будет указывать на канал, а не на терминал, и vim будет работать в фоновом режиме.
    • Использовать псевдотерминал -tty. Да, я знаю, ты сказал, что не хочешь этого; но если требуются перенаправления, то избежать псевдо -ttys невозможно .
    0
    27.01.2020, 20:27

    Я не совсем понимаю вопрос, но вот кое-что из того, что вы ищете.

    Передний план и задний план являются понятиями оболочки.

    • Активное задание имеет доступ к tty. Его можно приостановить, нажав ctrl -z.
    • Приостановленное задание можно переместить на передний план(fg)или на задний план(bg).
    • Задание можно запустить в фоновом режиме с помощью «command»&.
    • Фоновое задание можно вывести на передний план с помощьюfg %jobid
    • Задание — это процесс, плюс другие метаданные, -помогающие оболочке. К заданию можно получить доступ только как к заданию из оболочки, которая его запустила. С другой точки зрения, это просто процесс.
    -1
    27.01.2020, 20:27

    Теги

    Похожие вопросы