Как стать автором
Обновить

Комментарии 10

> Помимо локального режима, схожего по функционалу с xargs, он имеет возможность выполнения программ через SSH на нескольких серверах.
Ого. Однозначно плюсов вам. Я даже не догадался такое поискать, хотя и parallel активно использую.

> так как один из целевых хостов будет перегружен.
А у него вроде есть параметр maxla? Или via ssh он не работает?
Честно говоря, мы не сильно углублялись в нутра parallel, т.к. широкого применения он у нас не имеет, а предварительные изыскания показали его неприменимость к нашей задаче.
Помимо загруженности хоста есть ещё понятие «доступности» (выключен, например, или gracefully выводится из эксплуатации :). Также, нам не хочется держать где-то в конфиге список хостов и их технические характеристики — пусть это будет головной болью кластер-менеджера.
НЛО прилетело и опубликовало эту надпись здесь
Спасибо за комментарий и интересный инструмент!
Из входных данных проекта https://github.com/cheusov/paexec/:
Small program that processes a list of tasks in parallel on different CPUs, computers in a network or whatever.
Очень похоже на то, что выполняет наша утилита.
А здесь: https://github.com/cheusov/paexec/blob/master/paexec/paexec.pod
Tasks are read by paexec from stdin and are represented as one line of text, i.e. one input line — one task.
И здесь мы схожи.

Выходит, что реализации схожи, и, с моей точки зрения, обе могут называться «распределённым xargs» :)

Со своей колокольни обратил внимание на пару вещей, из-за которых мы бы не стали этот инструмент брать в рассмотрение:

https://github.com/cheusov/paexec/blob/master/paexec/paexec.pod
Remember that empty line MUST NOT appears in general result lines

Мы ограничены форматом output'а того, что мы запускаем на удалённой стороне.

Последовательность fork-exec
krash@krash:~$ paexec -t '/usr/bin/ssh -x' -n 'cloud1' -c '/usr/bin/uptime; echo ""' -d
nodes_count = 1
nodes [0]=cloududs1
cmd = uptime; echo ""
start: init__read_graph_tasks
start: init__child_processes
running cmd: /usr/bin/ssh -x cloududs1 'env PAEXEC_EOT='\'''\''  /bin/sh -c '\''/usr/bin/uptime; echo ""'\'''


Команды транспорта опускаем, рассмотим то, что запускается на удалённой стороне:
/bin/sh -c "/usr/bin/uptime"

При выполнении этой команды, мы получим на удалённой стороне последовательность fork-exec, которая сначала запустит /bin/sh, а затем — fork-exec для /usr/bin/uptime.
Я запустил paexec, указав в качестве команды пользователя /usr/bin/sleep 1000, затем прервал выполнение paexec через SIGINT.
Что мы получаем в результате? Правильно — на удалённом хосте у нас висит /usr/bin/sleep (аналог нашего долгоиграющего приложения).
Т.е. при прерывании работы управляющего приложения, дочерние не прибиваются. Именно по этой причине, мы в своей реализации не используем spawn shell'а, а сразу зовём execve приложения.
Насчет ограничений на outout. Их нет. Пустая строка — значение ПО УМОЛЧАНИЮ, потому ее использовать нельзя. Но никто не мешает ее сменить. См. paexec -y

ЕМНИП python-fabric умеет параллельно запускаться на разных хостах, делать всё что скажешь и не терять stdout.

Спасибо за ещё один инструмент в копилку!
Как я написал в комментарии ниже, за счёт spawn'а remote shell, мы рискуем оставить после себя долгоиграющий неприбитый процесс, что для нас неприемлемо. Ну и да, опять — где брать список хостов, и т.д.
Я так понимаю что это применимо только к тем задачам которые только производят трансформации над чем-то. Но не сохраняют ничего в локальную фс, но я так понял все же есть возможность использования hdfs? Просто допустим у нас есть задача сохранять файл с именем и содержимым в виде переданного аргумента, то куда в итоге все будет сохраняться если запускать такую задачу через ваш hadoop-xargs? Потому что судя по всему скормить ему можно абсолютно любую программу и он будет ее запускать с нужными аргументами.
В общем случае, любой кластер, где производятся подобного рода вычисления, является statless. Это означает, что после выполнения программы, все артефакты (временные файлы), которые она наплодила, должны быть уничтожены. Для сохранения каких-либо результатов следует использовать shared-ресурсы (база данных, HDFS).
Конкретно в случае нашей задачи, мы на Python производим вычисления и записываем результат в файл в текущей рабочей директории. Когда бизнес-логика отработала, файл заливается в HDFS (из этого же процесса).
В случае краха процесса/уничтожения YARN контейнера, рабочая директория контейнера уничтожается, и мы не мусорим локальную FS кластера.
Спасибо за ответ, побольше бы статей с особенностями Hadoop/Spark etc и хорошими практиками по работе с ними.
Зарегистрируйтесь на Хабре, чтобы оставить комментарий