Tại sao ghi đồng thời không được phép trên cơ sở dữ liệu SQLite?


79

Tôi đang làm lập trình cơ sở dữ liệu bằng Java với SQLite.

Tôi đã thấy rằng chỉ có một kết nối tại cơ sở dữ liệu có khả năng ghi, trong khi nhiều kết nối cùng một lúc có khả năng đọc.

Tại sao kiến ​​trúc của SQLite được thiết kế như thế này? Chừng nào hai điều đang được viết không được ghi vào cùng một vị trí trong cơ sở dữ liệu, tại sao hai lần ghi không thể xảy ra cùng một lúc?



5
Bởi vì SQLite được thiết kế để "lite". Bộ nhớ thấp và xử lý thấp với hiệu suất. Hãy suy nghĩ về cách bạn sẽ làm cho SQLite xử lý nhiều lần ghi vào cùng một tệp. Thiết kế hiện tại rất dễ thực hiện - toàn bộ tệp bị khóa và những người khác phải chờ. Để xử lý việc viết đồng thời ở mức độ chi tiết thấp hơn, yêu cầu khóa hàng / trang mà bạn nhận được từ RDMS. Nếu yêu cầu yêu cầu viết đồng thời, thì SQLite không phải là ứng cử viên và thay vào đó, bạn nên tìm đến RDBMS nhẹ: en.wikipedia.org/wiki/ Kẻ
Thomas Carlisle

Câu trả lời:


157

Bởi vì "nhiều lần ghi đồng thời" rất khó thực hiện trong công cụ cơ sở dữ liệu cốt lõi so với trình ghi đơn, nhiều người đọc. Nó vượt ra ngoài các tham số thiết kế của SQLite và bao gồm cả khả năng nó sẽ phá hủy kích thước nhỏ và đơn giản thú vị của SQLite.

Hỗ trợ mức độ đồng thời ghi cao là một đặc điểm nổi bật của các công cụ cơ sở dữ liệu lớn như DB2, Oracle, SQL Server, MySQL, PostgreQuery, NonStop SQL và Sybase. Nhưng về mặt kỹ thuật khó thực hiện, đòi hỏi các chiến lược tối ưu hóa và kiểm soát đồng thời như cơ sở dữ liệu, bảng và khóa hàng hoặc, trong các triển khai hiện đại hơn, kiểm soát đồng thời nhiều phiên bản . Các nghiên cứu về vấn đề / yêu cầu này là rất lớn và trở lại trong nhiều thập kỷ .

SQLite có triết lý thiết kế rất khác so với hầu hết các DBMS tập trung vào máy chủ hỗ trợ nhiều người viết. Nó được thiết kế để mang lại sức mạnh của SQL và mô hình quan hệ cho các ứng dụng riêng lẻ và thực sự có thể nhúng trong mỗi ứng dụng. Mục tiêu đó đòi hỏi sự đánh đổi đáng kể. Không thêm cơ sở hạ tầng quan trọng và chi phí cần thiết để xử lý nhiều nhà văn đồng thời là một trong số đó.

Triết lý có thể được tóm tắt bằng một tuyên bố trên trang sử dụng phù hợp của SQLite :

SQLite không cạnh tranh với cơ sở dữ liệu máy khách / máy chủ. SQLite cạnh tranh với fopen ().


41
+1. SQLite là một cơ sở dữ liệu trong quá trình. Không có trọng tài trung tâm như trong DB dựa trên máy chủ. Các nhà văn sẽ phải hợp tác trực tiếp và tin tưởng lẫn nhau. Một nhà văn độc hại có thể tàn phá chỉ bằng cách không hợp tác.
Jörg W Mittag

12
Ngoài ra, một số môi trường mà SQLite thực thi trong đó thậm chí có thể không hỗ trợ nhiều quy trình.
david25272

1
Có lẽ một bài viết độc hại đã có thể tàn phá bằng cách không hợp tác. Họ không thể sử dụng mã SQLite để làm điều đó, nhưng họ có thể có mã riêng, đó có thể là một cuộc gọi để hủy liên kết ()
bdsl

12
Trong các ứng dụng đồng thời, không có nhiều cơ sở. Bạn có thể nhận được sự đồng thời, tính nhất quán và tính toàn vẹn dữ liệu về cơ bản 100% thời gian, bao gồm cả trong các điều kiện đầy thách thức và các trường hợp cạnh, hoặc bạn không. Nếu bạn không, nó dễ vỡ, chậm và dễ bị hỏng và mọi người ngừng tin tưởng nó rất nhanh. Nhưng làm cho nó thường xuyên đúng là rất khó khăn. Không có nhiều tình huống trong đó các nhà văn có thể, vắng mặt hàng loạt hỗ trợ cốt lõi, tự mình điều phối các bài viết xen kẽ.
Jonathan Eunice

8
@bdsl Cơ sở dữ liệu thuộc bất kỳ loại nào đều phải cho rằng các nhà văn sẽ không được cư xử tốt để họ không bị mất dữ liệu. Các tác giả SQLite định vị nó như một đối thủ cạnh tranh fopen(), vì vậy hãy xem xét tất cả các kiểu tóc đi kèm với việc viết đồng thời vào một tệp văn bản đơn giản.
Blrfl

12

Bởi vì không có máy chủ nào có thể cho biết liệu mọi thứ có được ghi vào cùng một nơi hay không. Chỉ có hai quá trình cố gắng ghi vào một tập tin.

Như được chỉ ra trong một bình luận, việc viết đồng thời cũng có thể được hỗ trợ bởi một luồng nội bộ. Không chắc điều này sẽ hoạt động tốt như thế nào (cũng không nghĩ nhiều về nó). Dù sao đây là lý do tại sao SQLite không sử dụng các luồng: Tiến sĩ Hipp nghĩ rằng các luồng là xấu.

Việc DR Hipp nghĩ rằng các chủ đề là xấu được ghi lại trong Câu hỏi thường gặp về SQLite .


2
Điều này giải thích lý do kỹ thuật tại sao viết đồng thời không được phép, nhưng không giải thích tại sao quyết định thiết kế được đưa ra.
Robert Harvey

3
Quyết định thiết kế SQLite sao cho nó chỉ xử lý một lần ghi.
Robert Harvey

7
@Goyo một máy chủ không bắt buộc phải xử lý ghi đồng thời: vì máy chủ cơ sở dữ liệu là một quy trình riêng biệt, có thể có một luồng riêng biệt bên trong SQLite phục vụ cùng một mục đích. Robert Harvey là chính xác: đã có một quyết định thiết kế được đưa ra bởi nhóm SQLite và nó không liên quan gì đến khả năng của một thư viện duy nhất có thể xử lý việc viết đồng thời (về lý thuyết có thể).

1
Câu trả lời này có vẻ tốt với tôi. Để xử lý việc ghi đồng thời, có vẻ như người ta sẽ cần phải có máy chủ hoặc triển khai sqlite đa luồng. Bởi vì cả hai đã bị loại trừ bởi các quyết định thiết kế khác, việc thực hiện viết đồng thời sẽ vô cùng khó khăn.
jpa

5
@jpa: SQLite quản lý để đồng bộ hóa khóa giữa một số quy trình / luồng mà không có "máy chủ". "Máy chủ" không bắt buộc - sử dụng khóa / đồng bộ hóa / IPC / hệ điều hành do hệ điều hành cung cấp, nhưng mọi thứ đều rất nhanh. "Chủ đề nội bộ" được đề cập trong bài viết không có ý nghĩa.
Mat
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.