Como você mencionou, resolveu o problema para sua situação específica, abaixo de uma solução para uso geral. Graças ao xdotool
's --sync
opção, ele funciona muito confiável nos testes que fiz; Eu poderia "enviar" comandos para janelas de terminal específicas e funcionou perfeitamente sem uma exceção.
Como funciona na prática
A solução existe a partir de um script, que pode ser executado com duas opções
-set
e -run
:
Para configurar (abrir) um número arbitrário de janelas de terminal, neste exemplo 3:
target_term -set 3
Três novos terminais se abrirão, seu ID de janela será lembrado em um arquivo oculto:
Por motivos de clareza, minimizei a janela do terminal da qual executei o comando :)
Agora que criei três janelas, posso enviar comandos para qualquer uma delas com o comando run (por exemplo):
target_term -run 2 echo "Monkey eats banana since it ran out of peanuts"
Como mostrado abaixo, o comando foi executado no segundo terminal:
Posteriormente, posso enviar um comando para o primeiro terminal:
target_term -run 1 sudo apt-get update
fazendo sudo apt-get update
correr no terminal 1:
e assim por diante...
Como configurar
O script precisa de ambos wmctrl
e xdotool
:
sudo apt-get install wmctrl xdotool
Copie o script abaixo em um arquivo vazio, proteja-o como target_term
(sem extensão!) Em ~/bin
(crie o diretório, ~/bin
se necessário.
Torne o script executável (não se esqueça) e efetue logout / login ou execute:
source ~/.profile
Agora configure suas janelas de terminal, com o número de janelas necessárias como argumento:
target_term -set <number_of_windows>
Agora você pode "enviar" comandos para qualquer um dos seus terminais com o comando:
target_term -run <terminal_number> <command_to_run>
O script
#!/usr/bin/env python3
import subprocess
import os
import sys
import time
#--- set your terminal below
application = "gnome-terminal"
#---
option = sys.argv[1]
data = os.environ["HOME"]+"/.term_list"
def current_windows():
w_list = subprocess.check_output(["wmctrl", "-lp"]).decode("utf-8")
w_lines = [l for l in w_list.splitlines()]
try:
pid = subprocess.check_output(["pgrep", application]).decode("utf-8").strip()
return [l for l in w_lines if str(pid) in l]
except subprocess.CalledProcessError:
return []
def arr_windows(n):
w_count1 = current_windows()
for requested in range(n):
subprocess.Popen([application])
called = []
while len(called) < n:
time.sleep(1)
w_count2 = current_windows()
add = [w for w in w_count2 if not w in w_count1]
[called.append(w.split()[0]) for w in add if not w in called]
w_count1 = w_count2
return called
def run_intterm(w, command):
subprocess.call(["xdotool", "windowfocus", "--sync", w])
subprocess.call(["xdotool", "type", command+"\n"])
if option == "-set":
open(data, "w").write("")
n = int(sys.argv[2])
new = arr_windows(n)
for w in new:
open(data, "a").write(w+"\n")
elif option == "-run":
t_term = open(data).read().splitlines()[int(sys.argv[2])-1]
command = (" ").join(sys.argv[3:])
run_intterm(t_term, command)
Notas
O script está definido para gnome-terminal
, mas pode ser usado para qualquer terminal (ou outro programa também), alterando a application
seção head do script:
#--- set your terminal below
application = "gnome-terminal"
#---
- Os comandos acima podem (é claro) ser executados a partir de um script, caso você deseje usá-lo para algum tipo de simulação.
- O script aguarda até que a janela de destino tenha foco e o comando seja digitado, para que o comando sempre apareça na janela do terminal direita.
Não é necessário dizer que o script funciona apenas com a configuração do terminal (windows) que foi chamada pelo comando:
target_term -set
As janelas do terminal serão "rotuladas" pelo script, como você mencionou na sua pergunta.
- Caso você inicie uma nova
target_term
sessão, o arquivo oculto, criado pelo script, será simplesmente substituído, portanto, não será necessário removê-lo.