Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Microsoft SQL Server Новый топик    Ответить
 Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
Привет
Я задал вопрос на stackoverflow.
Но что то с ответами пока плохо.
Возможно, кто то среди местных экспертов знает как это починить?
Спасибо.
19 сен 18, 20:25    [21680032]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Т-Миронов
Member

Откуда:
Сообщений: 3216
Alew,

Это баг SqlClient нужно ждать пока выкатят фикс или ретраить, когда очевидно что не все записи вернулись.
20 сен 18, 13:37    [21680759]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Alew
Привет
Я задал вопрос на stackoverflow.
Но что то с ответами пока плохо.
Возможно, кто то среди местных экспертов знает как это починить?
Спасибо.


Что означает это
"WHERE @@ROWCOUNT = 1 AND [Id] = @Id"?

Сколько записей вернет , если убрать
"WHERE [Id] = @Id"
?
20 сен 18, 14:10    [21680814]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Владимир Затуливетер
Member

Откуда:
Сообщений: 427
256k
Что означает это
"WHERE @@ROWCOUNT = 1 AND [Id] = @Id"?


Просто проверка что первый стейтмен успешно вставил запись. Если так, то второй делает выборку если нет то выборки не будет.
эквивалентно этому:

INSERT INTO [dbo].[IntegrationCommandLog] ([Id], [Content], [Topic])
VALUES ( @Id, @Content, @Topic);

if @@ROWCOUNT = 1 
    SELECT [OrderingKey], [RowVersion]
    FROM [dbo].[IntegrationCommandLog]
    WHERE [Id] = @Id
20 сен 18, 16:26    [21681068]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Владимир Затуливетер
256k
Что означает это
"WHERE @@ROWCOUNT = 1 AND [Id] = @Id"?


Просто проверка что первый стейтмен успешно вставил запись. Если так, то второй делает выборку если нет то выборки не будет.
эквивалентно этому:

INSERT INTO [dbo].[IntegrationCommandLog] ([Id], [Content], [Topic])
VALUES ( @Id, @Content, @Topic);

if @@ROWCOUNT = 1 
    SELECT [OrderingKey], [RowVersion]
    FROM [dbo].[IntegrationCommandLog]
    WHERE [Id] = @Id


Там такого нет, а есть такое в вопросе:
string sql = @"SET NOCOUNT ON;
INSERT INTO [dbo].[IntegrationCommandLog] ([Id], [Content], [Topic])
VALUES ( @Id, @Content, @Topic);
SELECT [OrderingKey], [RowVersion]
FROM [dbo].[IntegrationCommandLog]
WHERE @@ROWCOUNT = 1 AND [Id] = @Id";


Я не могу сказать точно, как будет вести себя это утверждение, но вполне возможно, что вернется одна запись.
20 сен 18, 17:24    [21681196]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Владимир Затуливетер
Member

Откуда:
Сообщений: 427
256k
Там такого нет, а есть такое в вопросе:

я сказал что это эквивалент того что там, внимательно мой ответ перечитайте.

256k
Я не могу сказать точно, как будет вести себя это утверждение, но вполне возможно, что вернется одна запись.

А тупо попробовать?
use tempdb
go

create table dbo.test1 (
    Id int not null primary key
  , Data varchar(128) 
)
go

declare @Id int = 123
insert into dbo.test1 ( Id, Data )
values ( @id, 'data')
select *
from dbo.test1
where @@rowcount = 1 and Id = @Id
20 сен 18, 19:51    [21681336]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Владимир Затуливетер
256k
Там такого нет, а есть такое в вопросе:

я сказал что это эквивалент того что там, внимательно мой ответ перечитайте.

256k
Я не могу сказать точно, как будет вести себя это утверждение, но вполне возможно, что вернется одна запись.

А тупо попробовать?
use tempdb
go

create table dbo.test1 (
    Id int not null primary key
  , Data varchar(128) 
)
go

declare @Id int = 123
insert into dbo.test1 ( Id, Data )
values ( @id, 'data')
select *
from dbo.test1
where @@rowcount = 1 and Id = @Id


Я для начала тупо прочитал вопрос, который беспокоит юзера

Why Sql Server SELECT does not return all entries?

Какие записи он еще хочет видеть? таким запросом выдастся только одна запись

зы. интересно, зачем тупо использовать
use tempdb
go

create table dbo.test1 (


а не тупо это?
create table #test1 (


спасиба тупо
21 сен 18, 13:26    [21681929]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
invm
Member

Откуда: Москва
Сообщений: 9349
256k
Why Sql Server SELECT does not return all entries?

Какие записи он еще хочет видеть?
ТС считает, что возвращваются не все строки, т.к. есть разрывы в последовательности OrderingKey.
21 сен 18, 13:31    [21681932]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Владимир Затуливетер
Member

Откуда:
Сообщений: 427
Alew
как это починить?


не надо вам строить логику вашего приложения на предположении что identity всегда последовательный.

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

опишите лучше в другом посте вашу реальную задачу, что вам нужно сделать, и вам подскажут.
21 сен 18, 14:58    [21682082]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
TaPaK
Member

Откуда: Kiev
Сообщений: 6801
Закладывать на монотонно возрастающий идентити это последнее дело. Кеширование значений, откаты транзакций как минимум всё это сдвигает значение. Да и не предназначен он для этого.
21 сен 18, 15:16    [21682108]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
Спасибо, за ответы. Отвлекся немного, думал, при ответах будут уведомления на почту

Т-Миронов , почему вы думаете, что это баг клиета, а не спицифика самого сервера? Больше то похоже как раз на последнего.

Владимир Затуливетер , TaPaK
Даже не пытался закладываться на отсутствие реальных гэпов. Проблема то как раз в том, что фактически гэпов нет, а в ответе они есть. И попытка усились транзакции эффекта не дает.
Почему минусуют это отдельный вопрос, но, в данном случае, я вижу это по другому, минус бы в предыдущей версии вопроса, после чего я его уже полностью переписал и новая версия уже содержит в себе все что нужно, но при этом даунвойтер не соизволил пересмотреть свою оценку. Хотя вопрос вполне конкретный и проделанный ресерч приложен как в комментах советовали.

Я создал второй вопрос уже ближе к тому, что именно я хочу сделать, но там тоже глухо. И тоже минусуют, скорее всего тот товарищ, который рабита пытался посоветовать, хотя он явно очень узко на мир смотрит.
27 сен 18, 13:47    [21688153]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
TaPaK
Member

Откуда: Kiev
Сообщений: 6801
Alew,

Минусуют потому что никто не понимает что же вы хотите/спрашиваете. Ну я так точно
27 сен 18, 13:51    [21688157]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
256k
Member

Откуда: с.Торчилово, Псковская обл.
Сообщений: 437
Alew
Спасибо, за ответы. Отвлекся немного, думал, при ответах будут уведомления на почту

Т-Миронов , почему вы думаете, что это баг клиета, а не спицифика самого сервера? Больше то похоже как раз на последнего.

Владимир Затуливетер , TaPaK
Даже не пытался закладываться на отсутствие реальных гэпов. Проблема то как раз в том, что фактически гэпов нет, а в ответе они есть. И попытка усились транзакции эффекта не дает.
Почему минусуют это отдельный вопрос, но, в данном случае, я вижу это по другому, минус бы в предыдущей версии вопроса, после чего я его уже полностью переписал и новая версия уже содержит в себе все что нужно, но при этом даунвойтер не соизволил пересмотреть свою оценку. Хотя вопрос вполне конкретный и проделанный ресерч приложен как в комментах советовали.

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


а чем Брокер не устаивает?
27 сен 18, 14:09    [21688182]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
invm
Member

Откуда: Москва
Сообщений: 9349
Alew
Т-Миронов , почему вы думаете, что это баг клиета, а не спицифика самого сервера? Больше то похоже как раз на последнего.
Специфика сервера возможна если бы в запросе не указывалось предложение order by. Поэтому, скорее всего, это специфика Dapper.

Если ваш проверочный запрос не показал наличия разрывов последовательности, то для начала измените свой тест:
1. Модифицируйте запрос
SELECT *, case when OrderingKey > lag(OrderingKey) over (order by OrderingKey) + 1 then 1 else 0 end as GapFlag FROM dbo.IntegrationCommandLog WHERE OrderingKey > @OrderingKey ORDER BY OrderingKey;
2. В приложении проверяйте наличие значений GapFlag <> 0
27 сен 18, 14:21    [21688191]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
TaPaK
Alew,

Минусуют потому что никто не понимает что же вы хотите/спрашиваете. Ну я так точно


Вот тут есть еще одна проблем, я задаю вполне конкретный вопрос и хочу получить ответ в строго заданных рамках, потому что так будет проще и быстрее. Если же ответов не будет, то тогда я задам следующий, более высокоуровневый вопрос. Вот ровно так было и в этом случае. В противном случае ответ не будет соответствовать тексту вопроса буквально. Периодически я сталкиваюсь этой проблемой, где мне в комментариях пишут, чтобы я озвучил более высокоуровневую проблему, но думаю, что тут надо комментарий минусовать, а не вопрос, потому что человек не знает как ответить на вопрос, но готов подумать как решить проблему на другом уровне. Я сам могу решить проблему на другом уровне, но об этом думать преждевременно, пока я получу или не получу ответ на текущий вопрос. Подозреваю, что 22 балла репутации намекают на джуна и люди хотят помочь из лучших побуждений, но зачем тогда минусовать?

256k
а чем Брокер не устаивает?


Может и устраивает, я с ним раньше не сталкивался. Просто это более дорогое в плане затрат на реализацию решение, в идеале, хотелось бы обойтись тюнингом запроса. Хотя, как предложение вполне.
27 сен 18, 15:53    [21688307]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
invm


Проблема в том, что там есть еще одно поле, по которому приходится фильтровать и проверить наличие гэпов фактически невозможно. Я пока решил тем что перезапрашиваю данные повторно если их метка времени меньше пары секунд, в надежде что 2+ секундные данные уж точно в запрос попадут.
27 сен 18, 16:07    [21688327]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
invm
Member

Откуда: Москва
Сообщений: 9349
Alew
Проблема в том, что там есть еще одно поле, по которому приходится фильтровать и проверить наличие гэпов фактически невозможно.
Т.е. опубликованный тест и полученные результаты не соответствуют друг-другу?
27 сен 18, 16:29    [21688358]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
invm,

не уверен, что понял вопрос. Тест на отсутствие пропусков
SELECT top 100 * FROM (SELECT *, rowid = ROW_NUMBER() OVER (ORDER BY OrderingKey) FROM [dbo].[IntegrationCommandLog]) l1
JOIN (SELECT *, rowid = ROW_NUMBER() OVER (ORDER BY OrderingKey) FROM [dbo].[IntegrationCommandLog]) l2 on l1.rowid + 1 = l2.rowid
WHERE l1.OrderingKey + 1 != l2.OrderingKey
говорит что пропусков нет, но он используется уже после, чтобы убедиться что те пропуски, которые были записаны в лог, в БД отсутствуют. То что вы предлагаете, поле для гэпа, не будет работать в моем случае, потому, что реальный запрос содержит фильтр и выборка будет не сплошной, т.о. ответ будет содержать гэпы, но это будут правильные гэпы.
1 окт 18, 19:58    [21691807]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
invm
Member

Откуда: Москва
Сообщений: 9349
Alew
То что вы предлагаете, поле для гэпа, не будет работать в моем случае, потому, что реальный запрос содержит фильтр и выборка будет не сплошной, т.о. ответ будет содержать гэпы, но это будут правильные гэпы.
Давайте рассматривать не ваш случай, а то, что было опубликовано на стеке.

Вы утверждаете - результаты запроса с сервера возвращаются либо с нарушенным порядком, либо не полностью.
Как проверить отсутствие нарушений последовательности в результате запроса я уже показал.
Проверить сколько строк вернул запрос можно с помощью методов SqlConnection ResetStatistics/RetrieveStatistics

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

Фрагмент
SET NOCOUNT ON;
INSERT INTO [dbo].[IntegrationCommandLog] ([Id], [Content], [Topic])
VALUES ( @Id, @Content, @Topic);
SELECT [OrderingKey], [RowVersion]
FROM [dbo].[IntegrationCommandLog]
WHERE @@ROWCOUNT = 1 AND [Id] = @Id
Вызывает вопросы.
Зачем там select? Насколько я вижу, это приводит к наличию в соединении недофетченного набора.
1 окт 18, 21:48    [21691925]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
invm,

я применил ваши советы и получилось, что результаты GapFlag и проверка на уровне приложения полностью совпадают.
Статистика тоже совпадает. Получается что это специфика сервера.
7 окт 18, 07:23    [21697211]     Ответить | Цитировать Сообщить модератору
 Re: Как починить этот код?  [new]
Alew
Member

Откуда:
Сообщений: 9
Селект в инсерте присутствует, чтобы обновлять сущность в приложении. Так делает entity framework для версионируемых сущностей.
Пробовал убрать селект, без влияния на результат.
7 окт 18, 13:52    [21697338]     Ответить | Цитировать Сообщить модератору
Все форумы / Microsoft SQL Server Ответить