Как отправить команду на все панели в tmux?

192

Мне нравится звонить :clear-historyпо панелям с огромным прокруткой. Однако я хочу написать способ отправки этой команды на все панели в различных окнах.

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

send-keysи synchronize-panesиз man-страницы tmux приходят на ум, но я не знаю, как их объединить. Но, возможно, есть более простой способ сделать это.

Дополнительные наблюдения:

Думая об этом немного, tmux list-panes -aкажется, перечислить все панели в текущем сеансе. Довольно полезно начать с. Куда мне идти отсюда?

Этеш Чоудхури
источник
Для тех, кто придет к этому вопросу в надежде найти решение, которое применимо к каждой панели, в каждом окне, в каждом сеансе: scripter.co/command-to-every-pane-window-session-in-tmux
chb

Ответы:

356

Вы пробовали следовать в окне Tmux с несколькими панелями

Ctrl-B :

setw synchronize-panes on

clear history
Шайлеш Гарг
источник
53
Просто ради полноты, чтобы выключить, если бы вы сделалиCtrl-b :setw synchronize-panes off
Митч
19
и вы можете связать ярлыки для этого ~/.tmux.conf, добавив: bind -n C-x setw synchronize-panes on и bind -n M-x setw synchronize-panes off
guneysus
4
можно установить такой же ярлык для переключения?
Арнольд Роа
20
@ArnoldRoa да, опция будет переключаться, если вы уйдете on/off. Итакbind -n C-x setw synchronize-panes
сенсация
1
Если я добавлю bind -n C-x setw synchronize-panesкакой короткий путь, я должен нажать, чтобы вызвать? Это префикс + C & X. Я перепробовал множество вариантов
Билл Голдберг,
29

Немного опоздал на вечеринку, но я не хотел устанавливать и снимать синхронизирующие панели, просто чтобы послать одну команду, поэтому я создал функцию-оболочку для tmux и добавил пользовательскую функцию с именем send-keys-all-panes.

_tmux_send_keys_all_panes_ () {
  for _pane in $(tmux list-panes -F '#P'); do
    tmux send-keys -t ${_pane} "$@"
  done
}

Я также создаю оболочку для команды tmux, чтобы упростить вызов этой функции (для удобства). Оболочка и приведенный выше код все здесь .

Это позволяет мне запускать tmux send-keys-all-panes <command>или tmux skap <commandотправлять <command>на все панели.

Обратите внимание, что tmux связан с моей функцией-оберткой tmux_pp.

kshenoy
источник
это bash, но можно сделать то же самое из командной строки tmux, я имею в виду, сделавprefix + :
Rho Phi
Я не знаю как или если это возможно. Каков ваш сценарий использования, через который вам нужно отправить команду <prefix>:?
кшеной
Я бы порекомендовал вызвать фрагмент bash ( : run "yourscript.sh yourargs..."); если ваша команда выводит, ваша активная или заданная панель будет отображать результаты, пока вы не нажмете q, но в этом случае это не должно быть. Конечно, вы можете псевдоним / привязать это по своему вкусу. Кроме того, внутренние процессы могут интерпретировать ваши нажатия клавиш или их влияние по-разному, поэтому #{pane_current_cmd}может потребоваться белый или черный список . У меня есть Ctrl + K для отправки Ctrl + I и очистки истории; это прекрасно работает для оболочек, но забивает буфер Вима. Мне нужно будет уточнить, прежде чем я смогу транслировать свои Ctrl + K.
Джон П
Это может быть больше проблемой XY; Командная строка Tmux полезна, но, похоже, вы используете ее, потому что у вас нет другой открытой командной строки. Вы можете установить привязку клавиш - без префикса, если хотите - чтобы переключать и фокусировать дополнительную панель с выбранной вами оболочкой, вместо отправки <prefix>:перед каждой командой, потери вывода после выхода из команды и всех ловушек, которые приходят с выполнением через Tmux. Например, <prefix>:run "man cat"это не приводит к тому, что человек появляется в моем текущем пейджере для мужчины pidof manили даже ps auxf | grep man«меньше».
Джон П
Ссылка мертва
Матеуш Пиотровский
10

Обновление июнь 2019

Краткая иллюстрация о том, как настроить собственную привязку для синхронизации панелей .

Добавил следующее в мои tmux.conf(комментарии, безусловно, относятся к моей общей конфигурации):

# synchronize all panes in a window
# don't use control S, too easily confused
# with navigation key sequences in tmux (show sessions)
unbind C-S
bind C-Y set-window-option synchronize-panes

Теперь я могу включить возможность синхронизации команд на нескольких панелях <C-a><C-y>.

(Да, я переназначил клавишу привязки на Ctrl a).

arcseldon
источник
4

Ни один из приведенных выше ответов не работал для меня (tmux v2.3), но это сработало из командной строки bash:

for _pane in $(tmux list-panes -a -F '#{pane_id}'); do \
  tmux clear-history -t ${_pane}  ; done

Более обобщенный скрипт для команд tmux, отличных от 'clear-history', просто заменит этот элемент параметром, например. $ 1. Будьте осторожны, если вы намереваетесь написать скрипт для обработки серии команд tmux, так как «-t $ {_ pane}» необходимо будет применить к каждой.

Обратите внимание, что -aпараметр to tmux list-panesнеобходим для покрытия всех панелей во всех окнах во всех сеансах. Без этого будут затронуты только панели в вашем текущем окне tmux. Если у вас открыто более одного сеанса tmux и вы хотите применить команду только к панелям в текущем сеансе, замените -aна -s(Это все на странице руководства tmux).

У меня нет модов, чтобы комментировать непосредственно каждый из приведенных выше ответов, поэтому вот почему они не работают для меня:

Проблема, с которой я столкнулся при ответе @ shailesh-garg, заключалась в том, что синхронизация затрагивала только команды, выдаваемые в пределах панелей, а не команды tmux, Ctrl-B :выполняемые с использованием которых находятся за пределами панелей.

У меня были три проблемы с ответом @kshenoy:

  1. он отправляет нажатия клавиш внутри панели, а не операции tmux этой панели, например, если на панели запущена оболочка bash и кто-то использует скрипт для отправки «clear-history», это будут нажатия клавиш, которые появится в командной строке bash. Обходным решением будет отправить «tmux clear-history» или предварительно подать «tmux» на «$ @», но я не редактировал ответ из-за других проблем с ответом;
  2. Я не мог понять, как отправить символ новой строки без буквального разрыва строки;
  3. Даже когда я это сделал, отправка "tmux clear-history" не имела никакого эффекта.
user1404316
источник
3

моя версия tmux 1.9a, и это работает для меня, одного ключа достаточно для включения и выключения

bind-key X set-window-option synchronize-panes\; display-message "synchronize-panes is now #{?pane_synchronized,on,off}"
Лю Ю
источник
2
tmux send-keys -t <session id> <command> C-m  

Замените «идентификатор сессии» и «команду» соответственно.

RJ
источник
хотел бы кое-что сказать об этом инопланетном языке
Мухаммед Омер Аслам
Какой? Английский не сложно Но если тебе есть что сказать, то скажи это.
RJ
4
:Dчувак, вам нужно добавить описание к вашему ответу, так как в нем очень мало текста, и поэтому Stackoverflow обнаруживает его как спам или сообщение низкого качества, просто добавьте к нему некоторые детали, чтобы они не отображались под ним.
Мухаммед Омер Аслам
6
Забавно, принятый ответ также не имеет описания и только кода, но неважно.
RJ
0

Это моя служебная функция, которая выполняет это, только выполняя команду, когда на панели ничего не работает.

#!/bin/bash

_send_bash_command_to_session() {
    if [[ $# -eq 0 || "$1" = "--help" ]] ; then
        echo 'Usage: _send_bash_command_to_session $session_name what ever command you want: '
        return
    fi
    input_session="$1"
    input_command="${@:2}"
    for _pane in $(tmux list-panes -s -t ${input_session} -F '#{window_index}.#{pane_index}'); do
        # only apply the command in bash or zsh panes.
        _current_command=$(tmux display-message -p -t ${input_session}:${_pane} '#{pane_current_command}')
        if [ ${_current_command} = zsh ] || [ ${_current_command} = bash ] ; then
            tmux send-keys -t ${_pane} "${input_command}" Enter
        fi
    done
}

tmux_set_venv() {
    _current_session=$(tmux display-message -p '#{session_name}')
    _send_bash_command_to_session ${_current_session} workon $1
}

Пример, нацеленный на сеанс dev, включающий python virtualenv на всех панелях, которые находятся в bashили zsh, избегая выполнения команды в панелях с vim или любым другим исполняемым файлом:

_send_bash_command_to_session dev workon myvirtualenv

или проще запомнить: чтобы сделать это в текущем сеансе:

tmux_set_venv myvirtualenv

Найдите мой файл конфигурации с этой функцией.

phcerdan
источник