问题
I am integrating yii2-formwizard for tabular input but unable to submit the data to my controller action and use Model::loadMultiple
.
I have to declare my model as array and then I need to initialize it before passing to view and in buttflattery/yii2-formwizard
front-end I must specify my model as array fine but I can not retrieve data from my controller dynamically.
I need to dynamically create instance from front-end and save them in back end. I can save only the instance I have initialize from my controller.if I do not initialize only first one instance saved.and also when I initialize multiple instance using for loop, front end replicate for all instance at once which again I do not need.
//controller
public function actionCreatemulti()
{
$this->layout='layout2';
$education = [new Edusubject()];
//## initialize array for 2 element (if I not initialize only one object pass or saved)
for ($i=0; $i < 2 ; $i++) {
$education[]= new Edusubject();
}
//## Model::loadMultiple --> works only if $education is declared as array
if (Model::loadMultiple($education, Yii::$app->request->post()) && Model::validateMultiple($education)) {
foreach ($education as $edu) {
$edu->save(false);
}
return $this->render('dummy');
}
return $this->render('createmulti', [
'education' => $education,
]);
}
FormWizard code in my View
<?php
echo FormWizard::widget(
[
'formOptions' => [
'id' => 'my_form_tabular'
],
'steps' => [
[
//should be a single model or array of Activerecord model objects but for a single model only see wiki on github
'model' => $education, //## here I canot declared array again as I pass an array alredy from controller
//set step type to tabular
'type' => FormWizard::STEP_TYPE_TABULAR,
when i declare model as array in my view i can get dynamic form as described in wiki but I can not save this array since I can not implement yii2 Collecting tabular input as described, on the other hand if I declare model as array and initialize it and send to front end then form is not dynamic. it is shown all instance in form so I need not press "add" button, which I do not need.
回答1:
I developed this widget but before i suggest you anything you should read about the basic implementation of the tabular inputs although the guide is'nt completely helpful there are portions that are still under TBD
and code sample for inserting/creating tabular data into the table isnt added yet with that much detail, but it is always better to look into the source method, after all we are Engineers and we should be able to understand the implementation of any function either a part of framework core or of a separate file.
Addressing Problems
Now about the issue, you have no reason to use the for loop that you have added on top of your action
for ($i=0; $i < 2 ; $i++) {
$education[]= new Edusubject();
}
You took that part from the guide here and copy-pasted it as is in your code ¯\_(ツ)_/¯ .
This part of code in the guide is for the understanding only how the tabular models array should be populated and then provided for loading and validating while creating new records.
Understanding
We need to load and validate the tabular inputs via
- Model::loadMultiple($models,$attributes)
- Model::validateMultiple($models)
Both of them take $models
array as 1st parameter which should hold the instances of the models to be loaded/validated.
For loadMultiple($models, $attributes)
remember that it will load all the attributes specified in the $attributes
array into each of the models specified in the $models
array, and all of those models need to be of the same class. the $attributes
array can be one of $_POST
or $_GET
or any other valid array, see the docs for details.
For validateMultiple($models)
it can be different models or same, it will call validate()
on each model in the $models
array.
Implementation
So you need to change it to below
public function actionCreatemulti()
{
$this->layout='layout2';
$education = [new Edusubject()];
//cehck if post request
if(Yii::$app->request->isPost){
//get total models submitted
$count = count(Yii::$app->request->post('Edusubject',[]));
//start the loop from 1 rather than 0 and use the $count for limit
for ($i=1; $i < $count ; $i++) {
$education[]= new Edusubject();
}
if (
Model::loadMultiple($education, Yii::$app->request->post())
&& Model::validateMultiple($education)
) {
foreach ($education as $edu) {
$edu->save(false);
}
return $this->render('dummy');
}
}
return $this->render('createmulti', [
'education' => $education,
]);
}
and in your view the model
property in the FormWizard
will look like below
'model' => $education,
I just tested it on localhost and it loads, validates and saves correctly.
来源:https://stackoverflow.com/questions/57713074/yii2-saving-tabular-data-using-yii2-formwizard