[Yii2笔记]025文件上传(Uploading Files) [ 技术分享 ]
说明
学习Yii Framework 2(易2框架)的过程是漫长的,也是充满乐趣的,以下是我学习Yii2框架时对官网英文资料(请参见原文网址)的翻译和代码实现,提供了较完整的代码,供你参考。不妥之处,请多多指正!
原文网址:
http://www.yiiframework.com/doc-2.0/guide-input-file-upload.html
本文主题:文件上传(Uploading Files)
在Yii中上传附件通常使用yii\web\UploadedFile,它封装每个上传的文件为一个UploadedFile对象,结合yii\widgets\ActiveForm和模型,你可以很容易的实现安全的文件上传机制。
1、创建模型(Creating Models)
和文本输入框一样,上传单个文件需要先创建一个模型类,并使用一个模型属性来保存上传文件实例,你可能还需要声明一个验证规则去验证上传文件,例如:
namespace app\models;
use yii\base\Model;
use yii\web\UploadedFile;
class UploadForm extends Model{
public $imageFile;
public function rules(){
return [
[['imageFile'],'file','skipOnEmpty'=>false,'extensions'=>'png,jpg'],
];
}
public function upload(){
if($this->validate()){
$this->imageFile->saveAs('uploads/'.$this->imageFile->baseName.'.'.$this->imageFile->extension);
return true;
}else{
return false;
}
}
}
上面的代码中,imageFile属性用于保存上传文件实例,它和file验证规则相关联,使用yii\validators\FileValidator以确保上传文件的扩展名是png或jpg。upload()方法会执行验证并保存上传文件到服务器。 file验证器允许你检查文件扩展名,文件大小,MIME类型,更多细节请参考Core Validators章节: http://www.yiiframework.com/doc-2.0/guide-tutorial-core-validators.html#file
小贴士:如果你上传的是一张图上,你可以使用image验证器,image验证器是yii\validators\ImageValidator,它将验证属性是否接收到了一个有效的图片,然后存储图片或使用Imainge扩展处理它。 Imainge扩展: https://github.com/yiisoft/yii2-imagine
2、渲染文件输入框(Rendering File Input)
下一步,需要在视图中添加一个文件输入框
<?php
use yii\widgets\ActiveForm;
?>
<?php $form = ActiveForm::begin(['options' => ['enctype' => 'multipart/form-data']]) ?>
<?= $form->field($model, 'imageFile')->fileInput() ?>
<button>Submit</button>
<?php ActiveForm::end() ?>
<? 需要记住的是你需要为表单添加一个enctype选项,以正确上传文件。fileInput()将渲染一个标签,这样客户就可以选择文件进行上传。
小贴士:自2.0.8版本起,当有文件输入框时,yii\web\widgets\ActiveField::fileInput将自动添加enctype到表单中。
3、连接起来(Wiring Up)
现在需要在控制器的动作中编写代码将模型和视图连接起来,共同完成文件上传:
namespace app\controllers;
use Yii;
use yii\web\Controller;
use app\models\UploadForm;
use yii\web\UploadedFile;
class SiteController extends Controller{
public function actionUpload(){
$model = new UploadForm();
if (Yii::$app->request->isPost) {
$model->imageFile = UploadedFile::getInstance($model, 'imageFile');
if ($model->upload()) {
// file is uploaded successfully
return;
}
}
return $this->render('upload', ['model' => $model]);
}
}
上述代码中,表单提交时,将调用yii\web\UploadedFile::getInstance()方法创建一个UploadedFile实例来表示上传的文件,然后我们依靠模型验证上传文件的有效性,然后存储文件到服务器。
4、上传多个文件(Uploading Multiple Files)
注意:多文件上传按钮点击后,要过一会儿才能弹出文件选择窗口,选中后、保存时也会等待较长时间。
//maxFiles,一次可上传的最大文件数 你可以一次上传多个文件,只需要将前述代码进行一些改动即可。 首先你需要调整模型类,在file验证规则中添加maxFiles来限制可上传的最大文件数,将maxFiles设置为0意味着不限制同时上传的文件数量。同时可上传的文件最大数量也受PHP的参数max_file_uploads的限制,其默认值是20。 其次还需要将upload()方法修改,将多个上传的文件一个一个进行处理。
namespace app\models;
use yii\base\Model;
use yii\web\UploadedFile;
class UploadForm extends Model{
/**
* @var UploadedFile[]
*/
public $imageFiles;
public function rules(){
return [
[['imageFiles'], 'file', 'skipOnEmpty' => false, 'extensions' => 'png, jpg', 'maxFiles' => 4],
];
}
public function upload(){
if ($this->validate()) {
foreach ($this->imageFiles as $file) {
$file->saveAs('uploads/' . $file->baseName . '.' . $file->extension);
}
return true;
} else {
return false;
}
}
}
在视图文件中,你需要在fileInput()中添加multiple选项,这样表单上传框才能接受多个文件。
<?php
use yii\widgets\ActiveForm;
?>
<?php $form = ActiveForm::begin(['options' => ['enctype' => 'multipart/form-data']]) ?>
<?= $form->field($model, 'imageFiles[]')->fileInput(['multiple' => true, 'accept' => 'image/*']) ?>
<button>Submit</button>
<?php ActiveForm::end() ?>
最后,需要在控制器的动作中调用UploadedFile::getInstances(),而不是UploadedFile::getInstance(),这样就可以将一个UploadedFile数组实例赋给UploadedForm::imageFiles。
namespace app\controllers;
use Yii;
use yii\web\Controller;
use app\models\UploadForm;
use yii\web\UploadedFile;
class SiteController extends Controller{
public function actionUpload(){
$model = new UploadForm();
if (Yii::$app->request->isPost) {
$model->imageFiles = UploadedFile::getInstances($model, 'imageFiles');
if ($model->upload()) {
// file is uploaded successfully
return;
}
}
return $this->render('upload', ['model' => $model]);
}
}
(全文完)
阿江
最后登录:2024-03-03
在线时长:186小时21分
- 粉丝94
- 金钱16816
- 威望160
- 积分20276