import os
import ast
import subprocess
def find_python_files(root_dir):
"""
Рекурсивно находит все Python файлы в заданном каталоге.
"""
python_files = []
for dirpath, _, filenames in os.walk(root_dir):
for filename in filenames:
if filename.endswith('.py'):
full_path = os.path.join(dirpath, filename)
python_files.append(full_path)
return python_files
def extract_cmds(file_path):
"""
Извлекает переменную CMDS из Python файла.
Предполагается, что CMDS является списком строк.
"""
with open(file_path, 'r', encoding='utf-8') as file:
file_content = file.read()
try:
parsed = ast.parse(file_content, filename=file_path)
except SyntaxError as e:
print(f"Ошибка синтаксиса в файле {file_path}: {e}")
return []
cmds = []
for node in parsed.body:
if isinstance(node, ast.Assign):
for target in node.targets:
if isinstance(target, ast.Name) and target.id == 'CMDS':
if isinstance(node.value, (ast.List, ast.Tuple)):
for elt in node.value.elts:
if isinstance(elt, ast.Str):
cmds.append(elt.s)
else:
print(f"Неподдерживаемый тип элемента в CMDS в файле {file_path}")
else:
print(f"Переменная CMDS не является списком или кортежем в файле {file_path}")
return cmds
def main(root_dir):
python_files = find_python_files(root_dir)
python_files.sort() # Сортировка путей в алфавитном порядке
executed_cmds = set()
for file_path in python_files:
cmds = extract_cmds(file_path)
if cmds:
print(f"\nОбрабатывается файл: {file_path}")
for cmd in cmds:
if cmd in executed_cmds:
print(f"Команда уже выполнена, пропуск: {cmd}")
continue
print(f"Выполнение команды: {cmd}")
try:
# Выполнение команды через оболочку
result = subprocess.run(cmd, shell=True, check=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True)
print(f"Результат:\n{result.stdout}")
except subprocess.CalledProcessError as e:
print(f"Ошибка выполнения команды '{cmd}': {e.stderr}")
executed_cmds.add(cmd)
if __name__ == "__main__":
# Укажите корневой каталог, откуда начать поиск Python файлов
root_directory = '.' # Текущий каталог
main(root_directory)
import os
import importlib.util
import subprocess
import logging
# Настройка логирования
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
def find_python_files(directory):
"""Ищет все Python-файлы в указанной директории."""
python_files = []
for root, _, files in os.walk(directory):
for file in files:
if file.endswith('.py'):
python_files.append(os.path.join(root, file))
logging.info(f'Найдено {len(python_files)} Python-файлов.')
return python_files
def extract_cmds_from_file(file_path):
"""Извлекает переменную CMDS из указанного Python-файла."""
spec = importlib.util.spec_from_file_location("module.name", file_path)
module = importlib.util.module_from_spec(spec)
try:
spec.loader.exec_module(module)
cmds = getattr(module, 'CMDS', None)
if isinstance(cmds, list):
logging.info(f'Извлечены команды из файла: {file_path}')
return cmds
else:
logging.warning(f'Переменная CMDS не найдена или не является списком в файле: {file_path}')
return []
except Exception as e:
logging.error(f'Ошибка при извлечении команд из файла {file_path}: {e}')
return []
def execute_commands(cmds):
"""Выполняет список команд, избегая дублирования."""
executed_commands = set()
for cmd in cmds:
if cmd not in executed_commands:
logging.info(f'Выполнение команды: {cmd}')
try:
subprocess.run(cmd, shell=True, check=True)
executed_commands.add(cmd)
except subprocess.CalledProcessError as e:
logging.error(f'Ошибка при выполнении команды "{cmd}": {e}')
else:
logging.info(f'Команда "{cmd}" уже была выполнена, пропускаем.')
def main(directory):
"""Основная функция для извлечения и выполнения команд."""
all_cmds = []
# Поиск всех Python-файлов
python_files = find_python_files(directory)
# Извлечение команд из файлов
for file in sorted(python_files):
cmds = extract_cmds_from_file(file)
all_cmds.extend(cmds)
# Удаление дубликатов и сортировка команд
unique_sorted_cmds = sorted(set(all_cmds))
# Выполнение команд
execute_commands(unique_sorted_cmds)
if __name__ == "__main__":
# Укажите путь к директории с Python-файлами
directory_path = input("Введите путь к директории с Python-файлами: ")
if os.path.isdir(directory_path):
main(directory_path)
else:
logging.error("Указанный путь не является директорией.")
Условие:
Дерево директорий, в котором лежат питон файлы (вложенность может быть любой).
В этих файлах должны находится переменная CMDS с shell командами echo, которые
нужно исполнить.
Задача:
Написать скрипт, который читает переменную CMDS со списком (list) команд из всех
файлов в дереве директорий
и выполнит их по очереди с сортировкой в алфавитном порядке по имени пути. Команды,
записанные в одном файле, должны быть выполнены в порядке, в котором они указаны в
переменной.
Команда может быть выполнены только 1 раз. Если команда уже была выполнена, то
необходимо вывести сообщение, что такая команда уже была выполнена и пропустить ее
выполнение.
Если решение предполагает использование сторонних библиотек, то описание
зависимостей необходимо сделать в формате requirements.txt.
ПРИМЕР:
БУДУ оч признателен за помощь