Bài 5: RealTime Index với Sphinx Search

Nếu các bạn mới bắt đầu làm quen với Sphinx Search qua 4 bài trước thì chắc hẳn bạn cũng nhận ra khuyết điểm của Sphinx là không thể Real Time Index đồng bộ với Database được. Do đó, những cột dữ liệu vừa được thêm vào trong Database thì không xuất hiện trong kết quả tìm kiếm cũng như những cột dữ liệu đã bị xóa đi lại vẫn xuất hiện cho đến khi chúng ta reindex lại. Chúng ta cũng có thể cấu hình reindex thường xuyên nhưng việc làm này khiến server phải chạy thường xuyên và gây tốn tài nguyên hệ thống. Để khắc phục, tôi sẽ hướng dẫn bạn khắc phục vấn đề này mà vẫn tối ưu server:

1. Giới thiệu về Delta Index
  • Delta Index là một Index phụ cho Index chính, chỉ dùng để Index các dữ liệu mới thêm vào và xóa đi các dữ liệu đã xóa.
  • Ý tưởng ở đây là sử dụng "hai index và 2 nguồn dữ liệu". Ví dụ áp dụng với 1 diễn đàn có 1.000.000 bài viết, mỗi ngày có 1000 bài viết mới thì Index chính sẽ dùng dể index những thứ ít thay đổi - 1.000.000 bài viết cũ. Còn Index Delta sẽ dùng để index những bài viết mới. Ta có thể thấy áp dụng mô hình này mang lại lợi ích khi Delta Index là một index nhỏ, có thể reindex thường xuyên mà không gây tốn quá nhiều tài nguyên server.
2. Cấu hình 1 Delta Index

Đầu tiên, ta tạo Table lưu ID dữ liệu lớn nhất mà Index chính đã Index (để Delta Index chỉ Index những dữ liệu mới) bằng câu lệnh SQL:

   CREATE TABLE `file_counter` (
       `id` int(11) NOT NULL AUTO_INCREMENT,
       `max_id` int(11) NOT NULL,
        PRIMARY KEY (`id`)
   ) 
   ENGINE=InnoDB DEFAULT CHARSET=utf8;

Sau đó ta tạo bằng để lưu ID những dữ liệu đã bị xóa:

  CREATE TABLE `deleted_file` (
       `id` int(11) NOT NULL AUTO_INCREMENT,
       `file_id` int(11) DEFAULT NULL,
        PRIMARY KEY (`id`)
  ) 
  ENGINE=InnoDB DEFAULT CHARSET=utf8;

Để tự động nhập ID những dữ liệu bị xóa, ta thêm Trigger sau vào Table chính bằng SQL:

   CREATE TRIGGER `link_del` BEFORE DELETE ON `link` FOR EACH ROW
   BEGIN
       INSERT INTO deleted_file (file_id) VALUES(OLD.id);
   END;;

Quá trình chuẩn bị đã xong, ta tiến hành chỉnh file config của Sphinx /etc/sphinx/sphinx.conf (Tôi chỉ trình bày những phần chính thay đổi, những phần khác bạn thêm vào cho phù hợp nhé):

source main
{
   sql_query_pre = SET NAMES utf8
   sql_query_pre = REPLACE INTO file_counter SELECT 1, MAX(id) FROM tên_table
   sql_query = SELECT col1, col2, col3 FROM tên_table WHERE id <= (SELECT max_id FROM file_counter WHERE id=1)
}

source delta : main
{
   sql_query_pre = SET NAMES utf8
   sql_query_killlist   = SELECT file_id FROM deleted_file
   sql_query = SELECT col1, col2, col3 FROM tên_table   WHERE id > (SELECT max_id FROM file_counter WHERE id=1)
}

index main
{
   source = main
   path = /path/to/main
}

index delta : main
{
   source = delta
   path = /path/to/delta
}

Ta có thể thấy theo config này, Main sẽ Index và lưu ID max nó đã index vào table file_counter. Còn Delta chỉ Index những ID lớn hơn ID mà Main đã Index. Ngoài ra, Delta sẽ lấy những ID dữ liệu đã xóa trong bảng deleted_file và xóa bỏ khỏi kết quả tìm kiếm (sql_query_killlist). Và để sử dụng, ta dùng cron_job để cấu hình reindex lại mỗi Index sao cho hợp lí, khi tôi cấu hình sphinx để sử dụng cho công cụ tìm kiếm file này thì tôi reindex Main hàng giờ và reindex lại Delta mỗi 5 phút.

Câu lệnh reindex Delta:

indexer --rotate delta

Câu lệnh reindex Main

indexer --rotate all

Vậy là xong rồi đấy, Bạn hãy tận tưởng công cụ tìm kiếm siêu nhanh của mình nào.

Dây rút nhựa tp hcm