Các chuỗi thoát trong đầu ra của tập lệnh được gọi từ ứng dụng ncurses


14

Tôi hiện đang chạy mcabber với tư cách là ứng dụng khách Jabber của mình (sử dụng ncurses) trong phiên tmux trên máy chủ của tôi. Tại địa phương tôi chạy iTerm2 như một trình giả lập thiết bị đầu cuối, hỗ trợ kích hoạt các thông báo gầm gừ thông qua các chuỗi thoát ký tự.

Lưu ý: Tất cả echotrong câu hỏi này hoạt động như printf %b, hoặcecho -e trong bash và GNU echo.

ví dụ echo "\e]9;foobar\007" làm cho iTerm2 gửi tin nhắn Growl với nội dung "foobar".

Tuy nhiên, khi trong một phiên tmux, các chuỗi thoát được ăn hết. Do đó, sử dụng chuỗi thoát ký tự độc quyền \Ptmuxcó thể được sử dụng như thế này:

echo "\ePtmux;\e\e]9;foobar\007\e\\"

Điều này kích hoạt một thông điệp gầm gừ từ trong một phiên tmux.

Tuy nhiên, khi tôi sử dụng điều này trong tập lệnh sự kiện mcabber của mình sẽ bị kích hoạt khi nhận được tin nhắn mới, không có thông báo nào được kích hoạt, như thể tiếng vang được gửi đến thiết bị đầu cuối sai.

Tôi cho rằng điều này có liên quan đến mcabber đó kích hoạt tập lệnh là một ứng dụng ncurses để đầu ra từ tập lệnh bash bình thường của tôi bị mất và iTerm 2 không bao giờ nhìn thấy nó.

Tôi cũng đã thử gọi smcup nhưng không thành công trước khi lặp lại với một số ý tưởng mà tôi phát hiện ra

tput smcup
echo "\ePtmux;\e\e]9;$FROM: $MSG\007\e\\"
tput rmcup

Tôi cho rằng điều này không hoạt động vì vấn đề không chuyển trở lại "cửa sổ thiết bị đầu cuối thực sự", mà chỉ đạo đầu ra nhiều hơn ở cửa sổ ncurses.

Có ý kiến ​​gì về cái này không?

Câu trả lời:


1

Lý do tại sao một tập lệnh sự kiện không gửi được thông báo "growler" là vì mcabberđóng các luồng đầu vào, đầu ra và lỗi tiêu chuẩn khi nó chạy một lệnh sự kiện. Bạn có thể thấy điều này trong hooks.c:

  if ((pid=fork()) == -1) {
    scr_LogPrint(LPRINT_LOGNORM, "Fork error, cannot launch external command.");
    g_free(datafname);
    return;   
  }    
  if (pid == 0) { // child
    // Close standard file descriptors
    close(STDIN_FILENO);
    close(STDOUT_FILENO);
    close(STDERR_FILENO);
    if (execl(extcmd, extcmd, arg_type, arg_info, bjid, arg_data,
              (char *)NULL) == -1) {
      // scr_LogPrint(LPRINT_LOGNORM, "Cannot execute external command.");
      exit(1);
    }
  }
  g_free(datafname);

Điều đó làm cho tập lệnh sự kiện chạy mà không can thiệp vào các luồng được sử dụng mcabber.

Không có chế độ ncurses đặc biệt nào chặn tin nhắn (rốt cuộc, tmuxđã chạy như một ứng dụng terminfo). Bạn có thể có thể giải quyết vấn đề bằng cách chuyển hướng echo(tốt nhất printf) của bạn sang /dev/tty, ví dụ:

#!/bin/sh
printf '\033Ptmux;\033\033]9;foobar\007\033\\' >/dev/tty

0

Các chương trình tmux và màn hình không trực tiếp đi qua các chuỗi thoát. Họ trình bày một loại thiết bị đầu cuối cho ứng dụng (loại thiết bị đầu cuối màn hình) và bản thân nó là một ứng dụng cần thiết cho thiết bị đầu cuối khác. Trong thực tế, nó là một cái gì đó giống như một dịch giả thiết bị đầu cuối. Vì vậy, có, nó tiêu thụ (hoặc loại bỏ) các chuỗi cho loại thiết bị đầu cuối "màn hình" và đưa ra một bộ đệm mà bạn nhìn thấy. Sau đó, phải mất các sự kiện thay đổi bộ đệm và sử dụng bất kỳ loại thiết bị đầu cuối nào bạn đang sử dụng để hiển thị bộ đệm hiện tại. Vì vậy, ứng dụng gốc và thiết bị đầu cuối xem được tách rời.


0

Nếu bạn định đặt một cái gì đó như ...

export "PTTY=$(tty)"

... trong của bạn /etc/profile tất cả các -lvỏ ogin mới mà bạn sẽ gọi (đó là điều thường xảy ra khi bạn mở một cửa sổ đầu cuối mới) , biến môi trường sẽ được cung cấp cho tất cả các quy trình con của nó - bao gồm tmuxvà tất cả các con của nó .

Điều này sẽ cho phép bạn làm ...

printf '\033]9;foobar\007' >"$PTTY"

... và do đó bỏ qua ngay bất kỳ pty lớp nào có thể tồn tại giữa lớp vỏ hiện tại của bạn và trình giả lập thiết bị đầu cuối bạn đang sử dụng.


0

Nếu vấn đề là đầu ra từ tập lệnh bash của bạn bị mất, thì bạn có thể thắng trận chiến với chuyển hướng:

tiếng vang "\ ePtmux; \ e \ e] 9; foobar \ 007 \ e \"> / dev / tty

Tuy nhiên, tôi nghi ngờ vấn đề thực sự là bạn nên sử dụng echo -eđể bash xử lý các chuỗi thoát trong chuỗi của bạn.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.