Я использую расширение Yii2 и Kartik FileInput, и я успешно загружаю файлы (только для одной загрузки). Моя проблема заключается в том, что я получаю ошибку, как в заголовке (с прикрепленными журналами), если я не выбрал никаких файлов (он должен быть необязательным).
После долгих поисков через Интернет, я думаю, что это должно быть чем-то связано с массивом, но я не уверен, как это исправить, особенно даже с журналами, указывающими на точную строку!
Вот мой журнал,
Вот моя модель,
namespace app\models; use Yii; class FormMovement extends \yii\db\ActiveRecord { public $file; public static function tableName() { return 'form_movement'; } public function rules() { return [ [['fm_date_received', 'fm_form_name', 'fm_from', 'fm_ptj'], 'required'], [['form_id'], 'integer'], [['fm_date_received', 'fm_date_action1', 'fm_date_action2','fm_upload'], 'safe'], [['fm_form_name', 'fm_note'], 'string', 'max' => 500], [['fm_from', 'fm_ptj', 'fm_action1', 'fm_action2'], 'string', 'max' => 100], [['file'], 'file', 'skipOnEmpty' => true, 'extensions'=>'jpg,pdf,png,doc,docx,xls,xlsx, jpeg', 'maxFiles' => 3], ]; }
Моя функция контроллера, журнал показывает, что он находится на линии 75, которая является этой,
$model->fm_upload='uploads/'.$fileName.'.'.$model->file->extension;
Возился с ним, но без успеха.
public function actionCreate() { $model = new FormMovement(); if ($model->load(Yii::$app->request->post())) { //set the file name $fileName = $model -> fm_form_name; //get instance $model->file = UploadedFile :: getInstance($model, 'file'); //set the file path in the db $model->fm_upload='uploads/'.$fileName.'.'.$model->file->extension; //save the file to the server directory $model->save(); $model->file->saveAs('uploads/'.$fileName.'.'.$model->file->extension); return $this->redirect(['view', 'id' => $model->form_id]); } else { return $this->render('create', [ 'model' => $model, ]); } }
Наконец, мой взгляд,
<div class="form-group kv-fieldset-inline"> <?= Html::activeLabel($model, 'file[]', [ 'label'=>'MUAT NAIK FAIL', 'class'=>'col-sm-1 control-label' ]) ?> <div class="col-sm-8"> <?= $form->field($model, 'file',[ 'showLabels'=>false ])->widget(FileInput::classname(), [ 'options' => ['accept' => 'file/*', 'multiple' => 'true'], 'pluginOptions'=>[ 'showUpload' => false, ] ]) ?> </div> </div>
Эта часть должна быть реорганизована:
//set the file name $fileName = $model -> fm_form_name; //get instance $model->file = UploadedFile :: getInstance($model, 'file'); //set the file path in the db $model->fm_upload='uploads/'.$fileName.'.'.$model->file->extension; //save the file to the server directory $model->save(); $model->file->saveAs('uploads/'.$fileName.'.'.$model->file->extension);
как это:
$model->file = UploadedFile::getInstance($model, 'file'); $model->save(); if ($model->file) { $model->fm_upload = "uploads/{$model->fm_form_name}.{$model->file->extension}"; $model->file->saveAs("uploads/{$model->fm_form_name}.{$model->file->extension}"); }
Также обратите внимание, что вы вообще не обрабатываете неудачную проверку в своем контроллере.
Для дальнейшей реорганизации эта строка:
$model->file = UploadedFile::getInstance($model, 'file');
можно переместить в обработчик события beforeValidate()
.
Эта часть:
if ($model->file) { $model->fm_upload = "uploads/{$model->fm_form_name}.{$model->file->extension}"; $model->file->saveAs("uploads/{$model->fm_form_name}.{$model->file->extension}"); }
может быть перемещен в обработчик события afterSave()
чтобы ваш контроллер был тонким.
В saveAs()
лучше использовать псевдоним, я описал его в этом ответе .