yii2 - Yii2:发送响应内容后刷新()不起作用
问题描述
我有一个ActiveForm
用来从中获取一些数据的工具,当我单击发送按钮时,它将运行模型(在本例中为 csv 文件生成器),但刷新不起作用,当我删除该方法时它会刷新。
经过一些测试后,似乎fputcsv()
会停止脚本,因此之后的所有内容都不会运行。
看法
public function actionIndex()
{
$model = new Export();
if ($model->load(Yii::$app->request->post()) && $model->validate()) {
$fields = Yii::$app->request->post('Export');
\backend\models\Export::generate();//this prevents the refresh
Yii::$app->session->setFlash();
return $this->refresh();
} else {
return $this->render('index' , ['model' => $model]);
}
}
模型
static public function generate()
{
header('Content-Encoding: UTF-8');
header('Content-Type: text/csv; charset=UTF-8');
header('Content-Disposition: attachment; filename="sample.csv"');
header("Pragma: no-cache");
header("Expires: 0");
$data = [array comes here];
$fp = fopen('php://output', 'w') or die("Unable to open file!");
fputs($fp, $bom =( chr(0xEF) . chr(0xBB) . chr(0xBF) ));
foreach ( $data as $line ) {
fputcsv($fp , $line , ';' );
}
stream_get_contents($fp);
fclose($fp);
}
解决方案
Controller::refresh()
使用Location
标题重新加载页面。由于标头需要在内容之前,因此您不能在发送内容后添加新标头。您的Export::generate()
方法发送内容,因此您不能在此之后添加任何标题,因此$this->refresh()
不起作用。
在 Yii 2.0.14 之前,有一个错误,框架简单地忽略了您在发送内容后尝试发送标头。如果你升级 Yii,在这种情况下你应该得到 "nice" 异常。
如果您在下载文件后尝试显示漂亮的页面,那么您的方法是不正确的。您不能真正返回文件,然后重定向到不同的页面。您应该首先显示漂亮的 HTML 页面,并在其中将用户重定向到下载页面(例如通过使用<meta http-equiv="refresh" content="0; url=http://example.com/" />
in head 或创建隐藏表单并通过 JavaScript 提交)。下载文件后,用户将停留在这个漂亮的页面上,所以从用户体验的角度来看,一切都应该没问题。
推荐阅读
- ruby-on-rails - 在 Ruby on Rails 中注册后将用户重定向到
- javascript - 我想在使用 google javascript 登录后同步 google 日历事件
- python-3.x - discord py - 消息删除性能缓慢(多台服务器)
- scala - Scala Jar:使用 DBUtils 读取 Databricks 机密
- r - R中的Pivot_longer()没有分隔符?
- c - 矩阵螺旋图案的一种变体
- python - 不支持为 CharField 查找“xx”或不允许在该字段上加入
- wso2 - WSO2 API Manager 发布者 URL 问题
- reactjs - 在另一个 Mutation 中使用 Mutation 的结果
- flutter - Flutter MultiProvider 或 ChangeNotifier 没有响应