Техника для бесконечно длинных труб - PullRequest
3 голосов
/ 28 июля 2010

Существует два очень простых способа, позволяющих одной программе отправлять поток данных другой:

  • Канал Unix, или сокет TCP, или что-то в этом роде. Это требует постоянного внимания со стороны программы потребителя, иначе программа производителя будет заблокирована. Даже увеличивая буферы их крошечными значениями по умолчанию, это все еще огромная проблема.
  • Обычные файлы - программа производителя добавляется с O_APPEND, потребитель просто читает все доступные новые данные в удобное для него время. Это не требует какой-либо синхронизации (если доступно дисковое пространство), но файлы Unix поддерживают усечение только в конце, а не в начале, поэтому он будет заполнять диск до тех пор, пока обе программы не закроются.

Есть ли простой способ сделать это обоими способами: хранить данные на диске до тех пор, пока они не будут прочитаны, а затем освобождены? Очевидно, что программы могут обмениваться данными через сервер базы данных или что-то в этом роде и не иметь этой проблемы, но я ищу что-то, что хорошо интегрируется с обычным конвейером Unix.

Ответы [ 4 ]

3 голосов
/ 28 июля 2010

Относительно простое ручное решение.

Вы можете попросить производителя создавать файлы и продолжать запись, пока не достигнет определенного размера / количества записей, в зависимости от того, что подходит вашему приложению.Затем производитель закрывает файл и запускает новый с согласованным алгоритмом именования.

Потребитель читает новые записи из файла, затем, когда он достигает согласованного максимального размера, закрывает и отменяет связь, а затем открывает следующий файл..

1 голос
/ 28 июля 2010

Если ваши данные можно разбить на блоки или транзакции какого-либо рода, вы можете использовать для этого метод файла с серийным номером.Производитель данных будет хранить первый мегабайт данных в outfile.1, следующий - в outfile.2 и т. Д. Потребитель может читать файлы по порядку и удалять их при чтении.Таким образом, вы получите что-то похожее на ваш второй метод, с последующей очисткой.

Вы, вероятно, должны обернуть все это в библиотеку, чтобы с точки зрения приложений это было трубойкакой-то.

0 голосов
/ 28 июля 2010

Я ничего не знаю, но не должно быть слишком сложно написать небольшую утилиту, которая принимает каталог в качестве аргумента (или использует $ TMPDIR);и использует команду select / poll для мультиплексирования между чтением из стандартного ввода, поиском по серии временных файлов и записью в стандартный вывод.

0 голосов
/ 28 июля 2010

Вы должны прочитать некоторую документацию на socat . Вы можете использовать его для устранения разрыва между сокетами tcp, файлами fifo, pipe, stdio и другими.

Если вам лень, есть несколько хороших примеров полезных команд.

...