2008-11-13 5 views
5

У нас есть система, которая одновременно вставила большой объем данных с нескольких станций, одновременно выставляя интерфейс запросов данных. Схема выглядит примерно так (извините о плохом форматировании):Уровень транзакции, nolock/readpast и параллелизм

[SyncTable] 
    SyncID 
    StationID 
    MeasuringTime 


[DataTypeTable] 
    TypeID 
    TypeName 


[DataTable] 
    SyncID 
    TypeID 
    DataColumns... 

вставка данных осуществляется в «Синхронизация» и выглядит следующим образом (мы только вставить данные в систему, мы никогда не обновлять)

INSERT INTO SyncTable(StationID, MeasuringTime) VALUES (X,Y); SELECT @@IDENTITY 

INSERT INTO DataTable(SyncID, TypeID, DataColumns) VALUES 
    (SyncIDJustInserted, InMemoryCachedTypeID, Data) 
    ... lots (500) similar inserts into DataTable ... 

и запросов выглядит следующим образом (для данной станции, measuringtime и тип данных)

SELECT SyncID FROM SyncTable WHERE StationID = @StationID 
           AND MeasuringTime = @MeasuringTime 
SELECT DataColumns FROM DataTable WHERE SyncID = @SyncIDJustSelected 
            AND DataTypeID = @TypeID 

Мой вопрос заключается в том, как мы можем совместить уровень транзакций на вставках и NOLOCK/READPAST намеки на запросы, так что:

  1. Мы максимально параллелизм в нашей системе, а в пользу вставок (нам нужно хранить много данных, что-то столь же высоко, как 2000+ записывает второй)
  2. Запросы только возврат данные из «фиксированной» синхронизации (мы не хотим, чтобы набор результатов с половинной вставленной синхронизацией или синхронизация с некоторыми пропущенными записями из-за блокировки)
  3. Нам все равно, включены ли «новейшие» данные в запрос, мы больше заботимся о согласованности и отзывчивости, а затем для «живых» и актуальных данных.

Это может быть очень противоречивые цели и может потребовать высокий уровень изоляции транзакций, но меня интересуют все трюки и оптимизации для достижения высокой отзывчивости как для вставок, так и для выбора. Я с удовольствием расскажу, нужны ли дополнительные детали, чтобы очистить больше трюков и трюков.

ОБНОВЛЕНИЕ: просто добавьте немного больше информации для будущих ответов. В настоящее время мы запускаем SQL Server 2005 (2008 в течение шести месяцев) в сети SAN с 5+ ТБ хранилища. Я не уверен, какой RAID-массив настроен и точно, сколько у нас дисков.

ответ

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

  2. Не могли бы вы обернуть вставки в транзакции, что сделало бы их недоступными для чтения до тех пор, пока вставка не будет закончена?

  3. Это должно произойти, если ваше оборудование настроено правильно, и вы обращаете внимание на свое SQL-кодирование, которое вам кажется.

Посмотрите в SQLIO.exe и SQL Stress инструменты:

SQLIOStress.exe SQLIOStress.exe имитирует различные модели поведения/вывода SQL Server 2000 I, чтобы обеспечить элементарную безопасность I/O.

Утилиту SQLIOStress можно загрузить с веб-сайта Microsoft. См. Следующую статью.

• Как использовать SQLIOStress утилиту для стресса дисковой подсистемы, таких как SQL Server http://support.microsoft.com/default.aspx?scid=kb;en-us;231619

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

SQLIO.exe SQLIO.exe - это утилита ввода-вывода SQL Server 2000, используемая для установления базовых результатов тестирования.

Утилиту SQLIO можно загрузить с веб-сайта Microsoft. Смотрите следующее: • SQLIO Performance Testing Tool (SQL Development) - Клиент Доступные http://download.microsoft.com/download/f/3/f/f3f92f8b-b24e-4c2e-9e86-d66df1f6f83b/SQLIO.msi

+0

Отметить это как ответ, так как часть «решения» была привязана к правильной настройке конкретной дисковой системы, что значительно улучшило пропускную способность. – 2009-10-14 09:03:10

1

Если вы работаете SQL 2005 и выше взгляд в реализации snapshot isolation. Вы не сможете получить последовательные результаты с помощью nolock.

Решение этого вопроса на SQL 2000 намного сложнее.

1

Это отличный сценарий для SQL Server 2005/2008 Enterprise Partitioning. Вы можете создать раздел для каждого StationID, и данные каждого StationID может перейти в свою собственную группу файлов (если вы хотите, не могут быть необходимыми в зависимости от нагрузки.)

Это покупает вам некоторые преимущества с параллелизмом:

  • Если вы разделяете файл stationid, то пользователи могут запускать отдельные запросы для файлов, которые в настоящее время не загружаются, и они вообще не будут запускать какие-либо проблемы с параллелизмом.
  • Если вы разбиваете на stationid, то несколько станций могут вставлять данные одновременно без проблем параллелизма (при условии, что они находятся в разных файловых группах)
  • Если вы разделяете диапазон синхронизации, то вы можете поместить старые данные в более медленное хранилище.
  • Если вы разделите на syncid диапазона, и если ваши диапазоны достаточно малы (то есть не ряд с тысячами syncids), то вы можете сделать нагрузки в то же время пользователей запрашивают, не сталкиваясь параллелизм вопросами

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

http://www.microsoft.com/technet/prodtechnol/sql/2005/projreal.mspx

Разметка еще лучше в SQL Server 2008, особенно вокруг параллелизма. Это еще не серебряная пуля - она ​​требует ручного проектирования и обслуживания квалифицированным администратором баз данных. Это не функция set-it-and-forget-it, и для нее требуется Enterprise Edition, стоимость которой превышает стандартную версию. Мне это нравится, хотя я использовал его несколько раз, и он решил конкретные проблемы для меня.

+0

Еще одно преимущество раздела по stationid: если вы создадите нужные кластерные индексы (stationid, syncid) на syncable, (syncid) на datatable и использовать идентификатор для syncid, вы никогда не получаете разбиений на страницы из активности вставки, что позволяет использовать READPAST для операторов select, которые тогда не мешают вообще вставке (они не 't ждать, чтобы получить свои S-блокировки для записей с блокировкой X и без обновлений, никакие X-блокировки не выдаются для любых S-заблокированных строк). Если раскол страницы был возможен, READPAST иногда может приводить к непоследовательным результатам, делая это опасным вариантом. – TToni 2013-09-09 15:41:43