2010-03-22 35 views
6

Có thể/nên sử dụng các chuỗi công nhân nền với điều khiển trình duyệt web không?BackgroundWorker và WebBrowser Control

Tôi đang tạo bot tìm kiếm từ khóa google, sau đó kiểm tra các trang web trong 10 trang đầu tiên để xem liệu trang web có được xếp hạng hay không.

Người dùng có thể cung cấp tối đa 20 trang web để kiểm tra và có thể sử dụng proxy. Vì vậy, lý tưởng tôi muốn có 5 chủ đề làm việc cùng một lúc.

Có thể không? Tôi có thể đã nghe ở đâu đó rằng có vấn đề với điều khiển WebBrowser và chủ đề.

Trả lời

15

Nó không phải là. WebBrowser sử dụng Internet Explorer là một thành phần COM. Các thành phần COM có một mô hình luồng, IE sử dụng "Căn hộ". Đó là một từ đắt tiền có nghĩa là nó không phải là chủ đề an toàn. Bạn được phép gọi các phương thức của nó trong BGW nhưng COM sẽ tự động sắp xếp cuộc gọi đến chuỗi giao diện người dùng. Vì tất cả các cuộc gọi phương thức và quyền truy cập thuộc tính thực sự xảy ra trên chuỗi giao diện người dùng, bạn sẽ làm cho nó chậm hơn bằng cách sử dụng BGW.

Bạn có thể thực sự chạy WebBrowser trên một chuỗi khác, bạn sẽ phải tạo một phiên bản của nó trên chuỗi đó. Và bạn sẽ phải tạo ra một chủ đề được gọi là Căn hộ đơn luồng. STA, một từ viết tắt bạn có thể nhận ra từ thuộc tính [STAThread] trên phương thức Main() của một ứng dụng Winforms hoặc WPF. Thay đổi một chuỗi công nhân thành STA yêu cầu gọi Thread.SetApartmentState() trước khi bạn bắt đầu nó. Bạn không thể làm điều này cho một BGW. Và thread phải bơm một vòng lặp tin nhắn để thực hiện hợp đồng STA, nó phải gọi Application.Run(). Cần thiết, cho một, để có được WebBrowser để nâng cao sự kiện của nó. This answer cho thấy cách tiếp cận.

Cân nhắc sử dụng lớp WebRequest.

+3

+1 cho 'Không phải là'! –

+2

Tôi đi qua câu trả lời này trong tìm kiếm của tôi cho dù nó có thể sử dụng 'WebBrowser.Navigate()' ** không ** trên thread UI. Sự hiểu biết của tôi từ câu hỏi của bạn rằng có, nó là có thể, nhưng nó sẽ không quan trọng bởi vì tất cả các cuộc gọi như vậy là marshaled anyway để thread UI. Tôi có hiểu điều này một cách chính xác không? –

1

Có lý do nào bạn sử dụng điều khiển IE trên thư viện như HTML Agility pack không? Điều đó có hỗ trợ đa luồng mà không có cơn ác mộng COM của IE, và mạnh hơn rất nhiều với việc phân tích cú pháp HTML.

+2

Bot cũng thực hiện nghiên cứu từ khóa và sử dụng một số công cụ khác của googles. Google rất nghiêm ngặt về các yêu cầu bot, vì vậy việc sử dụng IE dễ quản lý hơn nhiều so với việc sử dụng HttpWebRequest. –

+3

Tôi tự hỏi liệu họ có chính sách cho các bot sử dụng Trình duyệt hay không. –

+0

@HenkHolterman Họ có một chính sách chống lại bất cứ điều gì có thể làm tổn thương đến dịch vụ và lợi nhuận của họ. –

1

Để trả lời câu hỏi ngay lập tức của bạn: Tôi chưa bao giờ thử nó, nhưng nó sẽ không làm tôi ngạc nhiên nếu có vấn đề. Các điều khiển WinForms nói chung không có ý định truy cập từ các chủ đề khác ngoài luồng giao diện người dùng chính. Bạn nên sử dụng phương thức Control.Invoke() để chạy các phương thức gọi từ các chủ đề khác. Điều này xếp hàng chúng lên trên luồng giao diện người dùng chính.

Để giải quyết vấn đề rộng hơn: bạn có thể không nên sử dụng điều khiển WebBrowser nếu bạn không thực sự hiển thị HTML để người dùng xem. Bạn có thể tải xuống một trang bằng cách sử dụng lớp HttpWebRequest, nhẹ hơn nhiều. WebBrowser về cơ bản là trình duyệt Internet Explorer đầy đủ được nhúng trong ứng dụng của bạn.

Các vấn đề liên quan