#!/usr/bin/env python3 # Копирование файлов из/на сервер # scp_helper [host1:]/path [host2:]/path # import argparse import os CMD_TAR_DECOMP='tar -xz' CMD_TAR_COMP='tar -cz' SUDO_REMOTE=True def parse_arg(s): # Парсим путь. Проверяем тип пути if s.find(':') > -1: connection_name, path = s.split(':') else: connection_name = 'local' path = s if path[0] != '/': path = './' + path path_parts = path.split('/') work_path = '/'.join(path_parts[0:-1]) obj = path_parts[-1] return { 'connection_name': connection_name, 'work_path': work_path, 'obj': obj } def make_pack_cmd(work_path, obj): cmd = f'tar -C {work_path} -c {obj}' return cmd def make_unpack_cmd(work_path, obj): cmd = f'tar -C {work_path}/{obj} -x' return cmd def add_sudo(s): res = 'sudo ' + s return res def make_ssh_cmd(host, port, user, cmd): res = f"ssh {user}@{host} -p {port} '{cmd}'" return res def get_connection_config(con_name): # Получаем конфигурацию подключения по SSH config_path = os.environ.get('SSH_CONNECTOR_HOST_LIST') res = None with open(config_path, 'r') as f: for line in f: if line[0] not in ('#', ' ', '\n'): connection_name, host, user, port, *_ = line.split() if connection_name == con_name: res = { 'connection_name': connection_name, 'host': host, 'user': user, 'port': port } break if res is None: raise Exception('Connection name not found') return res def get_path_config(path): # Объединяем конфигурацию пути и конфигурацию подключения, если подключение удаленное config = parse_arg(path) if config['connection_name'] != 'local': res_config = { **config, **get_connection_config( config['connection_name'] ) } else: res_config = config return res_config def make_full_cmd(config, tar_func): cmd = tar_func(config['work_path'], config['obj']) if SUDO_REMOTE and config['connection_name'] != 'local': cmd = add_sudo(cmd) if config['connection_name'] != 'local': cmd = make_ssh_cmd( config['host'], config['port'], config['user'], cmd ) return cmd if __name__ == '__main__': parser = argparse.ArgumentParser( description='Copy files' ) parser.add_argument('in_path', type=str) parser.add_argument('out_path', type=str) args = parser.parse_args() in_config = get_path_config(args.in_path) out_config = get_path_config(args.out_path) in_cmd = make_full_cmd( in_config, make_pack_cmd ) out_cmd = make_full_cmd( out_config, make_unpack_cmd ) full_cmd = f'{in_cmd} | {out_cmd}' print(full_cmd)