Revision 2.2 - kisapapa1227/retrek-ui_V2 GitHub Wiki
主な変更:job管理用システムの導入
exe.py の進捗に関して(現状の不具合)
setInterval+ajax by javascript in blade.php で、exe.py の進捗具合のモニター、及び、不具合(exe.py が落ちた時)の対応をすると ブラウザーのタブがフォーカスされていないと、(ajax がさぼるので)上手くいかない --> setInterval のタイミングで処理が行われず、プロセスがハングアップしていると誤認識する。
タブが最小化されていても、ジョブ管理が適切に出来るように、
- 管理用プロセス(python)
- 進捗テーブル (mysql) で管理する。blade は、プロセスと作業結果を見に行くのではなく、データベースを読みに行く。
基本的な流れ、方針
現状の枠組みだと、単一ユーザーの複数 login 可能、かつ、中間ファイルに端末情報を入れていないので、単一ユーザで流せる探索は1系統にしないと不具合が起きる。
タイミングとしては、スクリプトを作る段階で判別する必要あり。 並列の探索を制限するためには、実行 job がある場合、multiProc へ飛ばし、multiSearchへの経路をなくす。job制御のプロセスを立ち上げ、GUI側を閉じてしまっても、計算は続ける。計算中でも menu に戻り、データベースは利用できるようにする。<-- 利用中のデータベースの削除は制限する。
pdf 作成の流れ(Rev 2.0 の確認)
- 探索(1)では、$uid/report に $substance.txt が作られる。そのファイル内に、指定した数の routes が書き込まれると
- exe.py の中から、make_report/routeAnalyzer.py が呼び出され、$uid/report/$substance.pdf が作られる。
- 共有データベースだと、$uid/report/$substance.pdf を report/$tableId.pdf に移動する。
- (これから)個人用データベースだと、$uid/report/$substance.pdf を $uid/report/$tableId.pdf とリネーム。
- 探索(1)だと、ボタン駆動で addDb を呼び出し、RetRekController.php 経由で、make_report/addDb.py を呼び出す。
- データベースの置き場所は固定で、RetReKで共有が sList.db で、個人用が sList$uid.db
- (重複するが)routeAnalyzer と同じ作業で、$substance.txt を解析、整理した結果をデータベースに登録する。
- (これから)探索(2)でも作業は同じだが、別プロセスでのジョブ投入、データベース管理の導入で、並列管理。
- データベース管理画面から作成する場合(pdf/pptx/db)共通で、syncPdf on RetRekController.php より
- make_report/readDb.py で作成する。出力ディレクトリーは -d で変更可能。ファイル名は、$tableId.pdf
仕様の整理
投げっぱなしで ok 。
- Controller でスクリプトを作成して、userId を渡して jobMaster を起動する。
- データベースへ情報の受け渡し方法は? <-- $uid_async.sh から読む。
- 引数で -start uid max_loop で開始、jobMaster -ask uid で情報を引き出す。
- uid_async.sh を有効利用。#abort:false_smiles、false_config、#smiles:$smiles の行を入れて受け渡す。
- Controller で、false_smiles (引数の不正)の場合には、script に #false:*** の行を入れる。
- jobMaster.db のテーブル
- Master(userId,max_job,running_job,exp_time):running_job>max_job で終了。
- Slave(userId,#,smiles,available,done,repeated,start_time,end_time,exp_time)
- 投入回数を repeated に記録して、たとえば、5回投入して落ちる場合は、なにかおかしい!ので、次のジョブに進む。
- 開始時刻、実行時間、終了時刻など、multiProc.php で必要な物はデータベースで保持する。
- multiSearch/SingleSearch を呼んだ時、検索中なら、進捗画面へ移動する。
- Master where userId で 実行中がないか確認する。-> multiProc へ飛ぶ
- (ありえないけど)jobMaster が落ちたら再起動する。
- cron で再起動する。*1
- multiProc のボタンを
- 実行中の Master を落として、戻る。
- 実行のまま menu に戻る。1.
- multiProc.blade の進捗表示に関して
askProc を利用、images/$uid/$substance.txt を読みに行く。プロセスの有無、及び、kill するときは、無差別!人のjob も瞬殺。<-- 別もあるけど、processId を持っている必要がある。 exe.py に $uid を付けてるので、これで選別できる。singleSearch/multiSearchが並走する場合には? 判断できないので、singleSearch は投入後に Masetr.db に登録する必要あり。- single user, single job: ジョブ実行中には、検索設定画面を開かせない。
- データベース任せで、自分では処理をしない。
cron の仕事 (jobMaster.py -start が行う)
-
作業
- Dockerfile に apt install -y cron を加える。Dockerfile では、複数のフロントプロセスは実行できない。。らしいので
- supervisord.conf に実行スクリプトを入れる。
- 実行記録 jobMaster.lock を作る。$uid を書き込む。
- crontab に、自分 (jobMaster.py) が落ちた時に、jobMaster.py -restart -uid uid を実行する。
- jobMaster.py -start/restart は、終了時に、jobMaster.lock を消す。crontab も消す。
- 足す場合:(crontab -l ; echo * * * * * command) | crontab -
- 消す場合:(crontab -l | grep -v command) | crontab -
- Dockerfile に apt install -y cron を加える。Dockerfile では、複数のフロントプロセスは実行できない。。らしいので
-
cron で、ps aux | grep uid | grep jobMaster.py が無ければ、jobMaster.py -restart -uid uid で再実行。
- jobWatcher.py
-
askMakeScript($n,$l):変更なし
-
multiProc($request) <-- blade からの繰り返し
- script を作り、jobMaster.py を起動する。それ以外の作業は、jobMaster.py へ移植。i.e.)ジョブ管理は Laravel から独立させる。
-
askProc: データベースから貰う。
- singleSearch/Proc 用に残すが、逐次探索では利用しない。
cron を supervisord から起動する。
cat supervisord.conf
[program:cron]
command=cron -f
stdout_logfile=/tmp/cron.log
redirect_stderr=true
container 内で、
$service cron status
* cron is running
で確認。
作業手順
- 何はともあれ、jobMaster.py を動かす。(済)
- Controllerの変更
- multiProc で、script の作成、async_jobMaster.sh (jobMaster.py) の実行(済)
- multiProc.blade の変更
- 必要な物はすべて、askProc から貰う。持ち物は $uid/$db_type のみ。
- kRet は、sail, python, $uid を含むすべて止める。
- mRet でジョブを残したまま、menu の戻る。
デーベースへの追加 ?jobMaster の仕事
jobMaster.py の詳細(仕様)
- -start -uid uid -max_loop 10 -db_type com データベースへ投入、動かす。
- テーブルを作る。
- master(user_id,max_loop,running_job,db_type,exp_time,abort)
- slave(user_id,script_id,smiles,substance_name,found_route,max_route,done,start_time,end_time)
- abort: 再投入=ジョブが終了したが、found_route と max_route が一致しなかった場合に再計算
- 両テーブル(master/slave)から、前のレコード where uid=$uid を delete する。
- master/slave にレコードを update する
- ジョブ(script)を非同期で逐次実行する。<-- &つきなので、仮に同期でもすぐに戻って来る!
- done in slave が "ready" でない場合は何もしない。
- master/slave の running_job/done,start_time を update する。
- 投入で、time.sleep でループ、終了待ち
- プロセスの有無をチェックする。<-- ps aux |grep exp.py | grep $uid
- どこまで進んでいるかは $substance.txtを読みに行く。
- 進捗があれば、master/salve (exp_time/found_route) を update
- プロセスが無ければ、終了処理。
- found != route の場合、abort をカウントアップして、再実行。
- slave の done="Complete"で終了。
- ジョブ終了
- addDb.py を呼んで、sList.db/sList$uid/db に追加する。
- readDb.py を呼んで、pdf を作る。
- テーブルを作る。
- -restart -uid uid : jobMaster.py が落ちていた場合に再開する。
- 実行中は ~/jobMaster.lock を作成、user_id を書き込む。終了したら消す。
- crone で見張って、jobMaster.lock が存在した場合、user_id を読み出して、restart する。
- 小さなことだが、実行中の exe.py があると無駄なので、
- kill するか、継続するか?こだわらずに放置か、時間があったら kill かな。
- -ask -uid uid -pid pid: 進捗情報を取得する。実行中のジョブ番号+"###"に続いて
- 実行中のジョブ番号と指定した pid が一致する場合は、検索済みルート数、、、、経過時間、終了時刻などを返す。
- 一致しない場合は、ジョブリストを返す。
multiSearch.php の詳細(仕様)
- スクリプトの作成、jobMaster.php の呼び出し
jobMaster.pygetPid で $uid で exe.py の起動確認- なければ、通常通り multiSearch.blade の呼び出し
- あれば、multiProc.bladeへ
mutliProc.blade の詳細(仕様)
- 「処理継続で戻る」を追加
singleSearch.php の詳細(仕様)
- multiSearch.php と同様
dbManage.blade
- jobMaster.py の起動中は db の削除、復元(=上書き)は禁止する。
- controller から dbMange を呼ぶときにチェックする。
動作確認中に起きた、cron/jobMaster.py の二重起動が起きた条件の検討
- jobWatcher.py が、jobMaster.py -uid $uid の有無を確認して再実行する。
- CUIで、同時に、二つ jobMaster.py -restart を投げれば、起きるかもしれないが、cron 管理なので起こらない。
- jobMaster.py では、-start オプション時に、batch table 作成、jobMaster.lock 作成、正常終了時に削除する。
不具合:ルートが見つからなかった場合
- addDb.py が落ちる。
- exe.py が見つからなかった場合に、要求数 smiles; と言う列を送ってくる。
- 同じルートを削除でまとめると、反応なしのルートが一つ見つかる。<-- 反応ありのルートが一つと区別がつかない。
- とりあえず、中途まで処理をすると、繋がりなし(len(connect)<1) になったら exit() <-- 検索条件は table に書き込み済み。
- readDb.py 側の処理。
- 対応するテーブル (searchTable$pid)が無い場合のしょり、
関連ファイル
- resouce/views/db.blade.php, dbManager.blade.php, menu.blade.php, multiProc.blade.php
- resources/js/Pages/Auth/Login.vue
- routes/web.php
- ReTReKpy/addDb.py, jobMaster.py, jobWatcher.py, readDb.py
- (installer)UninstallImages.sh
- docker/8.3/Dockerfile