import threading import os import re import time from scp import SCPClient import dearpygui.dearpygui as dpg import paramiko from utils import show_status_text HOST = 'geophyslab.srcc.msu.ru' URBAN_LES_REPOS = ( 'git clone http://{username}:{password}@tesla.parallel.ru/emortikov/nselibx-common.git', 'git clone http://{username}:{password}@tesla.parallel.ru/emortikov/nselibx-wstgrid.git', 'git clone http://{username}:{password}@tesla.parallel.ru/emortikov/nse-gabls1-urban-les.git' ) def build_model(server_username, server_password, gitlab_username, gitlab_password, repos=URBAN_LES_REPOS): try: ssh = paramiko.SSHClient() ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) ssh.connect(HOST, username=server_username, password=server_password) commands = [ 'mkdir run', 'cd ./run' ] for repo in repos: commands.append(repo.format(username=gitlab_username, password=gitlab_password)) commands += [ 'cd ./nse-gabls1-urban-les/nse-gabls1-urban-les/', 'chmod +x cpall.sh', './cpall.sh ../../code', 'cd ../../code', 'make -B MACHINE=local COMPILER=gnu -j 23', ] commands = '; '.join(commands) show_status_text(f'building model') dpg.show_item('loading') x, y = dpg.get_item_pos('status_text') dpg.set_item_pos('loading', (x - 40, y)) stdin, stdout, stderr = ssh.exec_command(commands) with open('log.txt', 'w') as file: file.write(stdout.read().decode()) ssh.close() show_status_text('') dpg.hide_item('loading') show_status_text('model builded:) log written to log.txt.') except Exception as e: show_status_text(f'error: {str(e)}') def make_run_command(): command = f'mpirun -np {int(dpg.get_value('-np'))} ./nsenx' if dpg.get_value('-arch') != 'cpu': command += f' -arch {dpg.get_value('-arch')}' if dpg.get_value('use-udump'): command += f' -udump {dpg.get_value('-udump')}' if dpg.get_value('use-model-output'): command += f' -model-output {dpg.get_value('-model-output')}' return command def run_on_lab_server(username, password): try: show_status_text('model running...') dpg.show_item('progress_bar') ssh = paramiko.SSHClient() ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) ssh.connect(HOST, username=username, password=password) scp = SCPClient(ssh.get_transport()) scp.put('tmp.txt', 'run/code/config.txt') command = make_run_command() commands = [ 'cd ./run', 'cd ./code', command ] commands = '; '.join(commands) log = '' stdin, stdout, stderr = ssh.exec_command(commands) while not stdout.channel.exit_status_ready(): if stdout.channel.recv_ready(): output = stdout.channel.recv(512).decode() update_progress(output) log += '\n\n' + output # time.sleep(1) output = stdout.read().decode() dpg.set_value('progress_bar', 1.) log += '\n\n' + output with open('log.txt', 'w') as file: file.write(log) scp.close() ssh.close() dpg.hide_item('progress_bar') show_status_text('success:) log written to log.txt.') except Exception as e: show_status_text(f'error: {str(e)}') def update_progress_building_model(): show_status_text(f'building model') dpg.show_item('loading') x, y = dpg.get_item_pos('status_text') dpg.set_item_pos('loading', (x - 40, y)) def update_progress(output): if not re.findall(r'([0-9]+)%', output): progress = 0.0 else: progress = int(re.findall(r'([0-9]+)%', output)[-1]) / 100 dpg.set_value('progress_bar', progress) def start_remote_execution(server_username, server_password): threading.Thread(target=run_on_lab_server, args=(server_username, server_password)).start() def start_model_build(server_username, server_password, gitlab_username, gitlab_password): threading.Thread(target=build_model, args=(server_username, server_password, gitlab_username, gitlab_password)).start() def get_server_output_structure(username, password): try: ssh = paramiko.SSHClient() ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) ssh.connect(HOST, username=username, password=password) stdin, stdout, stderr = ssh.exec_command('cd ./run/code/output; find . -type f') output = stdout.read().decode() ssh.close() return output except Exception as e: show_status_text(f'error: {str(e)}')