Quay lại blog

Cách khắc phục sự cố cookie thông qua proxy

Cookies thường trở thành nguồn gây ra vấn đề khi làm việc qua proxy. Tìm hiểu lý do tại sao điều này xảy ra và cách cấu hình xử lý chúng một cách chính xác.

📅8 tháng 12, 2025
```html

Cách khắc phục các vấn đề về cookies thông qua proxy

Cookies là một trong những nguồn gốc lỗi phổ biến nhất khi làm việc với proxy. Các phiên bị ngắt, xác thực bị lỗi, dữ liệu bị mất. Trong bài viết này, chúng tôi sẽ tìm hiểu lý do tại sao điều này xảy ra và cách cấu hình đúng cách xử lý cookies để hoạt động ổn định.

Tại sao cookies bị mất khi sử dụng proxy

Khi bạn gửi yêu cầu thông qua proxy, một nút trung gian sẽ xuất hiện giữa máy khách của bạn và máy chủ đích. Điều này tạo ra một số vấn đề:

  • Các địa chỉ IP khác nhau cho một phiên. Máy chủ có thể nhận thấy rằng các yêu cầu đến từ các địa chỉ khác nhau và từ chối cookies như đáng ngờ.
  • Mất các tiêu đề Set-Cookie. Cấu hình proxy không chính xác có thể không truyền các tiêu đề Set-Cookie cho máy khách.
  • Miền và đường dẫn không khớp. Nếu proxy viết lại tiêu đề Host, cookies có thể không được lưu do miền không khớp.
  • Thiếu lưu trữ trạng thái. Nếu bạn gửi từng yêu cầu riêng biệt mà không lưu trữ cookies, phiên sẽ bị mất.

Cookie jar là kho lưu trữ cookies tự động quản lý việc gửi và nhận chúng. Thay vì thêm tiêu đề Cookie vào từng yêu cầu theo cách thủ công, bạn cho phép thư viện thực hiện việc này tự động.

Hầu hết các máy khách HTTP đều có hỗ trợ cookie jar tích hợp:

import requests
from requests.cookies import RequestsCookieJar

# Tạo jar để lưu trữ cookies
jar = RequestsCookieJar()

# Yêu cầu đầu tiên — máy chủ sẽ gửi Set-Cookie
response1 = requests.get(
    'https://example.com/login',
    cookies=jar,
    proxies={'https': 'http://proxy.example.com:8080'}
)

# Cookies được lưu trữ tự động trong jar
print(jar)

# Yêu cầu thứ hai — cookies sẽ được gửi tự động
response2 = requests.get(
    'https://example.com/dashboard',
    cookies=jar,
    proxies={'https': 'http://proxy.example.com:8080'}
)

Nếu không có jar, bạn sẽ phải phân tích cú pháp Set-Cookie theo cách thủ công và thêm chúng vào yêu cầu tiếp theo — điều này không đáng tin cậy và cumbersome.

Lưu trữ cookies giữa các yêu cầu

Nếu tập lệnh của bạn chạy trong thời gian dài hoặc bạn cần khôi phục phiên sau khi khởi động lại, hãy lưu cookies vào tệp:

import requests
from http.cookiejar import LWPCookieJar

# Tạo jar với lưu trữ vào tệp
jar = LWPCookieJar('cookies.txt')

# Tải cookies cũ nếu chúng tồn tại
try:
    jar.load(ignore_discard=True, ignore_expires=True)
except FileNotFoundError:
    pass

# Sử dụng jar trong các yêu cầu
response = requests.get(
    'https://example.com/login',
    cookies=jar,
    proxies={'https': 'http://proxy.example.com:8080'}
)

# Lưu trữ cookies được cập nhật
jar.save(ignore_discard=True, ignore_expires=True)

Các cờ ignore_discard=Trueignore_expires=True cho phép lưu trữ ngay cả các cookies tạm thời.

Các vấn đề với liên kết miền của cookies

Cookies có thuộc tính Domain xác định những miền nào sẽ nhận được chúng. Các vấn đề phát sinh nếu:

  • Proxy viết lại Host. Nếu proxy thay đổi tiêu đề Host, cookie jar có thể từ chối cookie vì nó thuộc về miền khác.
  • Các miền con không khớp. Cookie cho example.com có thể không được gửi đến api.example.com.
  • Đường dẫn không khớp. Cookie cho /api sẽ không được gửi đến /admin.

Kiểm tra các thuộc tính cookie như sau:

import requests

response = requests.get(
    'https://example.com',
    proxies={'https': 'http://proxy.example.com:8080'}
)

# Xuất tất cả các cookies
for cookie in response.cookies:
    print(f"Name: {cookie.name}")
    print(f"Value: {cookie.value}")
    print(f"Domain: {cookie.domain}")
    print(f"Path: {cookie.path}")
    print(f"Secure: {cookie.secure}")
    print(f"HttpOnly: {cookie.has_nonstandard_attr('HttpOnly')}")
    print("---")

Nếu Domain quá hẹp, hãy thử chỉ định cookies một cách rõ ràng thay vì quản lý tự động:

headers = {
    'Cookie': 'session_id=abc123; user_token=xyz789'
}

response = requests.get(
    'https://example.com/api',
    headers=headers,
    proxies={'https': 'http://proxy.example.com:8080'}
)

Các cờ Secure và HttpOnly

Cờ Secure có nghĩa là cookie chỉ được gửi qua HTTPS. Nếu bạn sử dụng proxy HTTP để truy cập tài nguyên HTTPS, hãy đảm bảo rằng kết nối đến proxy được bảo vệ hoặc proxy chuyển tiếp HTTPS một cách chính xác.

Cờ HttpOnly cấm truy cập cookie từ JavaScript. Điều này không ảnh hưởng đến việc gửi cookie trong các yêu cầu, nhưng điều quan trọng cần nhớ là bạn sẽ không thể đọc các cookies như vậy từ trình duyệt.

Khi làm việc với proxy dân cư, hãy đảm bảo rằng:

  • Proxy hỗ trợ HTTPS (phương thức CONNECT)
  • Chứng chỉ hợp lệ (không sử dụng verify=False trong production)
  • Các tiêu đề không được viết lại bởi proxy

Các ví dụ thực tế với mã

Ví dụ 1: Đăng nhập với lưu trữ phiên

import requests
from requests.cookies import RequestsCookieJar

jar = RequestsCookieJar()
proxy = 'http://proxy.example.com:8080'

# Đăng nhập
login_response = requests.post(
    'https://example.com/login',
    data={'username': 'user', 'password': 'pass'},
    cookies=jar,
    proxies={'https': proxy}
)

if login_response.status_code == 200:
    print("Đăng nhập thành công")
    
    # Sử dụng phiên được lưu trữ
    dashboard = requests.get(
        'https://example.com/dashboard',
        cookies=jar,
        proxies={'https': proxy}
    )
    print(dashboard.text)

Ví dụ 2: Xử lý nhiều yêu cầu

import requests
from http.cookiejar import LWPCookieJar
import time

jar = LWPCookieJar('session.txt')
try:
    jar.load(ignore_discard=True)
except:
    pass

proxy = 'http://proxy.example.com:8080'
urls = [
    'https://example.com/page1',
    'https://example.com/page2',
    'https://example.com/page3'
]

for url in urls:
    response = requests.get(
        url,
        cookies=jar,
        proxies={'https': proxy},
        timeout=10
    )
    print(f"{url}: {response.status_code}")
    jar.save(ignore_discard=True)
    time.sleep(1)  # Không quá tải máy chủ

Ví dụ 3: Truyền cookies một cách rõ ràng khi có vấn đề

import requests

proxy = 'http://proxy.example.com:8080'

# Nếu quản lý tự động không hoạt động
cookies_dict = {
    'session_id': 'abc123def456',
    'user_pref': 'dark_mode'
}

headers = {
    'User-Agent': 'Mozilla/5.0...',
    'Cookie': '; '.join([f"{k}={v}" for k, v in cookies_dict.items()])
}

response = requests.get(
    'https://example.com/api/data',
    headers=headers,
    proxies={'https': proxy}
)

print(response.json())

Gỡ lỗi các vấn đề về cookies

Nếu cookies không hoạt động, hãy sử dụng các công cụ này:

Công cụ Mục đích
requests.Session Tự động quản lý cookies cho tất cả các yêu cầu trong phiên
logging Bật DEBUG cho requests để xem tất cả các tiêu đề
Fiddler / Charles Chặn lưu lượng và xem các tiêu đề Set-Cookie và Cookie
curl -v Kiểm tra điều tương tự thông qua proxy từ dòng lệnh

Bật ghi nhật ký để gỡ lỗi:

import logging
import requests

logging.basicConfig(level=logging.DEBUG)

# Bây giờ tất cả các yêu cầu sẽ xuất ra các tiêu đề và cookies
response = requests.get(
    'https://example.com',
    proxies={'https': 'http://proxy.example.com:8080'}
)

Kiểm tra xem proxy có chặn cookies không:

curl -v -x http://proxy.example.com:8080 https://example.com

# Xem các tiêu đề:
# Set-Cookie: ... (nên có)
# Cookie: ... (nên được gửi trong yêu cầu tiếp theo)

Mẹo: Nếu sử dụng proxy dân cư, hãy nhớ rằng chúng có thể xoay vòng IP giữa các yêu cầu. Hãy đảm bảo rằng logic xử lý cookies của bạn tính đến điều này — một số máy chủ từ chối các yêu cầu từ các IP khác nhau trong cùng một phiên.

Tóm tắt

Các vấn đề về cookies khi làm việc thông qua proxy được giải quyết bằng cách cấu hình đúng:

  • Sử dụng cookie jar để quản lý cookies tự động
  • Lưu trữ cookies giữa các yêu cầu vào tệp
  • Kiểm tra liên kết miền và các thuộc tính Path
  • Đảm bảo hỗ trợ HTTPS của proxy
  • Sử dụng gỡ lỗi để xác định các vấn đề

Đối với các tác vụ tự động hóa và phân tích cú pháp, nơi cần hoạt động đáng tin cậy với các phiên thông qua proxy, proxy dân cư với hỗ trợ HTTPS và quản lý cookies là phù hợp. Bắt đầu với cookie jar đơn giản và chuyển sang các lược đồ phức tạp hơn chỉ khi cần thiết.

```