diff --git a/backend/media_plan_processor.py b/backend/media_plan_processor.py index d0930e1..976c833 100644 --- a/backend/media_plan_processor.py +++ b/backend/media_plan_processor.py @@ -89,7 +89,9 @@ def parse_media_plan(excel_path: str) -> Dict: """ import openpyxl - wb = openpyxl.load_workbook(excel_path, data_only=True) + # read_only=True skips pivot-cache deserialization, which hangs this loader + # on workbooks with pivot tables (Amazon media plans use them extensively). + wb = openpyxl.load_workbook(excel_path, data_only=True, read_only=True) all_assets = [] channel_counts = {} @@ -106,7 +108,9 @@ def parse_media_plan(excel_path: str) -> Dict: continue ws = wb[sheet_name] - if ws.max_row < 2: + # In read_only mode max_row may be None until dimensions are read; treat + # that as "has data" and let iter_rows decide. + if ws.max_row is not None and ws.max_row < 2: continue # Get header row (row 1)