Trình phân tích đã hoạt động được nửa năm, và hôm nay cơ sở dữ liệu đã ghi lại những dòng trống. Ý nghĩ đầu tiên - bị cấm, cần phải thay đổi proxy. Bạn thay đổi pool, nâng cao chất lượng IP, trả tiền cho các địa chỉ IP dân cư thay vì từ trung tâm dữ liệu - nhưng các trường vẫn trống rỗng. Bởi vì nguyên nhân không phải do việc bị chặn: trang web đã chuyển sang bố cục mới, và bộ chọn CSS của bạn không còn gắn liền với bất kỳ thứ gì.
Đây là loại hỏng hóc đắt giá nhất, vì nó im lặng. Việc bị cấm có thể thấy ngay: 403, captcha, chuyển hướng. Sự trôi dạt của bố cục không làm rơi bất cứ thứ gì - HTTP 200, trang đã được nhận, lưu lượng đã được thanh toán, nhưng đầu ra là None. Hãy cùng tìm hiểu cách phân biệt một cái với cái khác trong vòng năm phút và cách ngừng việc viết lại các bộ chọn bằng tay sau mỗi lần thiết kế lại.
Ai cần điều này
Hướng dẫn dành cho những ai giữ trình phân tích trong sản xuất lâu hơn một sprint: giám sát giá cả của đối thủ, thu thập đánh giá, tổng hợp việc làm, xuất dữ liệu hàng ngày cho phân tích. Nếu bạn chỉ chạy kịch bản một lần và vứt bỏ - sự trôi dạt của bố cục không liên quan đến bạn. Nếu kịch bản chạy theo cron trong nhiều tháng, đây là khoản chi phí chính của bạn cho việc hỗ trợ.
Quy mô của vấn đề không phải là tưởng tượng. Theo ước tính của các nhà phân tích GroupBWT, những thay đổi cấu trúc không thể kiểm soát của các trang web tạo ra khoảng 40–60% chi phí lặp lại cho việc hỗ trợ các trình thu thập dữ liệu trong các dự án lớn. Trong một số ngành, 10–15% trình thu thập dữ liệu cần sửa chữa hàng tuần - do sự dịch chuyển DOM, fingerprinting và throttling của các điểm cuối. Điều này có nghĩa là việc sửa chữa các bộ chọn cạnh tranh về chi phí với việc vượt qua chống bot, nhưng lại nhận được ít sự chú ý hơn nhiều.
Tình hình không mấy khả quan: trong báo cáo của Apify "Tình trạng thu thập dữ liệu web 2026", 65,8% người tham gia đã tăng cường sử dụng proxy, 58,3% ghi nhận sự gia tăng chi phí cho proxy theo năm, và hơn 62% - sự gia tăng tổng chi phí cơ sở hạ tầng, chủ yếu do sự bảo vệ chống bot ngày càng tăng. Trong bối cảnh này, việc đốt cháy lưu lượng đã thanh toán trên các trang mà bạn vẫn không thu thập được gì - thật đáng tiếc gấp đôi.
Bước 1. Phân biệt việc bị cấm với sự trôi dạt của bố cục
Chẩn đoán mất vài phút và phải thực hiện theo thứ tự - nếu không sẽ dễ dàng "sửa chữa" nhầm lỗi.
- Xem mã phản hồi và kích thước của nội dung. 403, 429, 503, chuyển hướng đến trang kiểm tra hoặc nội dung từ 2–5 KB - đó là chống bot. HTTP 200 và trang đầy đủ từ 200–800 KB - trang web đã cho phép bạn, không phải vấn đề với proxy.
- Lưu HTML thô vào đĩa và mở bằng mắt. Không phải trong trình gỡ lỗi, mà trong trình duyệt. Nếu sản phẩm/đánh giá/giá cả vẫn ở đó, nhưng trình phân tích không thấy - đó là sự trôi dạt của bố cục.
- Tìm văn bản cần thiết bằng cách tìm kiếm trong tệp. Có trong HTML, nhưng không thể truy cập qua bộ chọn của bạn - định dạng đã thay đổi. Không có gì cả - nội dung được tải bởi kịch bản, cần một động cơ trình duyệt, không phải yêu cầu HTTP.
- So sánh với lần xuất dữ liệu thành công trước đó. So sánh HTML cũ và mới của cùng một URL: thường thì ngay lập tức có thể thấy lớp bao bọc mới, khối đã chuyển hoặc thay thế
idbằngdata-*. - Kiểm tra xem trang web có trả về phiên bản khác của trang không. Về điều này - sẽ được đề cập riêng bên dưới, vì ở đây proxy vẫn có liên quan.
Nếu sau điểm thứ ba, chẩn đoán là "định dạng đã bị lệch", thì việc thay đổi proxy là vô nghĩa. Cần một trình phân tích có khả năng tìm thấy phần tử, ngay cả khi bộ chọn đã hết hạn.
Bước 2. Bộ chọn thích ứng là gì
Ý tưởng rất đơn giản: thay vì gắn chặt vào chuỗi .product-card > h3.title, thư viện sẽ ghi nhớ "chân dung" của phần tử cần thiết một lần, và khi chạy lại lần sau sẽ tìm phần tử giống nhất với chân dung này trên trang.
Cách thực hiện thực tế nhất là trong Scrapling - một framework Python mã nguồn mở của Karim Shoair. Dự án được phát hành vào tháng 10 năm 2024 và đến tháng 9 năm 2026 đã thu thập được hơn 78.000 sao trên GitHub; phiên bản mới nhất tại thời điểm viết bài - v0.4.15 từ ngày 23 tháng 8 năm 2026, các commit diễn ra hàng ngày. Cần Python 3.10+.
Cơ chế tìm kiếm thích ứng được thiết lập như sau. Khi bạn gọi bộ chọn với auto_save=True, Scrapling sẽ lưu lại dấu vân tay của phần tử:
- tên thẻ, văn bản và tất cả các thuộc tính với giá trị của chúng;
- tên thẻ của các phần tử lân cận;
- đường dẫn đến phần tử - chỉ theo tên thẻ;
- thẻ, thuộc tính và văn bản của phần tử cha.
Dấu vân tay được lưu vào cơ sở dữ liệu SQLite cục bộ và được khóa bằng cặp "miền + định danh". Miền được lấy từ URL của trang (hoặc được chỉ định bằng tham số adaptive_domain), định danh mặc định là chính chuỗi bộ chọn - hoặc của riêng bạn, nếu truyền identifier=.
Khi bố cục thay đổi và bộ chọn thông thường trả về giá trị trống, việc gọi với adaptive=True sẽ nâng dấu vân tay đã lưu và chạy qua tất cả các phần tử trên trang, tính toán độ tương đồng mờ - cho đến thứ tự của các thuộc tính. Phần tử có độ tương đồng cao nhất sẽ được trả về.
Điều này có giá rất rẻ. Theo các tiêu chuẩn chính thức của dự án, việc phân tích mất 1,99 ms so với 2,01 ms của Parsel/Scrapy, 22,93 ms của PyQuery, 80,57 ms của Selectolax và 1541 ms của BeautifulSoup với lxml. Việc tìm kiếm thích ứng phần tử tương tự - 2,46 ms so với 13,3 ms của AutoScraper. Điều này có nghĩa là việc bảo hiểm chống lại việc thiết kế lại chỉ thêm vào yêu cầu khoảng hai mili giây trên nền độ trễ mạng hàng trăm mili giây.
Bước 3. Cài đặt và kích hoạt
Việc cài đặt phụ thuộc vào việc bạn có cần trình duyệt hay không:
pip install scrapling- chỉ trình phân tích, không có phần mạng. Đủ nếu bạn nhận được HTML bằng mã của mình.pip install "scrapling[fetchers]", sau đóscrapling install- thêm các bộ lấy và tải xuống trình duyệt cùng với các phụ thuộc.- Thêm:
[ai]- máy chủ MCP,[rag]- bọc cho RAG,[shell]- bảng điều khiển tương tác,[all]- tất cả ngay lập tức. Có hình ảnh sẵn cópyd4vinci/scrapling.
Tiếp theo - hai lần chạy. Lần đầu trên bố cục làm việc thực tế sẽ lưu dấu vân tay, lần thứ hai đã có khả năng sống sót sau việc thiết kế lại:
- Chạy mẫu. Tạo một đối tượng
Selectorvớiadaptive=Truevà nhất định phải truyềnurl- nếu không miền sẽ chuyển vào khóa"default", và các dấu vân tay của các trang web khác nhau sẽ bị trộn lẫn. Gọi bộ chọn cần thiết vớiauto_save=True. - Chạy thực tế. Cùng bộ chọn đó, nhưng với
adaptive=True. Khi định dạng còn nguyên vẹn, nó sẽ hoạt động theo cách thông thường. Khi bị hỏng - sẽ kích hoạt tìm kiếm theo độ tương đồng. - Ghi lại các sự khác biệt. Khoảnh khắc mà bộ chọn thông thường trả về giá trị trống, trong khi bộ chọn thích ứng tìm thấy điều gì đó - đó là tín hiệu "trang web đã chuyển", cần phải thấy trong giám sát, không phải nuốt chửng một cách im lặng.
Một chi tiết quan trọng về việc ghi đè: việc lưu không tích lũy. Việc auto_save lặp lại cho cùng một cặp "miền + định danh" sẽ ghi đè dấu vân tay trước đó. Do đó, mẫu được chụp trên một trang rõ ràng, không phải trong vòng lặp trên toàn bộ pool URL.
Bước 4. Proxy: chúng thực sự liên quan như thế nào
Chúng ta đã bắt đầu với việc sự trôi dạt của bố cục không liên quan đến proxy. Điều này đúng một nửa, và nửa còn lại thì tốn kém.
Trang web có thể trả lại cho bạn định dạng khác do sự ra đi của proxy. Địa phương, ngôn ngữ và quốc gia thay đổi mẫu của trang: thứ tự của các khối khác nhau, các lớp khác nhau, các định dạng giá cả và ngày tháng khác nhau. Đây không phải là giả thuyết - trong chính Scrapling có một sửa chữa điển hình: trong phiên bản 0.4.12, StealthyFetcher đã loại bỏ địa phương bắt buộc en-US, vì địa phương bị áp đặt không khớp với địa lý thực tế và làm hỏng hành vi. Từ đó, quy tắc làm việc: hãy chụp dấu vân tay mẫu từ cùng một địa lý mà bạn sau đó thu thập dữ liệu. Dấu vân tay được chụp qua IP của Đức sẽ khó khớp hơn với trang nhận được qua IP của Brazil - và bạn sẽ nhận được báo động sai "trang web đã thay đổi bố cục".
Hệ quả thực tiễn:
- Nếu pool đa quốc gia - hãy phân chia các dấu vân tay qua
adaptive_domain, chỉ định khóa dạng "miền + quốc gia". Nếu không, một bản ghi trong SQLite sẽ liên tục bị ghi đè bởi các phiên bản từ các địa lý khác nhau. - Đối với các kịch bản dài, hãy giữ một quốc gia và một phiên cho toàn bộ nhiệm vụ. Cách thực hiện điều này được giải thích chi tiết trong tài liệu về các phiên dính và khi nào nên sử dụng chúng.
- Các thử nghiệm A/B và triển khai dần dần cung cấp đồng thời hai bố cục sống trên cùng một miền. Ở đây, tìm kiếm thích ứng đặc biệt hữu ích: nó sẽ lấy phần tử từ cả hai nhánh, trong khi bộ chọn cứng sẽ ngẫu nhiên trả về giá trị trống trong một nửa số yêu cầu.
Có thể chỉ định proxy trong Scrapling trên tất cả các cấp độ. Đối với các yêu cầu HTTP nhanh, Fetcher và AsyncFetcher có tham số proxies. Đối với các phiên, có ProxyRotator, nhận danh sách địa chỉ - nó được đưa vào FetcherSession. Các phiên trình duyệt DynamicSession và StealthySession nhận proxy ở cấp độ phiên, để IP không thay đổi giữa các kịch bản.
Thêm một điều nữa, tiết kiệm cả pool và thần kinh, đã xuất hiện trong phiên bản 0.4.12 - AutoThrottle: thư viện tự điều chỉnh thời gian giữa các yêu cầu theo phản hồi của máy chủ, gấp đôi độ trễ khi bị chặn và tôn trọng tiêu đề Retry-After. Đây chính là hành vi mà phân biệt việc thu thập cẩn thận với việc gia tăng các lệnh cấm bằng các lần thử ngây thơ.
Các cạm bẫy
- Không commit SQLite với các dấu vân tay vào git. Tài liệu đã cảnh báo điều này rõ ràng. Đồng thời, không sử dụng
auto_savetrên các trang có dữ liệu cá nhân - văn bản và thuộc tính của phần tử sẽ được đưa vào dấu vân tay. - Tìm kiếm thích ứng không phải là sự thay thế cho việc giám sát. Nó sẽ trả về phần tử "giống nhất", nhưng phần tử giống nhất không phải lúc nào cũng đúng. Nếu trang web đã hoán đổi giá với giảm giá và giá không giảm, độ tương đồng cao, nhưng dữ liệu không chính xác. Hãy giữ kiểm tra trên phạm vi giá trị và tỷ lệ các trường trống trong xuất dữ liệu.
- Hỏng hóc im lặng đắt hơn hỏng hóc ồn ào. Trong khi bộ chọn im lặng trả về None, pipeline vẫn tiếp tục đi qua các trang và đốt cháy lưu lượng đã thanh toán. Về chi phí thực sự của một gigabyte mà không thu thập được dữ liệu, có một phân tích riêng - tại sao giá proxy cho GB lại sai.
- Dấu vân tay sẽ cũ đi. Sau khi xác nhận việc thiết kế lại, hãy chụp lại mẫu một lần nữa, nếu không lần sửa đổi tiếp theo của trang web sẽ được coi là từ chân dung đã lỗi thời, và độ chính xác sẽ giảm.
- Nếu không có nội dung trong HTML - tính thích ứng sẽ không giúp ích gì, cần một bộ lấy từ trình duyệt. Trong phiên bản 0.4.15, các tab của trình duyệt đã được tái sử dụng giữa các yêu cầu, và phương thức
close_pages()sẽ đóng chúng một cách cưỡng bức; tại đó cũng đã sửa các treo trong chế độ headless và giải pháp Turnstile không còn phụ thuộc vào địa phương của trình duyệt.
Loại proxy nào nên chọn cho nhiệm vụ này
Việc lựa chọn không được quyết định bởi trình phân tích, mà bởi trang web mục tiêu:
- Proxy từ trung tâm dữ liệu - cho các trang web không có chống bot nghiêm trọng: tài liệu, đăng ký nhà nước, danh bạ mở, RSS và CSV feeds (đối với cái sau trong phiên bản 0.4.13 đã thêm
XMLFeedSpidervàCSVFeedSpidervới việc giải nén gzip tự động). Rẻ và nhanh, và độ ổn định của định dạng ở đây thường cao hơn. - Proxy dân cư - cho các thị trường, tổng hợp và mọi thứ cá nhân hóa kết quả theo địa lý. Chính ở đây việc chụp mẫu là rất quan trọng và thu thập dữ liệu từ một quốc gia, nếu không bạn sẽ sửa chữa không phải lỗi, mà là địa lý của chính mình.
- Proxy di động - khi trang web trả về mẫu di động và cần phải phân tích như vậy, hoặc khi sự tin cậy của IP quan trọng hơn giá cho một gigabyte.
Tóm tắt
Các trường trống trong xuất dữ liệu là hai chẩn đoán khác nhau với phương pháp điều trị khác nhau. Đầu tiên hãy kiểm tra mã phản hồi và HTML thô: nếu trang đã đến đầy đủ, không cần thay đổi proxy, mà là định dạng đã bị lệch. Các bộ chọn thích ứng của Scrapling giải quyết lớp hỏng hóc này trong vòng vài mili giây cho mỗi yêu cầu - hãy lưu dấu vân tay trên bố cục làm việc, bật adaptive=True trong thực tế và ghi lại các khoảnh khắc kích hoạt như tín hiệu về việc thiết kế lại. Và hãy giữ địa lý ổn định: một nửa "thiết kế lại bất ngờ" thực tế hóa ra là phiên bản ngôn ngữ khác của trang, đến từ việc thay đổi quốc gia xuất phát.
Nếu địa lý ổn định và phiên dự đoán là những gì mà trình phân tích của bạn còn thiếu, hãy xem proxy dân cư của ProxyCove: lựa chọn quốc gia, các phiên dính và thanh toán cho lưu lượng thực sự sử dụng.
