Как заставить скрипт определять, запущен ли эмулятор терминала в сеансе рабочего стола или нет?

10

У меня есть сценарии, которые я запускаю, которые записывают текстовый файл, а затем открывают его в редакторе. Если я открою окно эмулятора терминала в сеансе своего рабочего стола и запустлю скрипт, я бы хотел, чтобы редактор был графическим, например gedit. Но если я войду через ConnectBot на моем телефоне или чем-то подобном (без сеанса на рабочем столе), я бы хотел, чтобы редактор был nano.

В настоящее время я должен поддерживать 2 разных скрипта, идентичных, за исключением последнего шага (или запустить графический скрипт, отключить ошибку, затем вручную открыть файл nano). Наличие двух в основном идентичных сценариев неэффективно с точки зрения обслуживания.

Может ли скрипт определить, в какой из этих ситуаций я нахожусь, и открыть правильный редактор?

(Я нашел способ для скрипта определить, запущен ли он в окне эмулятора терминала или двойным щелчком, но пока не нашел способа определить, работает ли окно на рабочем столе ... Не думаю, что знать правильную терминологию для Google)

Органический мрамор
источник
6
Если ваш сценарий предназначен для использования другими людьми, вы должны использовать программу, указанную $EDITORпо умолчанию, а не использовать ее nano, nanoесли она не установлена.
Бакуриу
Спасибо, отличный совет, и приятно слышать, что такое хорошая практика. Только я, хотя.
Органический мрамор

Ответы:

13

Вы можете использовать переменную среды $DISPLAYкак триггер в ifусловии. Обычно, когда эта переменная имеет значение, вы можете запускать графические приложения.

Вот пример :

if [[ -z $DISPLAY ]]
then
    nano
else
    gedit
fi

Оператор -zвернет true, когда envvar $DISPLAYпуст и ваш скрипт запустится nano, во всех остальных случаях он запустится gedit.


Согласно этому комментарию @ vurp0 :

На большинстве современных рабочих столов Wayland (например, рабочих столов по умолчанию в Fedora и Ubuntu) $DISPLAYвсе еще устанавливается из-за обратной совместимости (через XWayland), но для более надежного сценария было бы хорошо проверить оба $DISPLAYи $WAYLAND_DISPLAYбыть уверенным.

Я бы предложил изменить тестовое выражение следующим образом:

[[ -z ${DISPLAY}${WAYLAND_DISPLAY} ]]

Таким образом, значения двух переменных будут объединены в общую строку, которая будет обработана оператором -z.


Ссылки:

pa4080
источник
1
Или для явной логики:[[ -z ${DISPLAY} && -z ${WAYLAND_DISPLAY} ]]
Приостановлено до дальнейшего уведомления.
7

Обычно виртуальные терминалы используют /dev/ptsпсевдо-терминалы . Итак, основываясь на выводе ttyкоманды, мы можем создать простую caseинструкцию для открытия определенного редактора:

case "$(tty)" in ; "/dev/pts"*) nano ;; "/dev/tty"*) gedit ;; ;esac

Или лучше отформатировать:

case "$(tty)" in
    "/dev/pts"*) gedit ;; 
    "/dev/tty"*) nano ;;
    *) echo "Not suitable tty" > /dev/stderr ;;
esac

По сравнению с использованием переменных окружения это немного более надежно, и, учитывая, что оно использует caseоператор с ttyкомандой, немного более переносимым. Что, вероятно, было бы лучше, это объединить оба, с дополнительным тестированием, таким как"/dev/tty"*) [ -n "$DISPLAY" ] && gedit ;;

Сергей Колодяжный
источник
Разве это не неправильно? На моей консоли Ctrl + Alt + F1, ttyдает /dev/tty1, тогда как gnome-terminal(первая вкладка) дает /dev/pts/0.
Пэдди Ландау
@PaddyLandau Да, geditдолжно быть на всякий /dev/pts*случай. Я переключил их во время тестирования ошибок в tty и в итоге скопировал их здесь, не переключаясь обратно. Спасибо, отредактировал уже.
Сергей Колодяжный
3

Это то, что я использовал:

# $TERM variable may be missing when called via desktop shortcut
CurrentTERM=$(env | grep TERM)
if [[ $CurrentTERM == "" ]] ; then
    notify-send --urgency=critical "$0 cannot be run from GUI without TERM environment variable."
    exit 1
fi

Причиной для этого кода был этот вопрос: ярлык на рабочем столе для Bash-скрипта вылетает и горит

Вы можете изменить это так:

# $TERM variable may be missing when called via desktop shortcut
CurrentTERM=$(env | grep TERM)
if [[ $CurrentTERM == "" ]] ; then
    nano ...
else
    gedit ...
fi
WinEunuuchs2Unix
источник