2016-07-21 1 views
1

Я собираюсь создать систему бронирования. В этой системе есть человек с ограниченной способностью встречаться с людьми в определенный период времени. Например. человек A может встретиться с 8 человек в воскресенье с 8:00 до 12:00.Управление логическим ограничением для обработки параллелизма в вставке базы данных mySQL

В моей базе данных У меня есть две таблицы об этом: Timings, которые показывают предопределенные графики и Bookings, где показаны заказы, которые исправлены. Эти таблицы определяются, как показано ниже:

CREATE TABLE IF NOT EXISTS `Timings` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `day` varchar(100) COLLATE utf8_persian_ci NOT NULL, 
    `start_time` int(11) NOT NULL, 
    `end_time` int(11) NOT NULL, 
    `capacity` int(11) NOT NULL, 
    `personFK` int(11) NOT NULL, 
    PRIMARY KEY (`id`), 
    KEY `fk_person_timing` (`personFK`), 
    KEY `id` (`id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_persian_ci AUTO_INCREMENT=12 ; 



CREATE TABLE IF NOT EXISTS `Bookings` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `user_id` varchar(100) COLLATE utf8_persian_ci NOT NULL, 
    `order` int(11) NOT NULL, 
    `booking_code` varchar(100) COLLATE utf8_persian_ci NOT NULL, 
    `timingFK` int(11) NOT NULL, 
    PRIMARY KEY (`id`), 
    KEY `fk_booking_timing` (`timingFK`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_persian_ci AUTO_INCREMENT=1 ; 

Так что, когда я собираюсь заказать новую встречу, я должен проверить, если количество строк в Bookings таблице, связанной с указанным времени меньше, чем его способность дать новый бронирование.

Это необходимое условие, но этого недостаточно, когда происходит параллелизм. Я имею в виду, если я проверю count of (timings where timingFK=XXX)< timing.capacity, для последнего доступного бронирования может случиться, что два человека могут быть допущены к бронированию в то же время, потому что когда они проверяют состояние, последнее бронирование было по-прежнему доступно. Я хочу знать, как я могу реализовать семафопоподобную вещь, чтобы избежать того, чтобы два человека забронировали последнюю левую позицию во время вставки нового бронирования?

ответ

0

Для максимальной безопасности используйте транзакцию + select for update.

Для индекса записывает поисковые встречи, SELECT ... FOR UPDATE замков строк и любых связанных записей индекса, то же самое, как если бы вы выдан оператор UPDATE для этих строк. Другие транзакции блокируются от обновления этих строк, от выполнения SELECT ... LOCK IN SHARE MODE или от чтения данных на определенных уровнях изоляции транзакций. Согласованные чтения игнорируют любые блокировки, установленные в записях, которые существуют в просмотре чтения . (Старые версии записи не могут быть заблокированы;. Они реконструированы с применением отмены журналов на экземпляре-памяти записи)

Таким образом, вы могли бы иметь

START TRANSACTION; 
SELECT COUNT(*) FROM Bookings WHERE somecondition FOR UPDATE 
INSERT INTO timings ... 
UPDATE Bookings .... 
COMMIT;