mvc-mini-profiler замедляет Entity Framework

Я установил mvc-mini-profiler для моего сайта MVC 3 на базе Entity Framework. Все настроено должным образом; Запуск профилирования в Application_Start, завершение в Application_End и так далее. Часть профилирования работает нормально.

Однако, когда я пытаюсь поменять местами создание объекта модели данных на предоставление профилируемых версий, производительность резко падает. Не каждый SQL-запрос, но некоторые запросы занимают примерно 5-кратную загрузку всей страницы. (Самая первая загрузка страницы после запуска IIS Express занимает немного больше времени, но это продолжается.)

Незначительное время (максимум ~ 2 мс) тратится на запросы, выполнение и "чтение данных" SQL, в то время как эта строка:

var person = dataContext.People.FirstOrDefault(p => p.PersonID == id);

... при заключении в с использованием (profiler.Step ()) записывается как занимающая 300-400 мс. Я профилировал с помощью dotTrace, который подтвердил, что время на самом деле тратится в EF как обычно (профилируемые компоненты появляются очень кратко), только это занимает гораздо больше времени.

Это заставляет меня полагать, что соединение или его часть в составных частях отсутствует достаточное количество данных, из-за чего EF работает намного хуже.

Это то, что я использую для создания объекта контекста (класс моей модели edmx называется DataContext):

var conn = ProfiledDbConnection.Get(
    /* returns an SqlConnection */CreateConnection());
return CreateObjectContext(conn);

Изначально я использовал mvc-mini-profiler предоставлен метод ObjectContextUtils.CreateObjectContext . Я погрузился в него и заметил, что он устанавливает строку пути к рабочей области метаданных с подстановочными знаками. Поскольку у меня уровень базы данных изолирован для одного проекта и нескольких сайтов MVC, как и для других проектов, использующих код, эти пути изменились, и я бы предпочел быть более конкретным. Кроме того, я думал, что это причина проблемы с производительностью. Я продублировал функциональность CreateObjectContext в моем собственном проекте, чтобы обеспечить это как таковое:

    public static T CreateObjectContext(DbConnection connection) where T : System.Data.Objects.ObjectContext {
        var workspace = new System.Data.Metadata.Edm.MetadataWorkspace(
          GetMetadataPathsString().Split('|'),
          // ^-- returns 
          //  "res://*/Redacted.csdl|res://*/Redacted.ssdl|res://*/Redacted.msl"
          new Assembly[] { typeof(T).Assembly });

        // The remainder of the method is copied straight from the original,
        // and I carried over a duplicate CtorCache too to make this work.
        var factory = DbProviderServices.GetProviderFactory(connection);
        var itemCollection = workspace.GetItemCollection(System.Data.Metadata.Edm.DataSpace.SSpace);
        itemCollection.GetType().GetField("_providerFactory", // <==== big fat ugly hack
            BindingFlags.NonPublic | BindingFlags.Instance).SetValue(itemCollection, factory);
        var ec = new System.Data.EntityClient.EntityConnection(workspace, connection);
        return CtorCache.Ctor(ec);
    }

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

Исчерпав все это, я нахожусь в упадке. Еще раз: когда я просто предоставляю свой контекст данных как обычно, производительность не теряется. Когда я предоставляю «профилируемый» контекст данных, производительность для определенных запросов падает (я тоже не знаю, что на это влияет). Что может сделать mvc-mini-profiler неправильно? Я по-прежнему скармливаю ему неправильные данные?

Думаю, это та же проблема, с которой столкнулся этот человек .

12
задан Community 23 May 2017 в 12:19
поделиться