專項練習 · 9 分鐘閱讀

Python robots.txt 練習:規則、延遲與倫理

robots.txt 檔案很小,影響卻很大。這些練習解析常見指令,解釋最長比對優先級,並把檔案放回「禮貌抓取或乾脆不抓」的完整決策中。

解析指令

每個非註解行都是冒號分隔的鍵和值,鍵不區分大小寫。只儲存需要的值,但不要把這個小解析器當成完整的 robots 標準實現。

robots = '''User-agent: *
Disallow: /private
Allow: /private/public
Crawl-delay: 2'''
rules = {}
for line in robots.splitlines():
    line = line.strip()
    if not line or line.startswith("#") or ":" not in line:
        continue
    key, value = line.split(":", 1)
    rules[key.strip().lower()] = value.strip()
print(rules)

鍵、值與註解

採用最長比對規則

Allow 和 Disallow 可能重疊。常見約定是最長比對路徑優先;長度相同時,更具體的規則通常獲勝。不要看到第一行就停止判斷。

rules = [("allow", "/private/public"), ("disallow", "/private")]
path = "/private/public/report"
decision = "allow"
best = -1
for kind, prefix in rules:
    if path.startswith(prefix) and len(prefix) > best:
        decision = kind
        best = len(prefix)
print(decision)

具體規則勝過寬泛規則

把延遲變成時間表

Crawl-delay 是請求間隔提示,不保證伺服器健康。每次請求後記錄時間戳,等到下一個允許時刻。如果站點在其他地方公布了更嚴格的限制,按更嚴格的執行。

from datetime import datetime, timedelta

start = datetime(2026, 1, 1, 12, 0, 0)
delay = 2
times = [start + timedelta(seconds=delay * i) for i in range(3)]
print([t.strftime("%H:%M:%S") for t in times])

有意識地拉開請求

遇到 429 就退讓

429 表示請求過多。有 Retry-After 時讀取它,至少等待那麼久,並降低併發。立刻重試只會讓問題更糟,甚至導致客戶端被封禁。

status = 429
retry_after = "30"
if status == 429:
    wait = int(retry_after)
    print(f"wait {wait} seconds")
else:
    print("continue")

尊重伺服器的回答

少收集,先詢問

頁面出現姓名、郵箱或健康資訊,不代表可以收集。先定義最少欄位,避免儲存身份標識,不需要時刪除原始頁面。登入、驗證碼、付費牆和存取控制是邊界,不是需要繞過的障礙。

record = {"name": "Ada", "email": "ada@example.com", "bio": "Python"}
public = {key: value for key, value in record.items() if key != "email"}
print(public)

儲存前先最小化

你的練習清單

常見問題

robots.txt 有法律約束力嗎?

它是技術約定,不是完整法律協議。站點條款、版權、隱私法和合同可能增加更嚴格的義務。

沒有 robots.txt 就可以隨便抓嗎?

不能自動視為授權。仍要查看條款並保持克制;檔案缺失不是抓取全部內容的邀請。

小任務可以忽略 Crawl-delay 嗎?

不要把任務小當作豁免理由。把延遲當作請求速率上限,伺服器吃力時還要進一步退讓。

練習 robots.txt 規則

12 道題,覆蓋指令、最長比對、延遲、429 處理和隱私。

打開練習

繼續閱讀: