«Хвіст -f | iconv -fsjis »нічого не виводить


14

Я хочу до tail -fфайлу, але його вміст знаходиться в sjisкодуванні, тому мені потрібно перетворити його в нативне (utf-8) кодування мого терміналу.

Коли я це роблю

хвіст -fx | iconv -fsjis

виходу не буде Як

хвіст х | iconv -fsjis

спрацьовує, спочатку я подумав, що це проблема буферизації, але спроба unbufferі stdbufяк описано в розділі Вимкнути буферизацію в трубі не допомогло.

Насправді, навіть після того, як до x додано більше 10k даних, виводу не буде, тому я думаю, що це не проблема буферизації (буфер становить 4 к, якщо я не помиляюся), але iconv почне виводити лише тоді, коли він отримує EOF.

Тож як я можу дотримуватися свого кодованого файлу sjis?

Відповіді:


11

(візьміть це із щіпкою солі) Наскільки я пам’ятаю, проблема полягає в тому, як це libiconvпрацює. Багатобайтним кодуванням потрібна державна машина для їх декодування таlibiconv вважає за краще отримувати цілі символи, тому ви не можете просто надати їй половину символу в одному виклику функції, а другій половині в наступному.

Я можу придумати ще два рішення: одне - це гарний позадіапазонний метод, інше - вбудований злом.

Зміна кодування термінального емулятора (поза межами діапазону) : одне - змінити кодування символів у вашому емуляторі терміналу, тому його кодованим кодування є Shift JIS. Я щойно перевірив konsole, чи підтримує це. У меню Виберіть → Кодування символів → Японія → sjis. Тоді ви можете просто просто tail -fфайл і konsoleподбаєте про розшифровку багатобайтових символів та їх відповідність шрифтовим гліфам.

Кодування терміналу транскоду на ходу (в діапазоні; найкраще) : люб’язно надано Жиллю, який нагадав мені luitпісля дуже довгого часу. Використовуйте luit, яке повинно бути поставлене з вашим дистрибутивом XOrg (на Debian це пакет x11-utils). Використовуйте його так:

$ luit -encoding SJIS -- tail -f x

Це зробить перекодування терміналу SJIS до / з термінального кодування та запуститься tail -f x. Мінусом luitє те, що він не підтримує багатство кодувань, які підтримує libiconv. Перевернути її можна майже скрізь.

Кодування терміналу транскодування на льоту (in-band; hack) : ttyconvце хак, про який я писав багато років тому (спочатку в C, пізніше перероблений у Python), який використовуєlibiconv для перекодування терміналу вводу-виводу. Він породжує новий псевдотермінал і (a) перекодує символи, які ви вводите з локального кодування, у віддалене кодування, і (b) перекодує символи, які ви отримуєте з віддаленого кодування, до локального кодування. Я використовував це для розмови з серверами, які використовували кодування, не підтримувані стандартними терміналами Linux. Зверніть увагу, що всі віддалені кодування, з якими я тестував, були однобайтовими кодуваннями, тому я не можу гарантувати, що він буде працювати для Shift JIS. Я не часто зустрічаю дзвінки, щоб використовувати його в наші дні, оскільки більшість систем переходить на Unicode.

Ось як би ви його використовували:

$ ttyconv -rsjis -- tail -f x

Мінус у ttyconvтому, що я написав це, ніхто не використовує його, окрім мене, він, ймовірно, повний помилок. Я переважаю в цьому. Переваги полягають у тому, що він використовує libiconv, тому якщо кодування незвичне, це найкраща ставка. При останньому підрахунку ttyconv --listпідтримує 100 кодувань.


Дивовижне, спасибі Поза межами діапазону не працював для мене (gnome-terminal, хоча він дозволяє змінювати кодування), але ttyconv працює як шарм.
Євген Бересовський

2
На сьогоднішній день тут є luitчастина стандартного утиліти X11, яка схожа на вашу ttyconv.
Жил "ТАК - перестань бути злим"

@Gilles luitсхожий, за винятком того, що він працює набагато краще, ніж у мене. ;) Спасибі! Саме тому я перестала використовувати в першу чергу. За 12 років, як я встиг забути навіть ім'я команди, і з тих пір я її шукав.
Олексій

@Gilles luitпрацює і для мене. Чому ви не зробите це «офіційною» відповіддю? Це було частиною моєї установки (debian), і, отже, для мене найпростіший у використанні.
Євген Бересовський

1
Я оновив відповідь, щоб включити luitяк кращий вибір для SJIS. На жаль, здається, він не підтримує кожне кодування libiconv. Схоже, мені все ж доводиться використовувати власне рішення для власних сюрреалістичних цілей. :)
Олексій

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.