import json import os import time import openpyxl from kivy.app import App from kivy.uix.label import Label from kivy.uix.button import Button from kivy.uix.boxlayout import BoxLayout from kivy.uix.popup import Popup from kivy.uix.filechooser import FileChooserListView from selenium import webdriver from selenium.webdriver.common.by import By from selenium.webdriver.common.keys import Keys from selenium.webdriver.chrome.options import Options from selenium.webdriver.support.ui import WebDriverWait from selenium.webdriver.support import expected_conditions as EC from selenium.common.exceptions import NoSuchElementException, TimeoutException # Файл конфигурации для сохранения последнего пути CONFIG_FILE = 'config.json' def get_last_used_directory(): """Возвращает последний использованный каталог из файла конфигурации.""" if os.path.exists(CONFIG_FILE): with open(CONFIG_FILE, 'r') as file: config = json.load(file) return config.get('last_dir', '') return '' def save_last_used_directory(directory): """Сохраняет последний использованный каталог в файл конфигурации.""" with open(CONFIG_FILE, 'w') as file: json.dump({'last_dir': directory}, file) def get_search_key(filename): """ Преобразует имя файла: удаляет расширение и заменяет дефисы на подчёркивания. Например, "3M-Protemp4-Banner-900x450-BG.jpg" превращается в "3M_Protemp4_Banner_900x450_BG". """ if not filename: return "" base = os.path.splitext(filename)[0] return base.replace("-", "_") class FileSearchApp(App): def build(self): self.file_path = "" self.extensions = [".psd", ".indd", ".tif", ".tiff"] layout = BoxLayout(orientation='vertical') self.label = Label(text="Select an Excel file with Asset IDs") layout.add_widget(self.label) choose_button = Button(text="Choose File") choose_button.bind(on_press=self.select_file) layout.add_widget(choose_button) start_button = Button(text="Open Login Page") start_button.bind(on_press=self.open_login_page) layout.add_widget(start_button) self.continue_button = Button(text="Continue After Login", disabled=True) self.continue_button.bind(on_press=self.start_search) layout.add_widget(self.continue_button) return layout def select_file(self, instance): last_dir = get_last_used_directory() or '.' filechooser = FileChooserListView(path=last_dir, filters=['*.xlsx']) popup = Popup(title="Choose Excel File", content=filechooser, size_hint=(0.9, 0.9)) filechooser.bind(on_submit=lambda chooser, selection, touch: self.on_file_select(selection, popup)) popup.open() def on_file_select(self, selection, popup): if selection: self.file_path = selection[0] self.label.text = f"Selected File: {self.file_path}" print(f"Selected file: {self.file_path}") save_last_used_directory(os.path.dirname(self.file_path)) popup.dismiss() else: print("No file selected.") def open_login_page(self, instance): if not self.file_path: popup = Popup(title='Warning', content=Label(text='Select a file before starting!'), size_hint=(0.8, 0.3)) popup.open() return options = Options() options.add_argument("user-data-dir=/Users/vadymsamoilenko/Library/Application Support/Google/Chrome/Profile 1") self.driver = webdriver.Chrome(options=options) try: self.driver.get("https://mmmspinco.brand-portal.adobe.com/mediaportal.html/content/dam/mac/mmmspinco") time.sleep(5) WebDriverWait(self.driver, 30).until( EC.presence_of_element_located((By.XPATH, "/html/body/coral-shell/coral-shell-content/div[1]/a/img")) ) self.continue_button.disabled = False print("Login successful, ready to continue.") login_popup = Popup(title='Login', content=Label(text='Please log in and complete 2FA.\nClick "Continue After Login" once logged in.'), size_hint=(0.8, 0.3)) login_popup.open() except Exception as e: print("Error opening login page:", e) self.driver.quit() def start_search(self, instance): if not self.file_path or self.continue_button.disabled: popup = Popup(title='Warning', content=Label(text='Ensure you are logged in before starting!'), size_hint=(0.8, 0.3)) popup.open() return try: wb = openpyxl.load_workbook(self.file_path) sheet = wb.active # Предполагаем, что: # - Столбец 1: Asset ID # - Столбец 3: Имя файла (с расширением) for row in sheet.iter_rows(min_row=2, max_row=sheet.max_row): asset_id = row[0].value # Asset ID file_name = row[2].value if len(row) >= 3 else None # Имя файла found_link = None if asset_id and file_name: search_key = get_search_key(file_name) print(f"Processing Asset ID: {asset_id} with search key: {search_key}") self.driver.get("https://mmmspinco.brand-portal.adobe.com/aem/search.html") search_box = WebDriverWait(self.driver, 10).until( EC.presence_of_element_located((By.NAME, "fulltext")) ) # Очистка поля ввода через clear() и JavaScript time.sleep(3) search_box.clear() self.driver.execute_script("arguments[0].value = '';", search_box) # Поиск по asset_id для первоначального отбора search_box.send_keys(asset_id) search_box.send_keys(Keys.RETURN) time.sleep(3) try: properties_button = WebDriverWait(self.driver, 30).until( EC.element_to_be_clickable((By.XPATH, "//button/coral-icon[@icon='infoCircle']")) ) properties_button.click() time.sleep(3) # Получаем все PSD-ссылки из секции "Others" psd_link_elements = WebDriverWait(self.driver, 30).until( EC.presence_of_all_elements_located( (By.XPATH, "//div[contains(@class, 'references-referencing')]//a[@data-relation='others' and contains(@data-asset-path, '.psd')]") ) ) time.sleep(3) # Выводим отладочную информацию для каждого кандидата for elem in psd_link_elements: title_attr = elem.get_attribute("title") href = elem.get_attribute("href") print(f"Candidate element -> title: {title_attr}, href: {href}") # Выбираем элемент, где search_key встречается в title или href (без учета расширения) for elem in psd_link_elements: title_attr = elem.get_attribute("title") href = elem.get_attribute("href") search_key_lower = search_key.lower() if (search_key_lower in title_attr.lower() if title_attr else False) or \ (search_key_lower in href.lower() if href else False): found_link = href print(f"Selected link matching search key: {found_link}") break except TimeoutException: print("Timeout while waiting for the PSD link element.") found_link = None except NoSuchElementException: print("PSD link element not found.") found_link = None except Exception as e: print(f"Unexpected error occurred: {e}") found_link = None if not found_link: print("No suitable link found for asset:", asset_id) sheet.cell(row=row[0].row, column=2, value=found_link if found_link else "Links not found") print(f"Processed asset {asset_id}, link: {found_link}") save_path = self.file_path.replace(".xlsx", "_updated.xlsx") wb.save(save_path) success_popup = Popup(title='Success', content=Label(text=f"File saved: {save_path}"), size_hint=(0.8, 0.3)) success_popup.open() finally: self.driver.quit() if __name__ == '__main__': FileSearchApp().run()