首页 > 解决方案 > 在 bash 中启动多个 tmux 会话

问题描述

我有一个 python 脚本,my_python_script它需要一个输入日期。我有一个 bash 脚本,它在 for 循环中为一系列日期调用这个 python 脚本。我尝试在 for 循环中创建一个命名会话,但这嵌套了 tmux 会话:

call_runner_date_range() {
    start=$1
    end=$2

    start=$(date -d $start +%Y%m%d)
    end=$(date -d $end +%Y%m%d)

    while [[ $start -le $end ]]
    do
            tmux new -s $start
            start=$(date -d"$start + 1 day" +"%Y%m%d")
            formatted_date=$(date -d $start +%m-%d-%Y)
            python -m my_python_script --analysis-date=$formatted_date
    done
}

call_runner_date_range '2016-12-31' '2019-08-15'

我想修改这个 bash 脚本为每个日期打开一个新的 tmux 会话(我想使用 tmux 的原因是我可以监控输出日志),以便这些脚本可以并行运行。我该怎么做,有没有比使用 tmux 更好的选择?

标签: bashtmux

解决方案


要在后台启动进程,请使用&命令的终止字符。用于>将进程的标准输出重定向到文件。对于一些参考,您可以查看bash 手册命令列表bash 手动重定向,但许多资源都可以在线获得。

所以脚本会变成:

call_runner_date_range() {
    start=$1
    end=$2

    start=$(date -d $start +%Y%m%d)
    end=$(date -d $end +%Y%m%d)

    while [[ $start -le $end ]]
    do
            start=$(date -d"$start + 1 day" +"%Y%m%d")
            formatted_date=$(date -d $start +%m-%d-%Y)
            python -m my_python_script --analysis-date=$formatted_date > log_$start.log &
    done
}

call_runner_date_range '2016-12-31' '2019-08-15'

您可以使用wait内置的 shell 来等待当前 bash shell 中所有当前仍在运行的后台进程。$!或者,您可以使用并指定要等待的 pid 列表来保存每个后台作业进程 ID PID 。

childs=() # bash array, initializing to empty

# then later:
python -m my_python_script --analysis-date=$formatted_date > log_$start.log &
childs+=($!)  # append the background jobs pids name to bash array

# then later
wait "${childs[0]}" # wait for first background job in childs array
wait "${childs[@]}" # wait for all background jobs in childs array

请注意,您可能有兴趣使用xargs它可以(在大多数实现中)为每行输入并行执行命令,或者令人惊叹的GNUparallel,它只是一个外壳工具,可以尽可能简单地并行执行多个作业。


推荐阅读