Как преодолеть Сбой при получении блокировки записи на запись из таблицы?

Я выполняю запрос с использованием OpenQuery и получаю странную ошибку.

Это мой запрос:

select * from OpenQuery("CAPITAOC",'SELECT per.*
    FROM pub."re-tenancy" AS t 
       INNER JOIN pub."re-tncy-person" AS per
       ON t."tncy-sys-ref" = per."tncy-sys-ref" 
       INNER JOIN pub."re-tncy-place" AS place
       ON t."tncy-sys-ref" = place."tncy-sys-ref"
    WHERE t."tncy-status" = ''CUR'' and place."place-ref"=''GALL01000009''') 

Это сообщение об ошибке:

Поставщик OLE DB "MSDASQL" для связанного сервера "CAPITAOC" вернул сообщение "[DataDirect] [ODBC Progress OpenEdge Wire Protocol] [OPENEDGE] Не удалось получить блокировку записи для записи из таблицы PUB.RE-TNCY-PERSON.". Поставщик OLE DB "MSDASQL" для связанного сервера "CAPITAOC" вернул сообщение "[DataDirect] [ODBC Progress OpenEdge Wire Protocol] Ошибка в строке.". Msg 7330, уровень 16, состояние 2, строка 1 Не удается получить строку от поставщика OLE DB «MSDASQL» для связанного сервера «CAPITAOC».

Как мне прочитать эти данные?


person Steve Staple    schedule 30.08.2016    source источник


Ответы (2)


Ошибка блокировки записи: в многопользовательской среде полезно блокировать обновляемые записи, чтобы предотвратить доступ к этой записи другим пользовательским сеансом. Это предотвращает «грязное чтение» ваших данных.

Чтобы решить эту проблему, я предлагаю прочитать эту статью: http://knowledgebase.progress.com/articles/Article/20255

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

И вот как вы узнаете, кто заблокировал вашу запись: http://knowledgebase.progress.com/articles/Article/19833

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

person Max Alexander Hanna    schedule 16.11.2016

Я тоже столкнулся с этой проблемой, и ссылки на другие ответы не были такими полезными, как я надеялся. Я использовал следующую ссылку: https://knowledgebase.progress.com/articles/Article/P12158 < / а>

Вариант №1 - применяется в OpenEdge 10.1A02 и новее. Используйте подсказку WITH (NOLOCK) в запросе SELECT. Это гарантирует отсутствие блокировок записей. Например,

SELECT * FROM pub.customer WITH (NOLOCK);

Подсказка WITH (NOLOCK) аналогична использованию уровня изоляции Read Uncommitted в том, что это приведет к грязному чтению.

Вариант №2 - применяется ко всем версиям OpenEdge (10.x / 11.x), использующим уровень изоляции Read Committed. Используйте подсказку WITH (READPAST) в запросе SELECT. Этот параметр заставляет транзакцию пропускать строки, заблокированные другими транзакциями, которые обычно появляются в наборе результатов, вместо того, чтобы блокировать транзакцию, ожидая, пока другие транзакции снимут свои блокировки с этих строк. Например,

SELECT * FROM pub.customer WITH (READPAST NOWAIT);
SELECT * FROM pub.customer WITH (READPAST WAIT 5);

Имейте в виду, что это может привести к тому, что будет возвращено меньше записей, чем ожидалось, поскольку заблокированные записи пропускаются / не включаются в набор результатов.

Вариант №3 - применяется ко всем версиям Progress / OpenEdge. Измените уровень изоляции на «Чтение без фиксации», чтобы гарантировать, что при чтении записи блокировок записи не будет. Использование уровня изоляции Read Uncommitted приведет к грязному чтению. Это можно сделать на уровне ODBC DSN или с помощью оператора SET TRANSACTION ISOLATION LEVEL <isolation_level_name>. Например,

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;

Вариант 1 у меня сработал.

person GammaGames    schedule 26.12.2019