2010-02-04 33 views
7

Hiện tại chúng tôi đang xem xét sự thay đổi từ Postgres sang CouchDB cho một ứng dụng giám sát sử dụng. Một số số điện thoại:Cấu trúc tài liệu được đề xuất cho CouchDB

Khoảng 2000 kết nối, được thăm dò sau mỗi 5 phút, cho khoảng 600.000 hàng mới mỗi ngày. Trong Postgres, chúng tôi lưu trữ dữ liệu này, được phân đoạn theo ngày:

t_usage {service_id, dấu thời gian, dữ liệu_in, data_out}
t_usage_20100101 kế thừa t_usage.
t_usage_20100102 kế thừa t_usage. v.v.

Chúng tôi ghi dữ liệu với một proc được lưu trữ lạc quan cho rằng phân vùng tồn tại và tạo phân vùng nếu cần. Chúng ta có thể chèn rất nhanh.

Để đọc các dữ liệu, trường hợp sử dụng của chúng tôi, theo thứ tự tầm quan trọng và hiệu suất hiện tại là:
* Dịch vụ Độc thân, Độc ngày Cách sử dụng: Tốt Performance
* Nhiều dịch vụ, Tháng Cách sử dụng: Hiệu suất nghèo
* Độc thân dịch vụ, Tháng Cách sử dụng: hiệu suất nghèo
* Nhiều dịch vụ, Nhiều tháng: Rất Poor Performance
* Nhiều dịch vụ, đơn ngày: Tốt Performance

này có ý nghĩa bởi vì các phân vùng được tối ưu hóa trong nhiều ngày, đó là cho đến nay chúng tôi nhất imp trường hợp sử dụng ortant. Tuy nhiên, chúng tôi đang xem xét các phương pháp cải thiện các yêu cầu phụ.

Chúng tôi thường cần phải tham số truy vấn theo giờ, ví dụ: chỉ cho kết quả từ 8 giờ sáng đến 6 giờ tối, vì vậy bảng tóm tắt bị hạn chế sử dụng. (Các tham số này thay đổi với tần suất đủ để tạo ra nhiều bảng tóm tắt dữ liệu bị cấm).

Với nền tảng đó, câu hỏi đầu tiên là: CouchDB có phù hợp với dữ liệu này không? Nếu có, cho các trường hợp sử dụng ở trên, làm cách nào để mô hình hóa dữ liệu tốt nhất trong các tài liệu CouchDB? Một số tùy chọn Tôi đã đi lại với nhau cho đến nay, trong đó chúng tôi đang trong quá trình chuẩn là (_id, _rev tự túc):

Một tài liệu mỗi kết nối mỗi ngày

{ 
    service_id:555 
    day:20100101 
    usage: {1265248762: {in:584,out:11342}, 1265249062: {in:94,out:1242}} 
} 

Khoảng 60.000 tài liệu mới một tháng. Hầu hết dữ liệu mới sẽ là bản cập nhật cho các tài liệu hiện có, thay vì các tài liệu mới.

(Ở đây, các đối tượng được sử dụng được đánh dấu trên dấu thời gian của cuộc thăm dò và giá trị byte vào và ra ngoài).

Một tài liệu mỗi kết nối mỗi tháng

{ 
    service_id:555 
    month:201001 
    usage: {1265248762: {in:584,out:11342}, 1265249062: {in:94,out:1242}} 
} 

Khoảng 2.000 tài liệu mới một tháng. Cập nhật trung bình cho các tài liệu hiện có được yêu cầu.

Một tài liệu mỗi Row của dữ liệu thu thập

{ 
    service_id:555 
    timestamp:1265248762 
    in:584 
    out:11342 
} 
{ 
    service_id:555 
    timestamp:1265249062 
    in:94 
    out:1242 
} 

Khoảng 15.000.000 tài liệu mới một tháng. Tất cả dữ liệu sẽ là một chèn vào một tài liệu mới. Chèn nhanh hơn, nhưng tôi có câu hỏi về mức độ hiệu quả của nó sau một năm hoặc 2 năm với hàng trăm triệu tài liệu. Các tập tin IO sẽ có vẻ prohibitive (mặc dù tôi là người đầu tiên thừa nhận tôi không hoàn toàn hiểu được cơ chế của nó).

Tôi đang cố gắng tiếp cận điều này theo cách hướng tài liệu, mặc dù phá vỡ thói quen RDMS rất khó :) Thực tế bạn chỉ có thể tối thiểu tham số hóa cũng như có chút lo ngại. Điều đó nói rằng, điều nào ở trên sẽ là thích hợp nhất? Có các định dạng khác mà tôi chưa xem xét sẽ thực hiện tốt hơn không?

Xin cảm ơn trước,

Jamie.

Trả lời

10

Tôi không nghĩ đó là một ý tưởng kinh khủng.

Hãy xem xét trường hợp Kết nối/Tháng của bạn.

Cho rằng mục nhập là ~ 40 (hào phóng) ký tự và bạn nhận được ~ 8,200 mục mỗi tháng, kích thước tài liệu cuối cùng của bạn sẽ dài ~ 350K vào cuối tháng.

Điều đó có nghĩa là, đi đầy đủ, bạn đang đọc và viết 2000 tài liệu 350K cứ 5 phút một lần.

I/O khôn ngoan, điều này nhỏ hơn 6 MB/s, xem xét đọc và ghi, được tính trung bình trong khoảng thời gian 5m. Đó là tốt ngay cả trong phần cứng thậm chí thấp ngày hôm nay.

Tuy nhiên, có một vấn đề khác. Khi bạn lưu trữ tài liệu đó, Couch sẽ đánh giá nội dung của nó để xây dựng khung nhìn của nó, vì vậy Couch sẽ phân tích cú pháp tài liệu 350K. Nỗi sợ của tôi là (ở lần kiểm tra cuối cùng, nhưng đã lâu rồi) Tôi không tin rằng Couch có thể nhân rộng trên các lõi CPU, vì vậy điều này có thể dễ dàng ghim lõi CPU đơn lẻ mà Couch sẽ sử dụng. Tôi muốn hy vọng rằng Couch có thể đọc, phân tích, và xử lý 2 MB/s, nhưng tôi thẳng thắn không biết. Với tất cả những lợi ích của nó, erlang không phải là ass tốt nhất trong một ngôn ngữ máy tính đường thẳng.

Mối quan tâm cuối cùng là cập nhật cơ sở dữ liệu. Điều này sẽ được viết 700 MB mỗi 5 phút vào cuối tháng. Với kiến ​​trúc Couchs (chỉ nối thêm), bạn sẽ ghi 700MB dữ liệu sau mỗi 5 phút, là 8.1GB mỗi giờ và 201GB sau 24 giờ.

Sau khi nén DB, nó giảm xuống 700MB (trong một tháng), nhưng trong quá trình đó, tệp đó sẽ trở nên lớn và khá nhanh.

Ở mặt truy xuất, các tài liệu lớn này không làm tôi sợ. Tải lên một tài liệu JSON 350K, có nó lớn, nhưng nó không phải là lớn, không phải trên phần cứng hiện đại. Có những avatar trên bảng thông báo lớn hơn thế. Vì vậy, bất cứ điều gì bạn muốn làm liên quan đến hoạt động của một kết nối trong một tháng sẽ được khá nhanh, tôi nghĩ. Thông qua các kết nối, rõ ràng là bạn càng lấy, càng tốn kém nó sẽ nhận được (700MB cho tất cả các kết nối 2000). 700MB là một con số thực sự có tác động thực sự. Cộng với quá trình của bạn sẽ cần phải được tích cực trong ném ra các dữ liệu bạn không quan tâm để nó có thể vứt bỏ các chaff (trừ khi bạn muốn tải lên 700MB đống trong quá trình báo cáo của bạn).

Với những con số này, Kết nối/Ngày có thể là đặt cược tốt hơn, vì bạn có thể kiểm soát mức chi tiết tốt hơn một chút. Tuy nhiên, thành thật mà nói, tôi sẽ tìm tài liệu thô nhất mà bạn có thể, bởi vì tôi nghĩ rằng cung cấp cho bạn giá trị tốt nhất từ ​​cơ sở dữ liệu, chỉ vì hôm nay tất cả đầu tìm kiếm và xoay vòng là những gì tiêu diệt rất nhiều hiệu năng I/O, nhiều đĩa dữ liệu luồng rất tốt. Tài liệu lớn hơn (giả định dữ liệu vị trí tốt, vì Couch được liên tục đầm chặt, điều này không phải là một vấn đề) dòng hơn tìm kiếm. Tìm kiếm trong bộ nhớ là "miễn phí" so với một đĩa.

Bằng mọi cách, hãy chạy thử nghiệm của riêng bạn trên phần cứng của chúng tôi, nhưng hãy cân nhắc tất cả những điều này.

EDIT:

Sau khi thử nghiệm thêm ...

Couple quan sát thú vị.

Trong khi nhập tài liệu lớn, CPU cũng quan trọng không kém đối với tốc độ I/O. Điều này là do số lượng marshalling và CPU được tiêu thụ bằng cách chuyển đổi JSON sang mô hình nội bộ để sử dụng bởi các khung nhìn. Bằng cách sử dụng các tài liệu lớn (350k), các CPU của tôi đã được tối đa khá nhiều (350%). Ngược lại, với các tài liệu nhỏ hơn, họ đã ồn ào cùng với 200%, mặc dù, tổng thể, đó là thông tin tương tự, chỉ chunked lên một cách khác nhau.

Đối với I/O, trong tài liệu 350K, tôi đã lập biểu đồ 11MB/giây, nhưng với tài liệu nhỏ hơn, chỉ 8MB/giây.

Nén dường như gần như được I/O ràng buộc. Thật khó cho tôi để có được con số tốt về tiềm năng I/O của tôi. Bản sao của tệp được lưu trong bộ nhớ cache đẩy 40 + MB/giây. Nén được chạy với tốc độ khoảng 8MB/giây. Nhưng đó là phù hợp với tải nguyên (giả sử chiếc ghế là di chuyển thông điệp công cụ bằng tin nhắn). CPU là thấp hơn, vì nó làm ít xử lý hơn (nó không giải thích các tải trọng JSON, hoặc xây dựng lại các khung nhìn), cộng thêm nó là một CPU duy nhất đang thực hiện công việc.

Cuối cùng, để đọc, tôi đã cố gắng loại bỏ toàn bộ cơ sở dữ liệu. Một CPU duy nhất được chốt cho điều này, và I/O của tôi khá thấp. Tôi đã làm cho nó một điểm để đảm bảo rằng các tập tin CouchDB đã không thực sự được lưu trữ, máy tính của tôi có rất nhiều bộ nhớ, do đó, rất nhiều thứ được lưu trữ. Kết xuất thô thông qua _all_docs chỉ khoảng 1 MB/giây. Đó là gần như tất cả tìm kiếm và chậm trễ quay hơn bất cứ điều gì khác. Khi tôi đã làm điều đó với các tài liệu lớn, I/O đã đạt 3 MB/giây, điều đó chỉ cho thấy luồng ảnh hưởng đến tôi đã đề cập đến một lợi ích cho các tài liệu lớn hơn.

Và cần lưu ý rằng có các kỹ thuật trên trang web của Couch về việc cải thiện hiệu suất mà tôi không theo dõi. Đáng chú ý là tôi đã sử dụng các ID ngẫu nhiên. Cuối cùng, điều này đã không được thực hiện như là một thước đo về hiệu suất của Couch là gì, thay vì nơi tải xuất hiện để kết thúc. Sự khác biệt lớn so với tài liệu nhỏ mà tôi nghĩ là thú vị.

Cuối cùng, hiệu suất tối ưu không quan trọng bằng cách chỉ thực hiện đủ tốt để bạn ứng dụng với phần cứng của mình. Như bạn đã đề cập, bạn đang làm thử nghiệm của riêng mình và đó là tất cả những điều thực sự quan trọng.

+0

CouchDB sẽ khởi chạy nhiều quy trình hệ thống cho máy chủ chế độ xem để xử lý chế độ xem, do đó, quy mô này chỉ hoạt động tốt trên nhiều lõi. Phần còn lại của CouchDB là ở Erlang và rất tuyệt khi sử dụng nhiều lõi. – mikeal

+0

Bạn nói đúng. Tôi chạy một thử nghiệm, và tôi chèn 2000 của các tài liệu lớn (20 quy trình chèn 100 mỗi, đồng thời) vào một ví dụ Couch v0.9. Trên một Mac Core 2.66G 4 lõi, chúng được chèn vào cơ bản 3m30s. Couch chiếm 350% CPU. Cuối cùng tập tin đĩa là ~ 2G. Ngay cả sau khi nén chặt, nó hầu như không thay đổi chút nào. Ngược lại, chèn 2000 tài liệu "một ngày" mất ~ 18 giây. Nhanh hơn nhiều, tất nhiên. 3m30s quá gần cửa sổ 5m mà chúng có. 18 tuổi tốt hơn nhiều. Tuy nhiên, việc thu gọn mất gần 3m. –

+0

Cảm ơn rất nhiều vì điều này, đây là một nơi tuyệt vời để bắt đầu. Chúng tôi đã chạy một số điểm chuẩn và tìm thấy nhiều điểm giống như bạn có. Vấn đề chính chúng ta sẽ có là các cập nhật liên tục cho dữ liệu - có vẻ như nó sẽ bị chậm nghiêm trọng đối với các tài liệu "toàn bộ tháng". Miễn là chúng tôi có thể thường xuyên nhỏ gọn, hy vọng chúng tôi sẽ ổn. Đó là một sự xấu hổ chúng tôi không thể đi cho một tài liệu cho mỗi điểm dữ liệu, nhưng như bạn nghi ngờ các tập tin IO có vẻ cấm. Thật không may để cập nhật bất kỳ loại tài liệu nào khác, chúng ta cần phải đọc trước khi chúng ta có thể viết, để có được _rev ... – majelbstoat

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