Doctrine 2 EntityManager приводит к потере времени при первом запросе - PullRequest
0 голосов
/ 23 июля 2011

Недавно я интегрировал Doctrine 2 ORM в CodeIgniter 2. Я настроил Doctrine 2 как библиотеку и автоматически загрузил ее в CodeIgniter.На странице я создаю экземпляр менеджера сущностей доктрины следующим образом:

private static $em = null;

public function __construct() {
    parent::__construct();
    $this->em = $this->doctrine->em;
}

А затем начинаю использовать Entity Manager, когда это необходимо.У меня проблема в том, что при каждом запросе страницы Entity Manager требуется некоторое время для инициализации (примерно 1 секунда).Это заставляет пользователя ждать, пока страница загрузится.Ниже вы можете увидеть некоторые результаты производительности, которые я измерил:

BENCHMARKS  
Loading Time: Base Classes          0.0166
Doctrine                            0.0486
GetArticle                          1.0441
Functions                           0.0068
Controller Execution Time           1.1770
Total Execution Time                1.1938

Функция GetArticle в основном выполняет вызов EntityManager-> find ():

$currentart = $this->em->find('Entities\Article', $artid);

Мне нужно подождать эту 1 секундуесли я использую метод EntityManager-> createQuery ().

На каждой странице из-за первого запроса EntityManager потеря времени составляет примерно 1 секунду.

Это часто встречается?

Эта 1 секунда проистекает из того факта, что EntityManager должен установить соединение с БД?Функции / запросы после первого запроса довольно быстрые.

1 Ответ

1 голос
/ 25 июля 2011

Самое трудоемкое, что делает Doctrine - это загрузка метаданных для ваших сущностей, будь то аннотации, XML или YAML.Doctrine lazy загружает метаданные, когда это возможно, поэтому вы не увидите снижения производительности, пока не начнете использовать сущности.Поскольку метаданные не изменяются, если вы не вносите изменения в свой код, Doctrine позволяет кэшировать метаданные между запросами.DQL-запросы также необходимо анализировать в SQL, поэтому Doctrine предоставляет для этого другую конфигурацию кэширования.

В производственной среде вы должны настроить эти кэши (похоже, что вы уже это сделали, но для других, читающих это):

$cache = new \Doctrine\Common\Cache\ApcCache(); // or MemcacheCache $configuration->setMetadataCachImpl($cache); // caches metadata for entities $configuration->setQueryCachImpl($cache); // caches SQL from DQL queries

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

$em->getMetadataFactory()->getAllMetadata();

Еще одним потенциальным узким местом является генерация прокси-классов.Если это не настроено правильно в производственной среде, Doctrine будет генерировать классы и сохранять их в файловой системе при каждой загрузке страницы.Эти прокси-классы не изменяются, если не изменяется код объекта, поэтому для этого снова нет необходимости.Чтобы ускорить процесс, вы должны сгенерировать прокси с помощью инструмента командной строки (orm: generate-proxies) и отключить автогенерацию:

$configuration->setAutoGenerateProxyClasses(false);

Надеюсь, это вам поможет.Дополнительную информацию можно найти по адресу http://www.doctrine -project.org / docs / orm / 2.0 / en / reference / улучшение-performance.html # bytecode-cache

...