Получите незафиксированные данные в MySQL

В SQL Server мы можем написать ниже SQL Queries получить Un-Committed данные в базе данных. Это означает, что данные все еще находятся в состоянии транзакции, а транзакция не завершена.

SQL Server Query

Select * from TableName With(NoLock);

Есть ли эквивалентность в базе данных MySQL для получения данных, даже если таблица заблокирована? Я пытаюсь это в PHP CodeIgnitor

17

Решение

Нашел статью с заголовкомСинтаксис MySQL NOLOCK«

http://itecsoftware.com/with-nolock-table-hint-equivalent-for-mysql

SQL Server WITH (NOLOCK) выглядит так:

SELECT * FROM TABLE_NAME WITH (nolock)

Чтобы добиться того же с MySQL, мы меняем режим изоляции сеанса, используя SET SESSION команда.

SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
SET SESSION TRANSACTION ISOLATION LEVEL REPEATABLE READ ;

Вы можете достичь того же, ниже также:

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
COMMIT ;

Этот оператор будет работать аналогично WITH (NOLOCK), т.е. READ UNCOMMITTED данные. Мы также можем установить уровень изоляции для всех соединений по всему миру:

 SET GLOBAL TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;

Кроме того, в MySQL сервере также существуют две системные переменные, связанные с уровнем изоляции:

SELECT @@global.tx_isolation; (global isolation level)
SELECT @@tx_isolation; (session isolation level)

Или установите уровень изоляции внутри транзакции:

SET TRANSACTION ISOLATION LEVEL REPEATABLE READ
GO

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

Для справки вы можете использовать следующий код:

$this->db->query("SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE");
$this->db->trans_start();

// your code

$this->db->trans_complete();

Обновление 1:

Вы можете просто установить уровень изоляции в запросе, прежде чем запускать свои операторы. Ниже приведен простой код PHP MySQL для использования isolation level read uncommited

//db connection
$mysqli = new mysqli('localhost', 'user', 'pass', 'db');

//set isolation level
$mysqli->query("SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED");

//your Select Query
$results = $mysqli->query("SELECT * FROM tablename");


while($row = $results->fetch_assoc()) {
//some statements
}

// Frees the memory associated with a result
$results->free();
$mysqli->query("COMMIT");
// close connection
$mysqli->close();
10

Другие решения

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
COMMIT ;

Ссылка

4

Операторы SELECT выполняются без блокировки, но может использоваться более ранняя версия строки. Таким образом, используя этот уровень изоляции, такие чтения не согласованы. Это также называется грязным чтением. В противном случае этот уровень изоляции работает как READ COMMITTED.

SERIALIZABLE

Этот уровень похож на REPEATABLE READ, но InnoDB неявно преобразует все простые операторы SELECT в SELECT … LOCK IN SHARE MODE, если автоматическая фиксация отключена. Если автокоммит включен, SELECT является его собственной транзакцией. Следовательно, известно, что оно доступно только для чтения и может быть сериализовано, если выполняется как согласованное (неблокирующее) чтение, и не требует блокировки для других транзакций. (Чтобы принудительно блокировать обычный SELECT, если другие транзакции изменили выбранные строки, отключите автокоммит.)

автокоммит

Command-Line Format --autocommit[=#]
System Variable Name    autocommit
Variable Scope  Global, Session
Dynamic Variable    Yes
Permitted Values    Type    boolean
Default ON

Режим автоматической фиксации. Если установлено значение 1, все изменения в таблице вступают в силу немедленно. Если установлено значение 0, вы должны использовать COMMIT для принятия транзакции или ROLLBACK для ее отмены. Если autocommit равен 0 и вы измените его на 1, MySQL выполняет автоматический COMMIT любой открытой транзакции. Другой способ начать транзакцию — использовать оператор START TRANSACTION или BEGIN. Увидеть
Раздел 13.3.1, «Синтаксис START TRANSACTION, COMMIT и ROLLBACK».

По умолчанию клиентские подключения начинаются с autocommit, установленного на 1. Чтобы клиенты начинали со значения по умолчанию 0, установите глобальное значение autocommit, запустив сервер с параметром —autocommit = 0. Чтобы установить переменную с помощью файла параметров, включите эти строки:

[mysqld]
autocommit=0

Смотрите это также

1

В коде воспламенителя вы можете использовать следующую команду перед любым запросом:

$this->db->simple_query("SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED");

Вы можете получить больше информации о Уровень изоляции MySQL в документации. Это требует таблиц innoDB.

Для получения дополнительной информации о simple_query(), в соответствии с документация кодигнитора, он используется, когда запрос не возвращает результата.

1

Только механизм хранения InnoDB полностью поддерживает транзакции. Он также реализует Oracle / PostgreSQL в стиле MVCC, который предотвращает блокировку чтения неявной блокировкой строки. Чтобы получить Read-Uncommitted в InnoDB, введите SET TRANSACTION LEVEL READ UNCOMMITTED перед выдачей запроса.

Синтаксис для этого в PHP будет выглядеть примерно так:

$dbh->exec('SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED');
$dbh->beginTransaction();

Это устанавливает уровень изоляции до следующего COMMIT или же ROLLBACK, Чтобы изменение уровня сохранялось в течение сеанса, используйте

SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED

вместо.

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

1
По вопросам рекламы [email protected]