Модераторы: skyboy

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Общий подход при работе с зависимости от таблицы 
:(
    Опции темы
maxipub
Дата 28.11.2016, 18:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Добрый день!

Снова со своими вопросами. smile Сорри, не очень придумал как топик назвать.

Вот предположим, есть движок форума. В нем функция, принимающая ответ в тему. Нужно проверить входящие данные, тра-та-та, и есть еще целый ряд прав на действие. Например, нельзя постить ответ в закрытую тему. Обычно изначально выбираются данные из БД, и потом идет проверка на языке движка форума а-ля if ($result['closed'] == 0)... А бывает идет запрос с условием вида closed=0, и т.д.... Суть в том, что мы сначала проверяем возможность/допустимость добавления ответа в тему, а лишь затем приступаем непосредственно к самому добавлению. Очевидно, что в промежутке между такой проверкой и собственно самим добавлением ответа в тему, эта тема вполне может быть закрыта.

Конечно, в случае с форумом такое крайне маловероятно, и даже если произойдет - это вообще ерунда. Но форум тут число дли наглядной иллюстрации сути вопроса.

В общем, как быть в такой ситуации, когда мы имеем дело со вставкой / изменением / удалением данных в БД, когда возможность данной операции определяется некоторыми значениями в некоторых таблицах этой БД, и мы хотим быть уверенными в целостности структуры БД после выполнения таких действий?
PM MAIL   Вверх
Akina
Дата 28.11.2016, 19:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20570
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 453



Цитата(maxipub @  28.11.2016,  19:39 Найти цитируемый пост)
мы сначала проверяем возможность/допустимость добавления ответа в тему, а лишь затем приступаем непосредственно к самому добавлению. Очевидно, что в промежутке между такой проверкой и собственно самим добавлением ответа в тему, эта тема вполне может быть закрыта.
...
как быть в такой ситуации, когда мы имеем дело со вставкой / изменением / удалением данных в БД, когда возможность данной операции определяется некоторыми значениями в некоторых таблицах этой БД, и мы хотим быть уверенными в целостности структуры БД после выполнения таких действий? 

Но возможно и другое - тема закрыта сразу после добавления ответа. Конечное состояние будет таким же. Во втором случае это состояние абсолютно легитимно - во всяком случае с точки зрения целостности структуры БД. Но состояние не содержит информации о пути его получения - значит, и в первом случае состояние легитимно, т.е. никаких проблем с целостностью структуры - нет.

Можно попробовать говорить о логической противоречивости - штамп времени последнего сообщения больше штампа времени события закрытия темы. Но в реальности речь пойдёт о секундах или даже долях секунды - явно не повод для беспокойства.

Ну и самое время вспомнить о транзакциях. Или, в простейшем варианте, SELECT ... FOR UPDATE.


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
Zloxa
Дата 29.11.2016, 11:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3470
Регистрация: 12.9.2008

Репутация: 33
Всего: 161



Цитата(maxipub @  28.11.2016,  19:39 Найти цитируемый пост)
В общем, как быть в такой ситуации, когда мы имеем дело со вставкой / изменением / удалением данных в БД, когда возможность данной операции определяется некоторыми значениями в некоторых таблицах этой БД, и мы хотим быть уверенными в целостности структуры БД после выполнения таких действий? 

Для обеспечения согласованности данных в конкурентной среде используют механизмы:
1) Ограничения целостности
2) Уровни изоляции транзакций.
3) Явные блокировки
Ранжировано в порядке предпочтительности. Там, где можно отжаться констрейтами, лучше отжиматься ими, если нет, пробовать отжаться изоляцией, если и тут нет - выстраивать стратегию блокирования самостоятельно.



--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
maxipub
Дата 7.12.2016, 16:15 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Akina, блин, ну неудачный пример, хотите придумаю другой - вместо добавления нового поста, пусть запрос на сохранение при редактировании существующего. очевидно, что после закрытия темы, никаких редактирований ее постов уже не стоит допускать. Суть не в примере, а в вопросе. По SELECT ... FOR UPDATE спасибо, сейчас буду читать.


Zloxa, спасибо, но вообще ничего не понял. smile
PM MAIL   Вверх
Akina
Дата 7.12.2016, 16:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20570
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 453



Цитата(maxipub @  7.12.2016,  17:15 Найти цитируемый пост)
По SELECT ... FOR UPDATE спасибо, сейчас буду читать.

В таком случае заодно почитай про REPLACE.


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
maxipub
  Дата 7.12.2016, 17:28 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Цитата(Akina @  28.11.2016,  19:13 Найти цитируемый пост)
самое время вспомнить о транзакциях

Не вспомнить а узнать! smile Юзаю MyISAM и переходить на всякие-там InnoDB только ради транзакций в ближайшем времени не планирую.

Так что пока смотрю в сторону блокировки таблицы средствами СУБД. Всякие поля типа locked для блокировки строк считаю стремными велосипедами.

Добавлено через 38 секунд
Цитата(Akina @  7.12.2016,  16:21 Найти цитируемый пост)
REPLACE

Про него знаю конечно. smile Но какое он имеет отношение к теме - не пойму?
PM MAIL   Вверх
maxipub
Дата 7.12.2016, 18:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Народ, читаю про блокировки. Ман, статьи, все что нахожу. Инфы что-то о ней совсем скудно. Есть вопросы.

https://habrahabr.ru/post/46542/
тут пишут:

Цитата
Обратите внимание на следующие особенности явных блокировок:
• Пока клиент удерживает явную блокировку, он не может использовать другие таблицы, поэтому блокировать нужно сразу все что понадобится (одним выражением), так как повторное использование оператора LOCK TABLES отменяет сделанные ранее блокировки.


В рамках блокировки мы можем обращаться только к тем таблицам, на которые выполнялась блокировка? Т.е. надо перечислять все-все-все, что будет использоваться в рамках блокировки, даже если по логике не все эти таблицы требуется блокировать. Или автор ошибся, и имел в виду что мы не сможем добавить новые таблицы в блокировку (поскольку новая блокировка автоматически закрывает существующую, и в этот промежуток опять же кто-то может вклиниться) ???

http://ru.stackoverflow.com/questions/3948...%B5-lock-tables
а вот тут в комментарии:

Цитата
... И блокировка не спасет: все равно будет два выполнения с теми же данными, просто не одновременных. ...

к коду:

Код
$db->query('lock tables `table`'); // заблокировали
$var = $db->query('select from `table`'); // выбрали значения
doSomething($var); // обработали
$db->query('update `table`'); // записали обратно
$db->query('unlock tables'); // разблокировали


А разве данные будут одинаковыми?

Я только начинают изучать блокировки. Но насколько понимаю, если поставить LOCK TABLES WRITE, параллельный вызов скрипта "зависнет" на первой строке (LOCK TABLES), будет ждать пока таблица станет доступна для блокировки (закроется текущая блокировка, закончится очередь), и только после этого будет выполняться SELECT во второй строчке... Или нет? smile 
PM MAIL   Вверх
Akina
Дата 7.12.2016, 19:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20570
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 453



Цитата(maxipub @  7.12.2016,  18:28 Найти цитируемый пост)
какое он имеет отношение к теме - не пойму? 

Стоп... это я на автомате. SELECT FOR UNDATE и INSERT ON DUPLICATE попутались.


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
maxipub
Дата 8.12.2016, 10:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Akina, по предыдущему моему сообщению можете дать комментарии? Мне это важно.
PM MAIL   Вверх
Akina
Дата 8.12.2016, 11:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20570
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 453



Цитата(maxipub @  7.12.2016,  19:22 Найти цитируемый пост)
В рамках блокировки мы можем обращаться только к тем таблицам, на которые выполнялась блокировка? Т.е. надо перечислять все-все-все, что будет использоваться в рамках блокировки, даже если по логике не все эти таблицы требуется блокировать. Или автор ошибся, и имел в виду что мы не сможем добавить новые таблицы в блокировку (поскольку новая блокировка автоматически закрывает существующую, и в этот промежуток опять же кто-то может вклиниться) ???
Автор не ошибся. Действительно надо перечислять всё-всё. 
Код

mysql> create table master (id int) engine=MyISAM;
Query OK, 0 rows affected (0.09 sec)

mysql> create table slave (id int) engine=MyISAM;
Query OK, 0 rows affected (0.05 sec)

mysql> insert into master select 1 union select 2 union select 3;
Query OK, 3 rows affected (0.07 sec)
Records: 3  Duplicates: 0  Warnings: 0

mysql> insert into slave select 1 union select 3 union select 5;
Query OK, 3 rows affected (0.00 sec)
Records: 3  Duplicates: 0  Warnings: 0

mysql> lock tables master read;
Query OK, 0 rows affected (0.00 sec)

mysql> select * from master;
+------+
| id   |
+------+
|    1 |
|    2 |
|    3 |
+------+
3 rows in set (0.00 sec)

mysql> select * from master, slave where master.id=slave.id;
ERROR 1100 (HY000): Table 'slave' was not locked with LOCK TABLES
mysql> lock tables master read, slave read;
Query OK, 0 rows affected (0.00 sec)

mysql> select * from master, slave where master.id=slave.id;
+------+------+
| id   | id   |
+------+------+
|    1 |    1 |
|    3 |    3 |
+------+------+
2 rows in set (0.03 sec)

mysql> unlock tables;
Query OK, 0 rows affected (0.00 sec)

Но если логика позволяет изменение части таблиц в процессе выполнения всего задания, разумнее перед каждым запросом или пачкой запросов выполнять ре-лок, устанавливая или снимая блокировки с нужных или ненужных в очередном запросе таблиц. Правда, следует учитывать, что релок неявно вызывает флаш ВСЕХ таблиц, а не только тех, чем статус блокировки меняется.
Цитата(maxipub @  7.12.2016,  19:22 Найти цитируемый пост)
насколько понимаю, если поставить LOCK TABLES WRITE, параллельный вызов скрипта "зависнет" на первой строке (LOCK TABLES), будет ждать пока таблица станет доступна для блокировки (закроется текущая блокировка, закончится очередь), и только после этого будет выполняться SELECT во второй строчке... Или нет?

Да, именно так. Попробуйте самостоятельно на такой же простой модели, но с 2 копиями клиента - увидите.
Вот только НАСТОЯТЕЛЬНО рекомендую явно указывать требуемые локи (по отдельности), причём строго в соответствии с документацией - сначала на запись, потом на чтение. Т.е. не 
Код

LOCK TABLES `table`;
а 
Код

LOCK TABLES `table` AS t1 WRITE, `table` AS t2 READ;




--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
maxipub
Дата 8.12.2016, 12:01 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Akina, круто, благодарю за доходчивые пояснения! smile 
PM MAIL   Вверх
Zloxa
Дата 8.12.2016, 12:03 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3470
Регистрация: 12.9.2008

Репутация: 33
Всего: 161



Цитата(maxipub @  7.12.2016,  18:28 Найти цитируемый пост)
Юзаю MyISAM

Afaik MyISAM предназначен для использования в проектах, не накладывющих требований ACID и не предназначен для использования в конкурентном окружении.

Использовать этот движок для тренировки обеспечения согласованности в конкурентной среде - как-то очень совесем не то smile

Это сообщение отредактировал(а) Zloxa - 8.12.2016, 12:04


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
maxipub
Дата 8.12.2016, 13:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Zloxa, мне это известно. Но боюсь если начну мигрировать с MyISAM на InnoDB, то наделанных мною косяков будет больше, чем выгоды от такого перехода. smile

Да и среда там конкурентная, но не высоко конкурентная. Т.е. надо заботиться о целостности данных. Но блокировка всей таблицы не является критической штукой. Как-то так...
PM MAIL   Вверх
Akina
Дата 8.12.2016, 13:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20570
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 453



Цитата(maxipub @  8.12.2016,  14:05 Найти цитируемый пост)
если начну мигрировать с MyISAM на InnoDB, то наделанных мною косяков будет больше, чем выгоды от такого перехода.

 smile а где можно накосячить в простейшем запросе 
Код

ALTER TABLE `table` ENGINE = InnoDB;
???


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
maxipub
Дата 8.12.2016, 13:28 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: 1
Всего: 1



Akina, но ведь между этими системами хранения есть отличия, которые надо учитывать. Готовый большой проект, все работает на MyISAM. Если просто поменять MyISAM -> InnoDB, 100% полезут глюки, надо учитывать структуру БД, запросы, логику...

Добавлено через 5 минут и 20 секунд
Навскидку вот такой даже примитив https://habrahabr.ru/post/156489/ и уверен есть куча подводных камней. А опыта работы с InnoDB у меня 15 минут. smile

Есть один проект, там CMS самописная (не моя) простая небольшая. Стоит на VPS, который быстренько поднял с полностью чистого образа. Проект небольшой, нагрузка - слезы. Через неделю после поднятия начались глюки - БД висла. Нагрузка минимальная, top показывает avg. 0.05 примерно - чтоб понимали. Начал копаться. Кароче там какой-то баг был из-за того, что в системе не было своп-файла. Так там нагрузка минимальна, 2Гб ОЗУ - зачем своп??? Подключил своп 2Гб, эти глюки пропали. Со временем появились новые. Уже не помню что там было, копался-копался, исправил. Потом еще что-то. Теперь опять БД временами виснет. Почему - непонятно. С MyISAM таких проблем нет. Примитивно, просто, но хорошо.
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | MySQL | Следующая тема »


 




[ Время генерации скрипта: 0.1786 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.