Cara Menghubungkan DuckDB ke Google Sheets
Kueri data Google Sheets dengan DuckDB SQL menggunakan Python dan Sheets API. Jalankan join, agregasi, dan GROUP BY pada data spreadsheet langsung dalam kurang dari 50 baris kode.
Google Sheets adalah tempat data Anda berada. DuckDB adalah tempat analisis SQL serius terjadi. Panduan ini menghubungkan keduanya - sehingga Anda dapat menjalankan GROUP BY, fungsi jendela, dan join multi-tabel terhadap data spreadsheet langsung, lalu menulis hasilnya kembali ke lembar baru. Pada akhirnya, Anda akan memiliki skrip Python yang berfungsi yang membaca dari Sheets ke instans DuckDB dalam memori, menguerinya, dan mendorong hasil kembali.
Yang Anda Perlukan
- Python 3.9+ terinstal secara lokal
- Proyek Google Cloud dengan Sheets API yang diaktifkan
- Akun Layanan Google dengan file kredensial JSON yang diunduh
- Keakraban dasar dengan SQL dan menjalankan skrip Python dari terminal
- Google Sheet dengan data tabel (header kolom di baris 1)
Panduan Langkah demi Langkah
Instal Dependensi Python
Instal 3 paket yang dibutuhkan pipeline ini: duckdb untuk mesin SQL, gspread untuk pembungkus Sheets API, dan google-auth untuk autentikasi akun layanan. bash pip install duckdb gspread google-auth
duckdb0.10+ disarankan - versi sebelumnya kurang beberapa peningkatan parsing CSVgspread6.x mengubah API autentikasinya; konfirmasi Anda berada di 6.x denganpip show gspreadgoogle-authmenangani penyegaran token OAuth secara otomatis - Anda tidak perlu mengelola token secara manual
Pro Tip
Gunakan lingkungan virtual (python -m venv venv && source venv/bin/activate) untuk menjaga dependensi ini terisolasi dari Python sistem Anda.Buat Akun Layanan Google
Akun layanan memungkinkan skrip Anda untuk mengautentikasi sebagai identitas non-manusia yang dapat membaca dan menulis spreadsheet tanpa interaksi pengguna - penting untuk skrip yang berjalan pada jadwal atau server.
- Buka Google Cloud Console → IAM & Admin → Service Accounts
- Klik Create Service Account, beri nama seperti
duckdb-sheets-connector - Lewati penugasan peran IAM opsional - izin dikendalikan di tingkat spreadsheet
- Di bawah tab Keys akun layanan, klik Add Key → Create new key → JSON
- Simpan file
.jsonyang diunduh sebagaicredentials.jsondi direktori proyek Anda
Pro Tip
Jangan pernah commitcredentials.json ke repositori git. Tambahkan ke .gitignore segera.Bagikan Spreadsheet Anda dengan Akun Layanan
Akun layanan memiliki alamat email (terlihat di file JSON di bawah client_email, format: [email protected]). Google Sheets memperlakukannya seperti pengguna lain mana pun.
- Buka spreadsheet yang ingin Anda kueri
- Klik Share, tempel alamat email akun layanan
- Berikan akses Editor (diperlukan jika Anda ingin menulis hasil kembali; Viewer bekerja untuk read-only)
- Salin ID spreadsheet dari URL - ini adalah string panjang antara
/d/dan/edit
Muat Data Sheets ke DuckDB
Google Sheets mengembalikan data sebagai array 2D string. Kode di bawah mengambil lembar kerja bernama, mengonversinya menjadi daftar dict menggunakan baris pertama sebagai header, kemudian mendaftarkannya sebagai relasi DuckDB. python import duckdb import gspread from google.oauth2.service_account import Credentials SCOPES = ["https://www.googleapis.com/auth/spreadsheets"] SPREADSHEET_ID = "your-spreadsheet-id-here" WORKSHEET_NAME = "Sheet1" # Autentikasi dan buka spreadsheet creds = Credentials.from_service_account_file("credentials.json", scopes=SCOPES) gc = gspread.authorize(creds) sheet = gc.open_by_key(SPREADSHEET_ID).worksheet(WORKSHEET_NAME) # Ambil semua record sebagai daftar dict records = sheet.get_all_records() # Menggunakan baris 1 sebagai header kolom secara otomatis # Muat ke DuckDB con = duckdb.connect() con.register("sheet_data", duckdb.from_arrow( __import__("pyarrow").Table.from_pylist(records) ))
get_all_records()mengembalikan setiap baris sebagai dict - spreadsheet 1.000 baris membutuhkan kurang lebih 300ms melalui APIregister()DuckDB membuat data dapat dikueri tanpa menyalinnya ke disk- Jenis kolom disimpulkan dari data; string yang terlihat numerik menjadi
DOUBLEsecara otomatis
Pro Tip
Untuk spreadsheet dengan lebih dari 5.000 baris, pertimbangkan pengelompokan dengansheet.get('A1:Z5000') dan sheet.get('A5001:Z10000') untuk tetap dalam batas ukuran per-permintaan Sheets API.Jalankan Kueri SQL Terhadap Data Sheets Anda
Setelah data didaftarkan, Anda menulis SQL standar. DuckDB mendukung fungsi jendela, CTE, join LATERAL, dan sebagian besar sintaks yang kompatibel dengan PostgreSQL - tidak ada yang ada dalam formula Sheets. python # Contoh agregasi: total pendapatan menurut wilayah result = con.execute(""" SELECT region, COUNT(*) AS deal_count, SUM(CAST(revenue AS DOUBLE)) AS total_revenue, AVG(CAST(revenue AS DOUBLE)) AS avg_deal_size FROM sheet_data WHERE status = 'Closed Won' GROUP BY region ORDER BY total_revenue DESC """).fetchdf() print(result)
- DuckDB memproses 10 juta baris dalam waktu kurang dari 2 detik di laptop - jauh lebih cepat daripada tabel pivot pada data yang sama
fetchdf()mengembalikan DataFrame pandas; gunakanfetchall()untuk daftar tuples biasa- Kolom string dari Sheets sering memerlukan
CASTeksplisit - Sheets tidak memberlakukan jenis, jadirevenuemungkin tiba sebagai"$12,000"daripada12000
Pro Tip
Bersihkan data Sheets kotor dalam SQL menggunakanREPLACE(REPLACE(revenue, '$', ''), ',', '') sebelum casting. Lebih mudah daripada membersihkannya di spreadsheet itu sendiri.Tulis Hasil Kueri Kembali ke Google Sheets
Setelah menjalankan analisis Anda, dorong DataFrame hasil kembali ke lembar kerja baru atau yang ada. Pola di bawah menghapus spreadsheet target dan menulis ulangnya sepenuhnya - andal untuk pekerjaan terjadwal, meskipun tidak ideal untuk spreadsheet yang sedang aktif diedit orang. python # Buat atau bersihkan lembar kerja output try: output_sheet = gc.open_by_key(SPREADSHEET_ID).worksheet("DuckDB Output") output_sheet.clear() except gspread.exceptions.WorksheetNotFound: output_sheet = gc.open_by_key(SPREADSHEET_ID).add_worksheet( title="DuckDB Output", rows=1000, cols=20 ) # Tulis header + data headers = result.columns.tolist() rows = result.fillna("").values.tolist() output_sheet.update([headers] + rows)
update()menerima daftar 2D dan menulisnya dimulai dari A1fillna("")mengubah NaN menjadi string kosong - Sheets API menolak tipeNaNPython- Kuota Sheets API adalah 300 permintaan penulisan per menit per proyek; untuk set hasil besar, gunakan
batch_update()sebagai gantinya
Otomatisasi Pipeline
Skrip satu kali berguna. Skrip yang terjadwal adalah pipeline data. Bungkus logika dalam fungsi dan jalankan pada jadwal cron untuk menjaga spreadsheet output Anda tetap segar. python import schedule import time def refresh_analysis(): records = sheet.get_all_records() con.register("sheet_data", duckdb.from_arrow( __import__("pyarrow").Table.from_pylist(records) )) result = con.execute(""" SELECT region, SUM(revenue) as total FROM sheet_data GROUP BY region """).fetchdf() output_sheet.clear() output_sheet.update([result.columns.tolist()] + result.fillna("").values.tolist()) print(f"Diperbarui pada {__import__('datetime').datetime.now()}") schedule.every(30).minutes.do(refresh_analysis) while True: schedule.run_pending() time.sleep(60)
- Jalankan ini pada VM kecil (instans $5/bulan menangani ini dengan mudah) untuk menjaga dasbor Sheets Anda tetap aktif
- Menurut dokumentasi Sheets API Google, permintaan baca dibatasi pada 300 per menit per proyek - interval penyegaran 30 menit membuat Anda tetap dalam batas kuota
- Untuk penggunaan produksi, tambahkan penanganan kesalahan di sekitar panggilan API dan catat kegagalan di spreadsheet pemantauan terpisah
Pro Tip
Simpan ID spreadsheet dan nama lembar kerja dalam variabel lingkungan (os.environ.get("SPREADSHEET_ID")) daripada mengeraskannya. Membuat skrip dapat digunakan kembali di seluruh proyek.Kesimpulan
Anda telah menghubungkan DuckDB ke Google Sheets: mengambil data langsung melalui Sheets API, memuatnya ke instans DuckDB dalam memori, menjalankan SQL yang tidak dapat disentuh formula Sheets, dan menulis hasil kembali. Pola yang sama diskalakan ke beberapa lembar kerja, join lintas lembar, dan pipeline terjadwal yang membuat tab pelaporan tetap terkini tanpa ekspor manual apa pun.\n\nGesekan yang terbuka ini nyata: setiap kali spreadsheet sumber Anda mengubah skema (seseorang mengganti nama kolom, menambah tab), SQL Anda rusak diam-diam. Itulah celah antara analisis ad hoc dan pipeline data yang tepat. Jika Anda mengatasi masalah itu berulang kali di seluruh model kompleks, ada baiknya melihat ModelMonkey - ini menjaga lapisan kueri DuckDB di dalam Sheets tempat kolaborator Anda dapat melihat apa yang sedang berjalan.
Pertanyaan Umum
Apakah saya perlu menerbitkan Google Sheet saya ke web untuk menguerinya dengan DuckDB?
Tidak. Pendekatan akun layanan mengautentikasi melalui OAuth - spreadsheet Anda tetap pribadi dan dibagikan hanya dengan email akun layanan. Penerbitan ke web hanya diperlukan jika Anda menggunakan fungsi read_csv DuckDB untuk mengambil URL ekspor publik secara langsung, yang melewati autentikasi sepenuhnya tetapi mengekspos data Anda secara publik.
Berapa banyak baris yang dapat ditangani DuckDB dari Google Sheets?
DuckDB sendiri menangani ratusan juta baris dalam memori (dibatasi oleh RAM, bukan DuckDB). Kemacetan praktis adalah Sheets API: get_all_records() pada spreadsheet 50.000 baris membutuhkan 3-8 detik dan mencapai batas muatan. Dokumentasi Google sendiri mencatat bahwa Sheets membatasi 10 juta sel per spreadsheet. Untuk spreadsheet di atas ~20.000 baris, kelompokkan panggilan get() Anda atau ekspor ke CSV terlebih dahulu, kemudian gunakan duckdb.read_csv() secara langsung.
Bisakah saya menggabungkan data dari dua Google Sheets berbeda dalam satu kueri DuckDB?
Ya. Ambil setiap spreadsheet ke dalam daftar dict terpisah, daftarkan masing-masing sebagai relasi DuckDB berbeda (con.register("orders", ...), con.register("customers", ...)), lalu gabungkan dengan SQL standar. DuckDB menangani join dalam memori - tidak ada server database yang diperlukan.
Apa yang terjadi jika kolom di spreadsheet saya memiliki jenis campuran (beberapa sel angka, beberapa teks)?
DuckDB menyimpulkan jenis kolom dari sampel data. Jika kolom memiliki jenis campuran, itu default ke VARCHAR. Anda perlu cast secara eksplisit dalam SQL Anda: CAST(TRY_CAST(revenue AS DOUBLE) AS DOUBLE). Varian TRY_CAST mengembalikan NULL alih-alih mengeluarkan kesalahan pada nilai yang tidak dapat dikonversi, yang lebih aman untuk data Sheets yang berantakan.
Apakah ada cara untuk mengueri Google Sheets dengan DuckDB tanpa Python?
Fungsi read_csv DuckDB dapat mengambil URL CSV publik apa pun secara langsung: SELECT * FROM read_csv('https://docs.google.com/spreadsheets/d/{ID}/export?format=csv'). Ini memerlukan spreadsheet dipublikasikan atau dibagikan secara publik. Untuk spreadsheet pribadi, Python dengan akun layanan adalah satu-satunya jalah yang didukung per Maret 2026.