Xterm.js: Kontrol aliran menggunakan XON / XOFF

Dibuat pada 10 Nov 2020  ·  3Komentar  ·  Sumber: xtermjs/xterm.js

Kontributor yang terhormat,

Saya menggunakan xtermjs untuk membangun aplikasi terminal yang berjalan di browser web, dan server target menggunakan Linux. Saya perhatikan bahwa xtermjs v4.9.0 tidak responsif terhadap ^ C saat menjalankan perintah yes .
Kemudian saya mundur ke v4.0.2 dan mengaktifkan opsi useFlowControl , berhasil.

useFlowControl menggunakan XON / XOFF telah ditambahkan dari v2.3.0 (PR # 447) tetapi dihapus dari v4.1.0 (PR # 2422).
Saya tidak dapat menemukan diskusi apa pun tentang alasan untuk menghapusnya. Apakah solusi XON / XOFF memiliki kelemahan?

Jika tidak, dapatkah kita memiliki rencana untuk mengembalikan fitur ini ke lib atau saya harus menerapkannya pada aplikasi saya sendiri?

Kontrol aliran yang dijelaskan dalam dokumen (https://xtermjs.org/docs/guides/flowcontrol/) tidak banyak membantu karena saya menggunakan websocket untuk terhubung ke backend.

typquestion

Komentar yang paling membantu

Kami menghapus XON / XOFF karena tidak berfungsi dengan baik di beberapa skenario. Dari belakang kepala saya, saya ingat kami memiliki masalah dengan shell ZSH, yang menggunakan urutan XON / XOFF untuk sesuatu yang berbeda. Saya yakin Terminal Windows juga mengalami masalah dengan urutan ini.

Bagaimanapun - cara saya menyelesaikan ini (juga menggunakan WebSockets - dalam kasus saya socket.io tetapi tidak masalah) adalah dengan secara manual membuat mekanisme kontrol aliran di atas soket itu sendiri.

Jadi - setiap kali data tiba di soket yang harus ditulis ke xterm.js, kami meningkatkan penghitung, dan setelah data berhasil ditulis ke xterm.js (yang berarti telah dirender oleh xterm.js), kami mengurangi penghitung itu .

Jika penghitung melebihi ambang tertentu, kami mengirim pesan pause melalui Websocket, yang di sisi server akan menghentikan sementara aliran pty ( terminalStream.pause() ). Setelah kami pergi ke bawah ambang itu, kami mengirim pesan resume melalui Websocket, yang di sisi server akan melanjutkan aliran pty ( terminalStream.resume() ).

Perhatikan bahwa metode terminalStream.pause() dan terminalStream.resume() adalah metode Stream node.js bawaan untuk menangani tekanan balik. node-pty serta ssh2 mendukung penanganan tekanan balik melalui metode ini.

// client
const MAX_PENDING_WRITES = 5;
let pendingWrites = 0;
let paused = false;
socket.on('data', (data) => {
  pendingWrites++;
  xterm.write(data, () => {
    pendingWrites--;
    if (pendingWrites > MAX_PENDING_WRITES && !paused) {
      paused = true;
      socket.emit('pause');
      return;
    }
    if (pendingWrites <= MAX_PENDING_WRITES && paused) {
      paused = false;
      socket.emit('resume');
      return;
    }
  });
});

// server
terminalStream.on('data', (data) => socket.emit('data', data);
socket.on('data', (data) => terminalStream.write(data));
socket.on('pause', () => terminalStream.pause();
socket.on('resume', () => terminalStream.resume();

Mekanisme ini bekerja cukup andal sejauh ini. Perintah yes tidak akan membanjiri koneksi lagi. Masih ada penundaan sekitar 0,5 detik antara CTRL+C dan penghentian perintah yang sebenarnya dalam skenario throughput tinggi, tetapi IMO tidak apa-apa.

Saya harap ini membantu.

Semua 3 komentar

Kami menghapus XON / XOFF karena tidak berfungsi dengan baik di beberapa skenario. Dari belakang kepala saya, saya ingat kami memiliki masalah dengan shell ZSH, yang menggunakan urutan XON / XOFF untuk sesuatu yang berbeda. Saya yakin Terminal Windows juga mengalami masalah dengan urutan ini.

Bagaimanapun - cara saya menyelesaikan ini (juga menggunakan WebSockets - dalam kasus saya socket.io tetapi tidak masalah) adalah dengan secara manual membuat mekanisme kontrol aliran di atas soket itu sendiri.

Jadi - setiap kali data tiba di soket yang harus ditulis ke xterm.js, kami meningkatkan penghitung, dan setelah data berhasil ditulis ke xterm.js (yang berarti telah dirender oleh xterm.js), kami mengurangi penghitung itu .

Jika penghitung melebihi ambang tertentu, kami mengirim pesan pause melalui Websocket, yang di sisi server akan menghentikan sementara aliran pty ( terminalStream.pause() ). Setelah kami pergi ke bawah ambang itu, kami mengirim pesan resume melalui Websocket, yang di sisi server akan melanjutkan aliran pty ( terminalStream.resume() ).

Perhatikan bahwa metode terminalStream.pause() dan terminalStream.resume() adalah metode Stream node.js bawaan untuk menangani tekanan balik. node-pty serta ssh2 mendukung penanganan tekanan balik melalui metode ini.

// client
const MAX_PENDING_WRITES = 5;
let pendingWrites = 0;
let paused = false;
socket.on('data', (data) => {
  pendingWrites++;
  xterm.write(data, () => {
    pendingWrites--;
    if (pendingWrites > MAX_PENDING_WRITES && !paused) {
      paused = true;
      socket.emit('pause');
      return;
    }
    if (pendingWrites <= MAX_PENDING_WRITES && paused) {
      paused = false;
      socket.emit('resume');
      return;
    }
  });
});

// server
terminalStream.on('data', (data) => socket.emit('data', data);
socket.on('data', (data) => terminalStream.write(data));
socket.on('pause', () => terminalStream.pause();
socket.on('resume', () => terminalStream.resume();

Mekanisme ini bekerja cukup andal sejauh ini. Perintah yes tidak akan membanjiri koneksi lagi. Masih ada penundaan sekitar 0,5 detik antara CTRL+C dan penghentian perintah yang sebenarnya dalam skenario throughput tinggi, tetapi IMO tidak apa-apa.

Saya harap ini membantu.

@tandatle Lihat juga dokumentasinya tentang flowcontrol .

Edit: Maaf, komentar dokumen Anda terlewatkan. Peduli untuk menjelaskan apa yang tidak jelas di sana? Ya, bagian websocket hanyalah sebuah rintisan (tidak ada cuplikan siap pakai), karena saya tidak tahu apa yang harus membuat banyak cuplikan untuk libs soket yang berbeda dan kebutuhan khusus (ini sulit dilakukan dengan benar dengan soket web untuk alasan keamanan saja) . Tetap merasa bebas untuk menambahkan potongan konkret, yang mencakup aspek-aspek tersebut.

@mofux @jerch Terima kasih atas bantuan Anda.
Saya tidak menggunakan node.js di backend, tetapi proses yang ditulis dalam C ++, jadi saya mungkin harus melakukan beberapa investigasi lagi untuk memilih antara menggunakan XON / XOFF dan menerapkan penanganan backpresure dalam proses backend saya.
Terima kasih banyak.

Apakah halaman ini membantu?
0 / 5 - 0 peringkat

Masalah terkait

ghost picture ghost  ·  4Komentar

Tyriar picture Tyriar  ·  4Komentar

Tyriar picture Tyriar  ·  4Komentar

circuitry2 picture circuitry2  ·  4Komentar

Tyriar picture Tyriar  ·  4Komentar