iT邦幫忙

2025 iThome 鐵人賽

DAY 17
0
自我挑戰組

一路side project - 學習筆記系列 第 17

[Day 17] [學習筆記] - n8n - API - Postgres (成功一小步 )

  • 分享至 

  • xImage
  •  

終於成功了qq 先來說明一下我的架構,再整理到底遇到了什麼問題。


架構概述

爬蟲與資料處理層

scraper

  • 負責爬取 GU 商品資料,並將結果存儲為 CSV 或直接傳遞給後續流程。
  • 使用 Python 實現,包含爬蟲邏輯(gu_scraper.py)與資料清理(refined.py)。
  • 內部服務,不對外開放。

n8n

  • 作為自動化排程工具,定時觸發爬蟲並將資料寫入主資料庫(db_primary)。
  • 提供流程管理,易於擴展其他自動化任務。

資料存儲層

db_primary

  • 主資料庫,負責接收爬蟲與其他內部服務的寫入。
  • 配置了 WAL(Write-Ahead Logging),支援資料同步。
  • 僅供內部服務使用,避免直接暴露給外部。

db_read

  • 唯讀資料庫,通過同步機制從主資料庫獲取資料。
  • 提供給對外查詢的 API 使用,確保主資料庫的安全性與穩定性。

API 層

ingest

  • 負責內部資料寫入的 API,將資料從爬蟲或其他來源寫入主資料庫。
  • 僅供內部服務使用,確保資料寫入流程的安全性。

read_api

  • 對外查詢 API,僅連接唯讀資料庫(db_read)。
  • 提供查詢功能,並可加入速率限制、驗證等安全機制。
  • 開放 8080 埠供外部訪問。

資料流與運作流程

資料流

  • scraper 爬取資料,並將結果存儲或傳遞給 ingest。
  • ingest 將資料寫入主資料庫(db_primary)。
  • 主資料庫通過同步機制將資料傳遞給唯讀資料庫(db_read)。
  • 外部用戶通過 read_api 查詢唯讀資料庫中的資料。

運作流程

  • n8n 定時觸發爬蟲,執行資料抓取。
  • 爬蟲完成後,資料經由 ingest 寫入主資料庫。
  • 主資料庫同步資料至唯讀資料庫。
  • 外部用戶通過 read_api 查詢資料。

我遇到的坑

除了2、3、4 是n8n的問題,其他都是docker設定、權限的問題。

1) ModuleNotFoundError: No module named 'psycopg'

原因:ingest imgae 沒裝 PostgreSQL 驅動
修正:新增 requirements.txt(含 psycopg[binary])與 Dockerfile,
pip install -r requirements.txt;重建容器。

requirements.txt

fastapi==0.115.0
uvicorn[standard]==0.30.6
psycopg[binary]==3.2.1
python-dotenv==1.0.1

2) 404 Not Found,n8n 拿取路徑變成 //ingest/price-points/bulk/ingest/price-points/bulk/... (路徑重複出現)

原因:n8n 的 HTTP 節點把 Base URL / URL / Path 拼了好幾次。
修正:只用一個欄位:
URL = http://ingest_api:8000/ingest/price-points/bulk
其他不要再拼路徑;必要時加一個 middleware log 確認 REQ POST /ingest/price-points/bulk。

3) Idempotency-Key 是 undefined

原因:我的 n8n 版本沒有 $uuid() helper
修正:改用表達式
{{ (Date.now().toString(36) + '-' + Math.random().toString(36).slice(2)) }}

4) n8n 發送陣列 Body,DB 仍然沒資料

原因:n8n 的「Using JSON」有時不會正確送出頂層就是陣列的 body

修正:改用 RAW body:{{ JSON.stringify($json.payload) }}
並設 Content-Type:application/json。
https://ithelp.ithome.com.tw/upload/images/20250930/201547642BZnDUF8MV.png

5) permission denied for table products

原因:ingest_user 沒有對 prod.products 的 INSERT/UPDATE/SELECT 權限。

修正:在主庫授權:
GRANT USAGE ON SCHEMA prod TO ingest_user;
GRANT INSERT,UPDATE,SELECT ON prod.products TO ingest_user;
GRANT INSERT,SELECT ON prod.price_points TO ingest_user;
(序列權限另見下一條)

6) permission denied for sequence products_id_seq

原因:插入 products 會讀取自增序列,sequence 權限獨立於表

修正:
GRANT USAGE, SELECT ON ALL SEQUENCES IN SCHEMA prod TO ingest_user;
並加
ALTER DEFAULT PRIVILEGES IN SCHEMA prod GRANT USAGE, SELECT ON SEQUENCES TO ingest_user;

7) permission denied for table product_stats(由 trigger 引發)

原因:prod.trg_after_pp_ins() 觸發器會呼叫 prod.recompute_product_stats() 去 INSERT/UPDATE prod.product_stats;觸發器以 ingest_user 身分執行,但它沒權限。

修正:補權限:
GRANT INSERT,UPDATE,SELECT ON prod.product_stats TO ingest_user;
GRANT EXECUTE ON FUNCTION prod.recompute_product_stats(bigint) TO ingest_user;


進入ingest看log ,終於看到 200 了 !!

docker compose logs -f ingest

https://ithelp.ithome.com.tw/upload/images/20250930/20154764u51YB4xl5T.png

https://ithelp.ithome.com.tw/upload/images/20250930/20154764rp6KCXDcyZ.png

主要來說在全限那搞了一段時間,希望是不要再改了 ̿̿ ̿̿ ̿'̿’\̵͇̿̿\з=( ͠° ͟ʖ ͡°)=ε/̵͇̿̿/‘̿̿ ̿ ̿ ̿ ̿ ̿


上一篇
[Day 16] [學習筆記] - Postgres資料庫架設、使用 (失敗_今日進度0 )
系列文
一路side project - 學習筆記17
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言