2010-02-22 24 views
5

Tôi sắp triển khai giải pháp FileSystemWatcher nguyên mẫu. Tôi có một thư mục để theo dõi các tập tin sáng tạo, và nhiệm vụ mút các tập tin được tạo ra và chèn vào một DB. Khoảng cách này sẽ liên quan đến việc đọc và xử lý 6 hoặc 7, 80 tệp văn bản char xuất hiện với tốc độ 150mS trong các vụ nổ xảy ra sau mỗi vài giây và hiếm khi tệp nhị phân 2MB cũng phải được xử lý. Điều này rất có thể sẽ là một quy trình 24/7.Sau khi FileSystemWatcher kích hoạt - Thread Pool hoặc Thread chuyên dụng?

Từ những gì tôi đã đọc về đối tượng FileSystemWatcher, tốt hơn là enqueue các sự kiện của nó trong một chủ đề và sau đó dequeue/xử lý chúng trong một chủ đề khác. Các quandary tôi có ngay bây giờ là những gì sẽ là cơ chế tạo ra tốt hơn của thread mà không chế biến. Những lựa chọn tôi có thể thấy là:

  1. Mỗi lần tôi nhận được sự kiện FSW, tôi tạo thủ công một chủ đề mới (vâng tôi biết .. kiến ​​trúc ngu ngốc, nhưng tôi phải nói).

  2. Ném chế biến tại CLR bơi thread bất cứ khi nào tôi nhận được một sự kiện FSW

  3. On khởi động, tạo ra một sợi thứ hai dành riêng cho việc xử lý và sử dụng một mô hình sản xuất/tiêu dùng để giải quyết công việc. Các chủ đề chính enqueues yêu cầu và thread thứ hai dequeues nó và thực hiện công việc.

Tôi đang hướng tới phương pháp thứ ba là phương pháp ưu tiên vì tôi biết chuỗi công việc sẽ luôn được yêu cầu - và cũng có thể nhiều hơn vì tôi không cảm thấy gì cho hồ bơi.

Trả lời

3

Nếu bạn biết rằng tiểu trình thứ hai sẽ luôn luôn được yêu cầu, và bạn cũng biết rằng bạn sẽ không bao giờ cần nhiều hơn một sợi công nhân, sau đó lựa chọn ba là đủ tốt.

+1

+1, tôi sẽ thêm điều đó bằng cách sử dụng nhóm chủ đề sẽ thử và xử lý yêu cầu của bạn đồng thời trên nhiều chủ đề không giống như một điều tốt cho ứng dụng của bạn. –

+0

Anon .. Từ thử nghiệm tôi đã thực hiện xử lý của tôi nên được thực hiện tốt và thực sự trong 150mS ngoại trừ trường hợp xử lý tệp nhị phân - sẽ chạy ở khoảng 150mS nhưng phải là một sự xuất hiện hiếm hoi sẽ có nhiều thời gian để bắt kịp nếu mọi thứ được xếp hàng đợi. –

2

Chỉ cần lưu ý rằng FileSystemWatcher có thể bỏ lỡ các sự kiện, không có đảm bảo rằng nó sẽ cung cấp tất cả các sự kiện cụ thể đã xảy ra. Thiết kế của bạn giữ công việc được thực hiện bởi các sự kiện nhận được thread ở mức tối thiểu, nên giảm thiểu cơ hội xảy ra, nhưng nó vẫn là một khả năng, với kích thước bộ đệm sự kiện hữu hạn (đứng ở 64KB).

Tôi rất muốn khuyên bạn nên phát triển một loạt các thử nghiệm tra tấn nếu bạn quyết định sử dụng FileSystemWatcher.

Trong thử nghiệm của mình, chúng tôi gặp sự cố với vị trí mạng, việc thay đổi InternalBufferSize không khắc phục được, nhưng khi chúng tôi gặp phải trường hợp này, chúng tôi cũng không nhận được thông báo sự kiện lỗi. Do đó, chúng tôi đã phát triển cơ chế bỏ phiếu của riêng mình để làm như vậy, sử dụng Directory.GetFiles, tiếp theo so sánh trạng thái của các tệp trả về với trạng thái được thăm dò trước đó, đảm bảo chúng tôi luôn có một đồng bằng chính xác.

Tất nhiên, điều này có chi phí đáng kể về hiệu suất, có thể không đủ tốt cho bạn.

+1

Leon, tôi biết rõ các giới hạn và vấn đề của FSW. Có vẻ như không mạnh trên các cổ phiếu mạng. Tôi chỉ sẽ được sử dụng trên một thư mục địa phương và tôi không mong đợi kích thước bộ đệm FSW sự kiện sẽ gây ra cho tôi vấn đề. Tôi sắp lập kế hoạch cho một quy trình quét dọn chỉ trong trường hợp tôi bỏ lỡ một số thứ. –

+0

Leon .. BTW Tôi sẽ lên kế hoạch cho rất nhiều bài kiểm tra .. FSW dường như có một số lượng lớn các gotchas ẩn. –

+0

Nếu tôi đã làm điều này, tôi sẽ đi cho FSW, và chạy một quét toàn bộ thư mục mỗi bây giờ và sau đó (có thể hàng ngày, tại một thời điểm hệ thống bình thường yên tĩnh?) Để đảm bảo tất cả mọi thứ bị bắt. –

3

Tùy chọn thứ ba là hợp lý nhất.

Liên quan đến FSW thiếu một số các sự kiện tập tin, tôi thực hiện điều này: 1) FSW Object mà cháy trên FileCreate 2) tmrFileCheck, ve = 5000 (5 giây) - Gọi tmrFileChec_Tick

Khi sự kiện FileCreate xảy ra, nếu (tmrFileCheck.Enabled == false) sau đó tmrFileCheck.Start()

Bằng cách này, sau 10 giây tmrFileCheck_Tick cháy mà a) tmrFileCheck.Stop() b) CheckForStragglerFiles

Trong số các thử nghiệm tôi đã chạy, tính năng này hoạt động hiệu quả khi có một tệp < 100 được tạo mỗi phút.

Một biến thể là chỉ đơn thuần là có một bộ đếm thời gian bao giờ NN giây và quét các thư mục cho các tập tin straggler.

Một biến thể khác là thuê tôi để nhấn F5 để làm mới cửa sổ và gọi cho bạn khi có các tệp có kích thước; Chỉ là một gợi ý. :-P