Laravel 4 с использованием nikic phpparser: не хватает памяти при отправке электронной почты

Только что узнал, что Laravel использует nikic phpparser изнутри.

Я изменил свой код для отправки электронных писем на одном из условий, и он начал умирать.
Логи PHP показали это:

[Сб. 03.10 21:18:23 2015] [error] [client xx.xx.xx.xx] Неустранимая ошибка PHP: допустимый объем памяти 33554432 байта исчерпан (попытка выделить 1048576 байтов) в /home/yyyy/public_html/vendor/nikic/php-parser/lib/PHPParser/NodeTraverser.php в строке 66, реферер: http://yyyy.com/home

Временно я увеличил память, чтобы решить проблему.
Но я хочу отойти от пластыря.
Я вижу, что функция NodeTraverser выполняет клонирование, это может вызвать проблемы:

   protected function traverseNode(PHPParser_Node $node)
   {

    ini_set('memory_limit', '64M'); // temporary fix
    $node = clone $node;

    foreach ($node->getSubNodeNames() as $name) {
        $subNode =& $node->$name;

        if (is_array($subNode)) {
            $subNode = $this->traverseArray($subNode);
        } elseif ($subNode instanceof PHPParser_Node) {
            foreach ($this->visitors as $visitor) {
                if (null !== $return = $visitor->enterNode($subNode)) {
                    $subNode = $return;
                }
            }

            $subNode = $this->traverseNode($subNode);

            foreach ($this->visitors as $visitor) {
                if (null !== $return = $visitor->leaveNode($subNode)) {
                    $subNode = $return;
                }
            }
        }
    }

    return $node;
}

Вот как я отправляю письмо. Это ничем не отличается от других, поэтому я сомневаюсь, что это вызовет проблему:

                 $this->mailer->queue('emails.forreg',
                        [
                            'toName' =>  $toEmailName,
                            'fromName' =>  $user->username,
                            'site_name' => \Config::get('site_title')
                        ],
                        function($mail) use($toEmailAddress, $user, $subject_to_send, $toEmailName)
                        {
                            $mail->to($toEmailAddress, $toEmailName)
                                ->subject($subject_to_send)
                                ->from('xxx@yyy.com', $user->username);
                        }
                    );

Любые идеи о том, как решить эту проблему?

1 ответ

Решение

У вас просто крайне низкий предел памяти. PHP ограничение IIRC начинается с 128M по умолчанию. Когда анализатор проходит через это, он создает узел для каждой отдельной части кода. Ничто не исключено, и нет быстрого исправления.

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

Другие вопросы по тегам