2012-05-15 33 views
6

Tôi đang lưu trữ hệ thống tệp của các thư mục và tệp.Xóa tầng của bảng dữ liệu và bảng tìm kiếm cùng một lúc

Trong một bảng InnoDB, tôi lưu trữ các chi tiết của mỗi thư mục/tập tin và duy trì mối quan hệ con cha mẹ với một ràng buộc khoá ngoại mà sẽ thác trên xóa.

Bảng myisam được sử dụng để tìm kiếm các thư mục/tệp này bằng tìm kiếm toàn văn. Nó chứa tên và id của mỗi hàng.

Bất kỳ hàng nào trong bảng dữ liệu (bảng innodb) sẽ có hàng tương ứng trong bảng tìm kiếm (bảng myisam) và thêm hoặc xóa hàng khỏi bảng dữ liệu phải được phản ánh trong bảng tìm kiếm.

Tôi đang cố gắng tìm ra giải pháp tốt nhất để duy trì tính nhất quán dữ liệu giữa hai bảng khi xóa một thư mục cha. Bảng innodb là tốt. Tôi xóa phụ huynh, xóa các thác thông qua các trẻ em cho đến khi tất cả chúng đều bị xóa. Việc xóa các hàng tương ứng khỏi bảng myisam sẽ khó hơn.

Suy nghĩ đầu tiên của tôi là sử dụng trình kích hoạt xóa trên bảng innodb. Khi một hàng bị xóa, nó sẽ xóa hàng tương ứng từ bảng myisam. Tuy nhiên, vì MySQL không kích hoạt các trigger trong quá trình xóa tầng (một lỗi đã biết trong 7 năm đã được khắc phục bằng cách đề cập đến việc thiếu sự hỗ trợ trong sổ tay), đó không phải là một lựa chọn.

Suy nghĩ thứ hai của tôi đã được đặt một mối quan hệ cha mẹ con trong bảng tìm kiếm, nhưng nó là một bảng myisam để hỗ trợ chức năng tìm kiếm văn bản đầy đủ, và do đó nó không hỗ trợ các ràng buộc khóa ngoại.

Tôi đã nghe nói rằng InnoDB bây giờ hỗ trợ tìm kiếm văn bản đầy đủ, vì vậy tôi nghĩ có lẽ tôi có thể thay đổi công cụ bảng tìm kiếm, nhưng nó chỉ có sẵn trong phiên bản phòng thí nghiệm.

Suy nghĩ cuối cùng của tôi là từ bỏ các ràng buộc khóa ngoài và chỉ sử dụng trình kích hoạt để duy trì tính nhất quán của dữ liệu. Khi xóa, xóa khỏi cả bảng innodb và myisam, nơi cha mẹ = OLD.id. Tuy nhiên, để ngăn chặn các vòng lặp vô tận có thể làm hỏng tất cả dữ liệu trong bảng, MySQL không hỗ trợ thao tác dữ liệu trong cùng một bảng kích hoạt trình kích hoạt.

Tôi đã viện đến lập trình lấy tất cả trẻ em dưới thư mục cha qua một vòng các yêu cầu, tuy nhiên, tôi cảm thấy có đã có được một lựa chọn tốt hơn. Có công việc nào khác có hiệu quả hơn không? Tại thời điểm này, chỉ có hai tùy chọn mà tôi có thể nghĩ là đang đợi một trong các cách tiếp cận trên được sửa hoặc thay đổi thành một RDBMS khác như PostgreSQL hỗ trợ kích hoạt các trình kích hoạt từ một lần xóa tầng.

Bất kỳ ý tưởng nào khác sẽ được đánh giá cao.

+0

Tôi không chắc liệu tôi có nhận được hay không, tôi khá bối rối về mối quan hệ giữa hai bảng, điều tôi nhận được là bạn xác định mối quan hệ giữa 2 bảng có loại khác nhau. Tôi đã thử điều này trước đây và gặp phải vấn đề khi duy trì tính nhất quán của dữ liệu, nếu bạn muốn duy trì tính nhất quán của dữ liệu thông qua mối quan hệ bảng với người dùng khóa ngoài và khóa chính sử dụng innodb trên tất cả các bảng nơi bạn sẽ xác định mối quan hệ của mình. –

+0

bảng tìm kiếm (myisam) được sử dụng làm công cụ tìm kiếm của tôi cho bảng dữ liệu (innodb). Nhưng như tôi thư mục với các thư mục con và các tập tin bị xóa, những thay đổi cần phải phản ánh trong cả bảng dữ liệu và bảng tìm kiếm. Tôi không thể sử dụng innodb cho công cụ tìm kiếm do thiếu hỗ trợ tìm kiếm văn bản đầy đủ (ít nhất, vào thời điểm đó). Mối quan hệ được xác định rõ trong bảng dữ liệu, nhưng các lần xóa không được phản ánh trong bảng tìm kiếm. – JayceTDE

+0

+1 cho câu hỏi được viết tốt; rất tiếc là tôi không thấy bất kỳ lựa chọn thay thế nào cho phương pháp hiện tại của bạn, nhưng có thể một người khác sẽ tìm ra thứ gì đó – Daan

Trả lời

1

Những loại nhức đầu này chính xác là điều khiến tôi chuyển khỏi mysql nếu có thể.

... Tôi cảm thấy có đã có được một lựa chọn tốt hơn ...

Đáng buồn là không có. Vấn đề đơn giản là bạn không thể xóa cascade và có mysql biết những gì nó vừa xóa. Do đó, lựa chọn duy nhất của bạn là để tìm hiểu những gì nó về để xóa trước khi nó (đây là thuật toán bạn đề nghị ở cuối).

Vì tầng sẽ phá vỡ dữ liệu của bạn, bạn không nên sử dụng khóa on update cascade để cố gắng xóa thư mục mẹ mà không xóa con sẽ thất bại.

Tôi khuyên bạn nên tạo một quy trình để thực hiện việc nâng hạng nặng (xóa) cho bạn. Điều này sẽ ngăn chặn một IO lớn giữa ứng dụng của bạn và DB khi nó recuses qua tất cả các thư mục. Iy cũng sẽ cung cấp mã phổ biến để làm như vậy nếu bạn đã từng truy cập cùng một db thông qua một ứng dụng khác (hoặc bạn chỉ muốn làm điều gì đó theo cách thủ công).

Như tôi đã nói đầu tiên, tôi sử dụng postgresql chủ yếu là những ngày này. Đây là một ví dụ về lý do tại sao.

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