コマンドをqsubで直接ジョブに投げられるようにする

TL;DR

スパコンを使っていると、qsubを使ってジョブを投げることがあるのではないかと思います。

このときに、ワンライナーを実行したいときなど、一回ファイル作ってからコマンドを投げるのが非常にめんどくさいことがあります。そこで、Pythonのargparseとsubprocessを使って擬似的にコマンドからジョブを投げられるようにしました。

やっている事自体は単純で、引数としてコマンドと各種パラメーターを受け取って、ファイルに加工して作成したファイル対してqsubを投げるだけです。

コード

#!/usr/local/bin/python
import os
import argparse
import subprocess
import random

from datetime import datetime


def main():
    parser = argparse.ArgumentParser()
    parser.add_argument("-c", "--command", type=str, required=True)
    parser.add_argument("-m", "--mem", type=str, default="4G")
    parser.add_argument("-s", "--slot", type=str, default="1")
    parser.add_argument("-n", "--name", type=str, default=None)
    parser.add_argument("--remove", action="store_true")
    args = parser.parse_args()

    mem_param = f'#$ -l s_vmem={args.mem} -l mem_req={args.mem}'
    slot_param = f'#$ -pe def_slot {args.slot}'
    time = datetime.now().strftime("%Y%m%d")

    script = [
        "#!/bin/bash",
        "#$ -S /bin/bash",
        "#$ -cwd",
        mem_param,
        slot_param,
        "",
        "source ~/.bashrc",
        "source ~/.bash_profile",
        "set -eu",
        args.command,
    ]
    if args.name is None:
        file_name = "tmp_" + time + "_" + "{:010d}".format(random.randint(0, 10**10)) + ".sh"
    else:
        file_name = args.name

    with open(file_name, "w") as f:
        f.write("\n".join(script))

    commands = ["qsub", file_name]
    subprocess.run(commands)


    if args.remove:
        os.remove(file_name)


if __name__ == "__main__":
    main()

運用

ファイルのある場所に対してパスを通して、ついでにシンボリックリンクを作成しておけばいつでも使えるようになるのでおすすめです。仮に上のファイル名をqsubpy.pyとしておくと

cat "export PATH:/path/to/qsubpy.py directory:$PATH" >> ~/.bash_profile
ln qsubpy.py qsubpy

みたいなことをしておけば

qsubpy -c "echo hello"

というような感じでジョブが投げられます。リソースを指定したければ

qsubpy -c "echo hello" --mem 16G --slot 4

作成したファイルなどが必要ないときは--removeを使ってもらえれば、作成されたshファイルは消えます。また、shファイルの名前などを指定したいときは--name hoge.shしてください。デフォルトでは、日付+ランダムな10桁の整数を名前につけます。

みたいな感じです。個人的には余り必要を感じませんが、引数を足せば当然簡単にlogとかそのへんもいじれるので、やってみるとより便利になる気がしました。

注意点

  • シバン行は各自の環境に合わせてください
  • 実行権限がなければchmod u+x qsubpyとかしてください

この記事に関するIssueをGithubで作成する

Read Next