Огромные вставки и система замедляются с NH3 - PullRequest
1 голос
/ 07 марта 2011

Мне нужно вставить дочерний элемент в объект, выбранный из базы данных, и сохранить обновленный объект.

Нет. юридических лиц: 10000 Число детей: 17000 (один или несколько дочерних объектов, а не 17000 для каждого объекта ..)

Я пробовал с кешем запросов, но после первых 1000 запросов, которые выполняются по 15 мс каждый, удваивается каждые 1000 вставок.

Я пытался получить все сущности и использовать кеш запросов, но получение 10000 также из кеша ужасно медленно.

Как я могу решить это? Я должен получить запрос сущности по имени, присоединить нового потомка и сохранить его.

EDIT

Я использую один сеанс для всех операций. У меня в основном есть файл в качестве ввода с парами «Имя сущности» | "Детское имя"

В моем пользовательском интерфейсе я создаю Список операций, это AddChildTo (entityName, childName). В моем сервисе за WCF я перечисляю все операции и для каждой извлекаю сущность на основе entityName, создаю новый дочерний элемент на основе childName, добавляю дочерний элемент к сущности и сохраняю сущность.

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

Я создаю секундомер и беру время на 1000 операций. Время удваивается каждые 1000 операций.

Создание метода «Секундомер внутри», который выполняет только запрос для извлечения сущности. Я понимаю, что запрос - это та часть, которая увеличивает итоговый общий итог прошедшего времени.

Это запросы, выполняемые для каждого дочернего элемента:

INSERT INTO Child
       (Codice, EntityId, CabinaUid, ComuneUid, Nota1, Nota2, Nome,
        Descrizione, Master, ColoreMaster, ValidFrom,ValidUntil,
        Uid, EntityType)
VALUES     ('IT022E00355269' /* @p0 */,
        9333 /* @p1 */,
        '00000000-0000-0000-0000-000000000000' /* @p2 */,
        '00000000-0000-0000-0000-000000000000' /* @p3 */,
        NULL /* @p4 */,
        NULL /* @p5 */,
        'IT022E00355269' /* @p6 */,
        'IT022E00355269' /* @p7 */,
        0 /* @p8 */,
        0 /* @p9 */,
        '01/01/0001 00:00:00' /* @p10 */,
        NULL /* @p11 */,
        '5c40f801-489d-459f-81ca-0cb53655e50f' /* @p12 */,
        'Child')

select SCOPE_IDENTITY()

and

SELECT this_.Id           as Id14_0_,
       this_.Codice       as Codice14_0_,
       this_.Interruttore as Interrut4_14_0_,
       this_.CabinaUid    as CabinaUid14_0_,
       this_.ComuneUid    as ComuneUid14_0_,
       this_.Nota1        as Nota7_14_0_,
       this_.Nota2        as Nota8_14_0_,
       this_.Nome         as Nome14_0_,
       this_.Descrizione  as Descriz10_14_0_,
       this_.Master       as Master14_0_,
       this_.ColoreMaster as ColoreM12_14_0_,
       this_.ValidFrom    as ValidFrom14_0_,
       this_.ValidUntil   as ValidUntil14_0_,
       this_.Uid          as Uid14_0_
FROM   Entity this_
WHERE  this_.Nome = 186034 /* @p0 */
       and ((this_.ValidUntil is null 
              or this_.ValidUntil > '01/01/0001 00:00:00' /* @p1 */)
            and this_.ValidFrom <= '01/01/0001 00:00:00' /* @p2 */)

Ответы [ 2 ]

0 голосов
/ 07 марта 2011

Недостаточно информации о том, как вы это делаете, но вот несколько общих советов по работе с большими наборами данных в NH:

  • Если возможно, разделите работу на несколько логических единиц работы(каждый из них является сеансом)
  • Всегда изменяйте режим сброса по умолчанию на что-то отличное от Авто
  • Рассмотрите возможность использования сеансов без сохранения состояния и HQL DML для массовых сценариев
  • Включить ADO.NETпакетирование в базах данных, которые его поддерживают
  • Вместо выполнения 10000 запросов для одного объекта каждый, используйте запросы, которые возвращают большую часть набора данных
  • Используйте профилировщик, чтобы определить, какие у вас узкие места

Не думаю, что кеш запросов поможет вам (возможно, я не понял ваш вариант использования)

0 голосов
/ 07 марта 2011

Для диагностики проблем с производительностью:

  • Сначала проверьте выполняемый SQL-запрос.(опубликуйте здесь)
  • Убедитесь, что вы используете обратную сторону на одной стороне отношений родитель-потомок, взгляните на мой пост NHibernate parent-childs сохранить избыточное обновление sql выполнено
  • Выполнение запросов за один сеанс (вам не нужно использовать какой-то специальный кеш, если все запросы находятся в одной Isession)
  • Использовать транзакцию, например, некоторые базы данных, такие как SQLite, действительно вставляют |обновлять операции быстрее в транзакции.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...