【问题标题】:Getting a "Headers already sent" error in Yii when rendering a view in beforeAction在 beforeAction 中渲染视图时,在 Yii 中出现“标头已发送”错误
【发布时间】:2018-10-25 13:10:16
【问题描述】:

我已经阅读了有关 Yii2 的处理程序的信息,但我不知道如何在这种情况下正确使用它们。

基本上在我的SiteController,我有:

class SiteController extends \app\components\Controller
{
    public function beforeAction($action)
    {
        // Makes some checks and if it's true, will render a file and stop execution of any action
        if (...)
            echo $this->render('standby');
            return false;
        }
        return true;
    }

    // All my other actions here
}

这似乎运行良好并停止执行,但是我得到 render() 行的“标头已发送”,就好像它正在执行重定向一样。

如果我写 Yii::$app-end() 而不是 return false,也会发生同样的事情。

如果我写exit(); 而不是return false,则不会显示异常,但调试面板不会显示,因为 Yii 没有正确终止。

我尝试删除 echo $this->render(..) 并导致一个空白页面,没有任何重定向,这似乎只是 Yii 抱怨我从 Controller 中回显内容。

当然我不能返回 render() 或返回 true 的结果,因为它会执行页面的操作,我试图避免并在此结束。

我知道在 beforeAction() 中返回 false 会触发 EVENT_BEFORE_ACTION,但我不知道应该在哪里使用它。 events documentation 并没有真正帮助我。

那么有没有办法显示“待机”视图,防止执行其他操作并避免从Controller回显的错误消息?

请注意,我正在尝试完成这项工作,而不必在每个操作方法中复制代码来检查 beforeAction() 的结果是否为假。

【问题讨论】:

  • 您是否有理由不只是使用重定向?

标签: yii yii2


【解决方案1】:

从 Yii 2.0.14 开始,您无法在控制器中回显 - 必须通过操作返回响应。如果要在beforeAction() 中生成响应,则需要设置Yii::$app->response 组件而不是回显内容:

public function beforeAction($action) {
    // Makes some checks and if it's true, will render a file and stop execution of any action
    if (...) {
        Yii::$app->response->content = $this->render('standby');
        Yii::$app->response->statusCode = 403; // use real HTTP status code here

        return false;
    }

    return parent::beforeAction($action);
}

不要忘记调用parent::beforeAction($action) - 省略它会导致意外且难以调试的行为。

【讨论】:

  • 直截了当,简单,干净,解释清楚。谢谢先生,希望我能投票两次!并特别感谢您标记我关于不调用父方法的错误
  • 确切地说,yii 2 通常不允许在控制器操作(如渲染输出)中发送原始输出,因为它之后会尝试发送有关响应类型的标头,但就在之后。在这种情况下,php通常会抱怨第一次出现的输出,但它并没有说明Yii中是否以及在哪里调用了“headers”函数
猜你喜欢
  • 2013-08-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-30
  • 1970-01-01
  • 2021-06-15
相关资源
最近更新 更多