Использование ITransaction
с IsolationLevel.Serializable
должно сделать эту работу. Однако будьте осторожны в борьбе за стол. Если у вас есть высокочастотные обновления на столе, вещи могут сильно замедлиться. Возможно, вы захотите профилировать попадание в БД при использовании GetMaxNumber()
.
Мне пришлось сделать что-то похожее, чтобы сгенерировать пользовательских идентификаторов для обеспечения высокого уровня параллелизма. Мое решение перенесло генерацию идентификатора в базу данных и использовало отдельную таблицу Counter
для хранения максимальных значений.
Использование отдельной таблицы Counter
имеет пару плюсов:
- Устраняет конфликт в таблице
Order
- Обычно быстрее
- Если он достаточно мал, его можно закрепить в памяти
Я также использовал сохраненный процесс для возврата следующего доступного идентификатора:
SET TRANSACTION ISOLATION LEVEL SERIALIZABLE
BEGIN TRAN
UPDATE [COUNTER] SET Value = Value + 1 WHERE COUNTER_ID = @counterId
COMMIT TRAN
RETURN [NEW_VALUE]
Надеюсь, это поможет.