Как запустить сценарии параллельно на удаленной машине?

16

Я могу SSH на удаленной машине, которая имеет 64 ядра. Допустим, мне нужно параллельно запустить 640 сценариев оболочки на этом компьютере. Как мне это сделать?

Я вижу разделение 640 скриптов на 64 группы в каждой из 10 скриптов. Как мне тогда запустить каждую из этих групп параллельно , то есть по одной группе на каждом из доступных ядер.

Был бы сценарий формы

    ./script_A &
    ./script_B &
    ./script_C &
    ...

где script_Aсоответствует первой группе, script_Bвторой группе и т. д., достаточно?

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

Том
источник
Не гарантируется, что они распределены по ядрам равномерно. Посмотрите на эту тему. stackoverflow.com/questions/13583146/…
Руи Ф. Рибейро

Ответы:

24

Это похоже на работу для параллельной GNU:

parallel bash -c ::: script_*

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

Конечно, если вы не хотите присматривать за сеансом SSH во время работы сценариев, вы должны использовать nohupилиscreen

Дмитрий Григорьев
источник
Это хороший ответ, и я принимаю его, так как в общем случае это будет работать хорошо. К сожалению, лично для меня у меня нет прав администратора на удаленной машине, и поэтому я не могу установить parallelпакет. Спасибо`
Том
10
Вам не нужно устанавливать параллельную глобально: вы должны иметь возможность запустить копию из своего домашнего каталога.
Даг
bash -cможет быть ненужными: parallel ::: ./script*. С сценарием 640, вероятно, они очень похожи (например, отличается только аргумент). Для этого рассмотрите возможность использования GNU Parallel напрямую, чтобы установить эти аргументы и использовать один скрипт.
Оле Танге
Как бы я установить GNU параллельно на удаленной машине?
Том
@ Том Что изменилось тем, что вы используете удаленный компьютер? Просто получите нужный пакет с gnu.org/software/parallel и установите.
Дмитрий Григорьев
5

Это будет работать до тех пор, пока вам не нужно следить за выводом, и вы можете оставить сеанс ssh открытым, пока скрипты запускаются. Если что-то из этого не соответствует действительности, я бы рекомендовал использовать screenнесколько вкладок. Вы могли бы сделать что-то вроде

screen
for script in script_A script_B script_C; do
  screen -t "$script" ./$script
done;
Дэвид Кинг
источник
Мониторинг выходов, которые меня не интересуют - я бы не хотел оставлять сеанс ssh открытым. Как насчет использования nohup? Это предотвратит остановку сценариев, если сессия закончится, нет? Я также посмотрю ваши рекомендации на экране. Благодарность!'
Том
nohupвероятно, сработает, я просто более знаком с ним, screenи у него гораздо больше функций, которые могут быть полезны для вас.
Дэвид Кинг,
2

Чтобы запустить и управлять большим количеством сценариев, вам понадобится какое-то программное обеспечение для управления, чтобы контролировать использование ресурсов (ЦП, память, приоритет), видеть состояние задания (ожидание, приостановка, выполнение, завершение).

Для этого построен Grid Engine, например, Sun Grid Engine ( http://wiki.gridengine.info/wiki/index.php/Main_Page ) или Open Grid Scheduler ( http://gridscheduler.sourceforge.net/). ). Вам нужно, чтобы администратор установил для вас подходящее программное обеспечение, прежде чем вы сможете начать. Администратор может с радостью это сделать вместо того, чтобы видеть сотни запущенных на машине процессов и не иметь над ними контроля.

В общем, администратор определяет, на сколько слотов машина может быть разделена, и вы отправляете задание в очередь и указываете, сколько слотов хочет использовать задание, механизм сетки будет отслеживать общее использование системы и запускать задание в соответствии с политика очередей, определенная администратором. например, одновременно может выполняться не более x заданий и т. д. Остальные задания будут находиться в очереди в состоянии ожидания и освобождаться после завершения предыдущих заданий.

user2912207
источник
0

Я делал это несколько раз и обычно просто запускаю свой собственный скрипт, чтобы выполнять работу с контролем работы. Обычно, если у вас есть имена всех скриптов, которые вы хотите запустить в файле, решение выглядит так:

#!/bin/bash
scripts=$(cat scriptfiles.txt)
declare -i NUM=0
declare -i MAX_PROCS=30
for script in "$scripts"
do
  NUM=$((NUM+1))
  ssh remote.host.ip "${script}" > ${script}.log 2>&1 &
  if [ $NUM -ge $MAX_PROCS ];then
    echo "Waiting for $NUM processes to finish."
    wait
    NUM=0
  fi
done
echo "Waiting for final $NUM processes to finish."
wait
exit

Это грубая сила, но эффективная. Кроме того, вам не нужно добавлять дополнительное программное обеспечение, такое как параллельное, в ваши системы.

Большая проблема заключается в том, что команда wait будет ожидать завершения самого медленного сценария, что может тратить время. Я создал сценарии, чтобы позаботиться об этой ситуации, но они становятся более сложными, как вы можете себе представить. Если все ваши сценарии выполняются примерно за одно и то же время, это работает хорошо.

Другая проблема заключается в том, что вам, возможно, придется настроить MAX_PROCS, чтобы определить наилучшую производительность.

Конечно, количество соединений ssh ​​может быть громоздким. В этом случае просто переместите этот сценарий на удаленный хост и измените строку «ssh ...», чтобы просто запускать сценарии напрямую.

Старожил
источник