Тайм-аут запроса NHibernate - PullRequest
       0

Тайм-аут запроса NHibernate

1 голос
/ 31 января 2011

Я получаю следующее исключение тайм-аута NHibernate:

could not execute query

с внутренним сообщением об исключении:

Timeout expired.  The timeout period elapsed prior to completion of the operation or the server is not responding.

Это код NHibernate, который не выполняется:

shareClassReturns = _session.CreateCriteria<ShareClassTrailingReturn>()
        .Add(LambdaSubquery.Property<ShareClassTrailingReturn>(x => x.ShareClass.Id).In(GetAvailableShareClassIds()))
        .Add(LambdaSubquery.Property<ShareClassTrailingReturn>(x => x.ShareClass.Id).In(GetShareclassIdsInCalculationGroup(peerGroups, classificationTypes)))
        .Add<ShareClassTrailingReturn>(c => c.CurrencyId == "GBP")
        .AddShareClassReturnOrder(order)
        .CreateCriteria<ShareClassTrailingReturn>(scr => scr.ShareClass, JoinType.InnerJoin)
        .Add(ApplicableIdentifiers(searchExpression))
        .AddShareClassOrder(order)
        .SetMaxResults(pageSize)
        .List<ShareClassTrailingReturn>();

Это SQL, который я вижу с помощью NHibernate Profiler (хотя я немного прибрал его и заменил все элементы, которые я выбрал, на select top 25 *, чтобы сделать его более читабельным):

SELECT   top 25 *
FROM     offline.ShareClassTrailingReturn this_
         inner join ShareManager.ShareClass shareclass1_
           on this_.SCTR_ShareClassId = shareclass1_.ShareClass_Id
         left outer join DCS.ShareClassInfo shareclass1_1_
           on shareclass1_.ShareClass_Id = shareclass1_1_.[ShareClassInfo_MSShareClassId]
WHERE    
    this_.SCTR_ShareClassId in 
    (
        SELECT this_0_.[Fund_ID] as y0_
        FROM   dbo.Fund this_0_
            inner join CAP.DataUniverse datauniver1_
              on this_0_.[Fund_TypeID] = datauniver1_.[DataUniverse_TypeId]
                 and this_0_.[Fund_CountryID] = datauniver1_.[DataUniverse_CountryID]
        WHERE  datauniver1_.[DataUniverse_SiteId] = 100 /* @p0 */
    )
    and this_.SCTR_ShareClassId in 
    (
        SELECT this_0_.ShareClass_Id as y0_
        FROM   dbo.vCalculationGroup this_0_
        WHERE  
            this_0_.PeerGroupId in (1,8)
            and this_0_.ClassificationId in (7,1)
    )
    and this_.SCTR_CurrencyId = 'GBP'
    and 
    (
        shareclass1_.ShareClass_MEX like '%axa%' 
        or shareclass1_.ShareClass_SEDOL like '%axa%'
        or shareclass1_1_.ShareClassInfo_RIC like '%axa%'
        or shareclass1_.ShareClass_ISIN like '%axa%'
        or shareclass1_.ShareClass_CUSIP like '%axa%'
    )
ORDER BY shareclass1_.ShareClass_Name asc

Если я изменю критерии NHibernate, чтобы он не выполнял выборку для vCalculationGroup, т.е. если я удалю эту строку:

.Add(LambdaSubquery.Property<ShareClassTrailingReturn>(x => x.ShareClass.Id).In(GetShareclassIdsInCalculationGroup(peerGroups, classificationTypes)))

или это из SQL

    and this_.SCTR_ShareClassId in 
    (
        SELECT this_0_.ShareClass_Id as y0_
        FROM   dbo.vCalculationGroup this_0_
        WHERE  
            this_0_.PeerGroupId in (1,8)
            and this_0_.ClassificationId in (7,1)
    )

Время запроса больше не истекло.Значит ли это, что мне нужно что-то сделать с этим View?Нравится индексирование или что-то в этом роде?

Может кто-нибудь подсказать, как мне подойти к решению этой проблемы?

Редактировать: Я должен добавить, что запросработает нормально из SQL Server Management Studio и возвращается примерно через 6 секунд.Хотя с учетом сказанного, когда я смотрю на план выполнения, он сообщает, что в автономном режиме отсутствует индекс.ShareClassTrailingReturn.Возможно ли, что это может быть проблемой?

1 Ответ

0 голосов
/ 31 января 2011

Я бы определенно посмотрел на индексирование в представлении, если удаление этой части сделает его лучше. Также стоит проверить время ожидания соединения в вашем приложении. Если вы говорите, что в Management Studio он работает нормально в течение шести секунд, возможно, тайм-аут подключения вашего приложения составляет менее шести секунд (или значение по умолчанию меньше). Это были бы хорошие отправные точки.

В целом стоит избегать множества вложенных подзапросов. У вас есть много в SQL, который производится. Иногда эффективнее написать SQL или HQL самостоятельно, а не использовать множество сложных объединений в API Criteria или Linq NHibernate. У вас больше шансов создать эффективный SQL для этой работы!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...