[[+content_image]]
M
M
MaikMain2020-12-18 15:39:53
Yii
MaikMain, 2020-12-18 15:39:53

Yii2. Extracting data from related tables?

Good afternoon. There was a problem with outputting data from related tables to the form.
MotoOption - Table with option names

spoiler

public function rules()
    {
        return [
            [['name','moto_option_category_id'], 'required'],
            [['name'], 'string', 'max' => 100],
        ];
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOptionTypes()
    {
        return $this->hasMany(MotoOptionType::className(), ['moto_option_id' => 'moto_option_id']);
    }

    public function getMotoOptionValue()
    {
        return $this->hasMany(MotoOptionValue::className(), ['moto_option_id' => 'moto_option_id']);
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOptionCategory()
    {
        return $this->hasOne(MotoOptionCategory::className(), ['moto_option_category_id' => 'moto_option_category_id']);
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotorcycleOptionValue()
    {
        return $this->hasMany(MotorcycleOptionValue::className(), ['moto_option_id' => 'moto_option_id']);
    }
}


MotoOptionValue - table with values ​​for options
spoiler

public function rules()
    {
        return [
            [['moto_option_id', 'name'], 'required'],
            [['moto_option_id'], 'integer'],
            [['name'], 'string', 'max' => 100],
            [['moto_option_id'], 'exist', 'skipOnError' => true, 'targetClass' => MotoOption::className(), 'targetAttribute' => ['moto_option_id' => 'moto_option_id']],
        ];
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOption()
    {
        return $this->hasOne(MotoOption::className(), ['moto_option_id' => 'moto_option_id']);
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOptionValue()
    {
        return $this->hasMany(MotorcycleOptionValue::className(), ['moto_option_value_id' => 'moto_option_value_id']);
    }
}


MotorcycleOptionValue - connecting table: motorcycle, options and option values
spoiler

/**
 * This is the model class for table "motorcycle_option_value".
 *
 * @property int $motorcycle_option_value_id
 * @property int $motorcycle_id
 * @property int $moto_option_id
 * @property int $moto_option_value_id
 *
 * @property Motorcycle $motorcycle
 * @property MotoOption $motoOption
 * @property MotoOptionValue $motoOptionValue
 */
class MotorcycleOptionValue extends \yii\db\ActiveRecord
{
    const SCENARIO_TABULATOR = 'tabular';

    public static function tableName()
    {
        return 'motorcycle_option_value';
    }

    public function rules()
    {
        return [
            [['motorcycle_id', 'moto_option_id'], 'required'],
            [['moto_option_value_id'], 'required', 'except' => self::SCENARIO_TABULATOR],
            [['motorcycle_id', 'moto_option_id', 'moto_option_value_id'], 'integer'],
            [['motorcycle_id'], 'exist', 'skipOnError' => true, 'targetClass' => Motorcycle::className(), 'targetAttribute' => ['motorcycle_id' => 'id']],
            [['moto_option_id'], 'exist', 'skipOnError' => true, 'targetClass' => MotoOption::className(), 'targetAttribute' => ['moto_option_id' => 'moto_option_id']],
        ];
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotorcycle()
    {
        return $this->hasOne(Motorcycle::className(), ['id' => 'motorcycle_id']);
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOption()
    {
        return $this->hasOne(MotoOption::className(), ['moto_option_id' => 'moto_option_id']);
    }

    /**
     * @return \yii\db\ActiveQuery
     */
    public function getMotoOptionValue()
    {
        return $this->hasOne(MotoOptionValue::className(), ['moto_option_value_id' => 'moto_option_value_id']);
    }
}


Motorcycle - table with a motorcycle (product)
spoiler

public function getMotorcycleOptionValue()
    {
        return $this->hasMany(MotorcycleOptionValue::className(), ['motorcycle_id' => 'id']);
    }



In views/motorcycle/view.php I display (in phpMyAdmin directly added data) a data bundle. And here everything is displayed correctly:
spoiler

<div class="tab-pane" id="har">
                        <p><?= Html::a('Добавить значение', ['option/motorcycle-option-value/create', 'motorcycle_id' => $model->id], ['class' => 'btn btn-primary']); ?></p>
        <?= GridView::widget([
            'dataProvider' => new \yii\data\ActiveDataProvider(['query' => $model->getMotorcycleOptionValue()->with('motoOptionValue')]),
            'columns' => [
                ['class' => 'yii\grid\SerialColumn'],

                [
                    'attribute' => 'moto_option_id',
                    'value' => 'motoOption.name',
                ],
                [
                    'attribute' => 'moto_option_value_id',
                    'value' => 'motoOptionValue.name',
                ],
                [
                    'class' => 'yii\grid\ActionColumn',
                    'header' => 'Действие',
                    'controller' => '/option/motorcycle-option-value',
                ],
            ],
        ]); ?>
        </div>


Trying to do in changing the motorcycle, adding new options. And this is where it doesn't work correctly.
MotorcycleController
spoiler

public function actionUpdate($id)
    {
        $model = $this->findModel($id);

        $values = $model->getMotorcycleOptionValue()->with('motoOptionValue')->indexBy('moto_option_id')->all();
        $options = MotoOption::find()->indexBy('moto_option_id')->all();

        foreach (array_diff_key($options, $values) as $option) {
            $values[] = new MotorcycleOptionValue(['moto_option_id' => $option->moto_option_id]);
        }

        foreach ($values as $value) {
            $value->setScenario(MotorcycleOptionValue::SCENARIO_TABULATOR);
        }

        $post = Yii::$app->request->post();

        if ($model->load($post) && $model->save() && Model::loadMultiple($values, $post)) {
            foreach ($values as $value) {
                if ($value->validate()) {
                    if (!empty($value->moto_option_value_id)) {
                        $value->motorcycle_id = $model->id;
                        $value->save();
                    } else {
                        $value->delete();
                    }
                }
            }
            return $this->redirect(['view', 'id' => $model->id]);
        } else {
            return $this->render('update', [
                'model' => $model,
                'values' => $values
            ]);
        }
    }


Or I wrote something incorrectly in the controller. Or I'm doing something wrong in the form.
The form:
spoiler

<div class="box-body">
            <div class="col-xs-4">
                foreach ($values as $value): ?>
                <?= $form->field($value, '[' . $value->motoOptionValue->moto_option_value_id . ']moto_option_value_id')->label($value->motoOptionValue->motoOption->name); ?>
                <?php endforeach; ?>
            </div>
        </div>



--------------------
And somehow you need to display in the dropDownList the values ​​​​related specifically to a specific (own) option.

Help me please. Thank you very much in advance! =)

Answer the question

In order to leave comments, you need to log in

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question