#!/usr/bin/env python3 """Update Google Sheet cho Bánh Chuối bằng cách ghi JSON trực tiếp vào file và đọc từ đó.""" import json import subprocess import sys import os from pathlib import Path SHEET_ID = "1UvQgzLxSVu5dNl_7Z73uTlmpnIk3B0q_isYZHQkjA-c" API_SCRIPT = "/root/.hermes/skills/productivity/google-workspace/scripts/google_api.py" TMP_DIR = Path("/tmp/gsheets_update") TMP_DIR.mkdir(exist_ok=True) def update_sheet(spreadsheet_id, sheet_name, start_range, values): """Cập nhật Google Sheet bằng cách ghi payload vào file .json rồi đọc từ biến env.""" # Ghi payload vào file JSON riêng json_file = TMP_DIR / f"{sheet_name.replace(' ', '_').replace('/', '_')}.json" with open(json_file, 'w', encoding='utf-8') as f: json.dump(values, f, ensure_ascii=False) # Đọc file và encode thành base64 để qua được shell safe import base64 payload_b64 = base64.b64encode(open(json_file, 'rb').read()).decode('ascii') # Tạo temp script để gọi google_api.py mà không cần escaped string tmp_script = TMP_DIR / "run_update.py" with open(tmp_script, 'w', encoding='utf-8') as f: f.write(f''' import base64 import sys import os # Decode payload từ base64 payload_b64 = "{payload_b64}" payload = base64.b64decode(payload_b64).decode('utf-8') # Gọi google_api.py với payload đã decode script_path = "{API_SCRIPT}" spreadsheet_id = "{spreadsheet_id}" sheet_name = "{sheet_name}" start_range = "{start_range}" cmd = [ sys.executable, script_path, "sheets", "update", spreadsheet_id, f"{{sheet_name}}!{{start_range}}", "--values", payload ] print("Running:", " ".join(cmd)) result = subprocess.run(cmd, capture_output=True, text=True) print(result.stdout) if result.returncode != 0: print("ERROR:", result.stderr, file=sys.stderr) sys.exit(1) else: print("SUCCESS") ''') # Chạy script result = subprocess.run([sys.executable, str(tmp_script)], capture_output=True, text=True) if result.returncode == 0: return True, result.stdout.strip() else: return False, result.stderr print("=" * 60) print("CẬP NHẬT GOOGLE SHEET: BÁNH CHUỐI - PHÂN TÍCH CHI PHÍ") print("=" * 60) print(f"Spreadsheet ID: {SHEET_ID}") print(f"URL: https://docs.google.com/spreadsheets/d/{SHEET_ID}/edit") print("=" * 60) # Dữ liệu Tab 2: Tính Giá Thành tab2_data = [ ["Hạng mục", "Chi tiết", "Chi phí / mẻ (VNĐ)", "Ghi chú"], ["Tổng Raw Cost Nguyên Liệu", "Tổng từ tab NGUYÊN LIỆU", "=SUM('Nguyên Liệu'!E2:E13)", "Tự động lấy tổng từ tab 1"], ["Bao bì & Tem nhãn", "Khay giấy nướng + Túi kính + Tem", 12000, "Tính cho 8 bánh/mẻ (1.500đ/bộ)"], ["Điện nướng bánh", "Lò nướng 1500W hoạt động trong 45 phút", 3000, "Ước tính tiêu thụ điện"], ["Hao hụt & Dọn dẹp", "Khấu hao dụng cụ, nước rửa", 1500, "5% trên Raw Cost nguyên liệu"], ["TỔNG CHI PHÍ 1 MẺ", "Raw Cost + Bao bì + Vận hành", "=SUM(C2:C5)", "Giá thành sản xuất thực tế của 1 mẻ"], ["Số lượng bánh thành phẩm / mẻ", "Khuôn bánh chuối nhỏ", 8, "Ước tính chia được 8 ổ nhỏ hoặc 8 slice"], ["GIÁ THÀNH ĐƠN VỊ (COST/BÁNH)", "Chi phí sản xuất cho 1 ổ bánh", "=C6/C7", "Đây là giá thành tối thiểu chưa có công và lời"] ] # Dữ liệu Tab 3: Đề Xuất Giá Bán tab3_data = [ ["MỨC MARKUP", "Công thức tính", "% Markup trên cost", "Giá bán / bánh (VNĐ)", "Lợi nhuận / bánh (VNĐ)"], ["Markup Thấp", "=C2*2", "50%", "=ROUND(C2*1.5,-2)", "=D2-C2"], ["Markup Trung Bình", "=C2*3", "100%", "=ROUND(C2*2,-2)", "=D3-C3"], ["Markup Cao", "=C2*4", "150%", "=ROUND(C2*2.5,-2)", "=D4-C4"], ["Giá bán thị trường tham khảo", "", "", "", ""], ["Bánh chuối lò than truyền thống", "", "", "", "8.000 - 15.000"], ["Bánh chuối cao cấp tại cafe/tiệm bánh", "", "", "", "20.000 - 35.000"], ["Bánh chuối online đóng hộp đẹp", "", "", "", "15.000 - 25.000"], ["", "", "", "", ""], ["KHUYẾN NGHỊ GIÁ BÁN", "", "", "", ""], ["Giá bán đề xuất", "(Trung bình giữa Markup TB và tham khảo online)", "", "15.000 - 25.000", "Tùy vào bao bì, vị trí và khách hàng"] ] success_count = 0 for name, data in [("Tính Giá Thành", tab2_data), ("Đề Xuất Giá Bán", tab3_data)]: range_addr = f"A1:D{len(data)}" if name == "Tính Giá Thành" else f"A1:E{len(data)}" print(f"\n[Bước 1/2] Cập nhật tab '{name}'...") ok, msg = update_sheet(SHEET_ID, name, range_addr, data) if ok: print(f"✓ Thành công!") success_count += 1 else: print(f"✗ Lỗi: {msg[:200]}") print("\n" + "=" * 60) if success_count == 2: print("HOÀN TẤT! Đã cập nhật cả 2 tabs.") else: print(f"Cảnh báo: Chỉ cập nhật thành công {success_count}/2 tabs.") print(f"\nXem kết quả tại:") print(f"https://docs.google.com/spreadsheets/d/{SHEET_ID}/edit") print("=" * 60)