为什么在 Phalcon 中使用 viewSimple 渲染器会破坏主渲染器

问题描述 投票:0回答:2

首先我声明这样的简单视图:

$di->set('viewSimple', function() {
    $view = new \Phalcon\Mvc\View\Simple();
    $view->setViewsDir('../app/views/');
    $view->registerEngines(array(
        ".volt" => 'volt'
    ));
    return $view;
});

然后生成 html 电子邮件,我使用它如下:

public function renderHTMLEmail($template_name, $template_params) {
    $content = $this->viewSimple->render("emails/$template_name", $template_params);
    return $this->viewSimple->render("emails/master", array( 'content' => $content) );
}

我的电子邮件生成得很好,但是每当我调用我的 renderHTMLEmail 函数时,实际页面渲染就会以某种方式损坏,并且页面显示完全空白(我必须使用重定向作为解决方法)。这对我来说是一个谜,因为主视图渲染器是完全不同的对象。我可以阻止这种情况吗?

或者是否有人推荐在主视图渲染过程之外生成任意 html 片段且不会干扰它的方法? SO 有几个类似的问题,但没有一个解决方案有效。他们要么不生成我的电子邮件,要么破坏主视图。

php phalcon
2个回答
2
投票

找到了一个解决方案,当将“\Phalcon\Mvc\View\Simple”组件注册到 DI 容器中时,请确保使用新的 volt 实例,否则它将以某种方式与应用程序的 \Phalcon\Mvc\View volt 实例结合起来。这是很多(https://stackoverflow.com/users/1672165/lot)在评论中建议的。

代码示例:

public function getTemplate($name, $params)
{
    $parameters = array_merge(array(
        'publicUrl' => $this->getDI()->getApp()->url->host . $this->getDI()->getApp()->url->baseUri
    ), $params);

    $app = $this->getDI()->getApp();

    $this->getDI()->set('simpleView', function() use ($app) {
        $view = new \Phalcon\Mvc\View\Simple();
        $view->setViewsDir(APP_DIR . $app->application->viewsDir);
        $view->registerEngines(array(
            ".volt" => function ($view, $di) {
                $volt = new \Phalcon\Mvc\View\Engine\Volt($view, $di);
                $volt->setOptions(array(
                    'compiledPath'      => APP_DIR . '/cache/volt/',
                    'compiledSeparator' => '_',
                    'compiledExtension' => '.compiled'
                ));
                $compiler = $volt->getCompiler();
                $compiler->addFunction('is_a', 'is_a');
                return $volt;
            }
        ));
        return $view;
    });



    /* @var $simpleView \Phalcon\Mvc\View\Simple */
    $simpleView = $this->getDI()->get('simpleView');

    foreach ($parameters as $key => $value) {
        $simpleView->{$key} = $value;
    }

    $html = $simpleView->render('emails/' . $name, $parameters);

    return $html;
}

示例是直接从我们的工作应用程序中提取的,因此可能需要一些返工,但应该有助于解决原始问题。

这对我来说很有效,使用 \View 作为应用程序 DI 注册的视图组件,它呈现控制器操作伏特视图,上面的 \View\Simple 成功注册了新的伏特电子邮件,并允许使用伏特的原始视图继续。

不久前有人问过这个问题,但我在其他地方没有看到可行的解决方案。

为了完整起见,我已将调查结果注册为 github 问题:https://github.com/phalcon/cphalcon/issues/3096


1
投票

我最近不得不处理一个类似的问题,我不确定你的不足之处,但一件重要的事情是使用与应用程序使用的视图不同的视图 - 你已经在这样做了。看看以下是否有效。

protected function renderView($view, $template, array $data = null)
{
    return $view
        ->reset()
        ->pick('emails/' . $template)
        ->setVars($data)
        ->start()
        ->render(null, null)
        ->finish()
        ->getContent();
}

public function renderHTMLEmail($template_name, $template_params) 
{
    $content = $this->render($template_name, $template_params);
    return $this->render('master', array('content' => $content));
}
© www.soinside.com 2019 - 2024. All rights reserved.