Search and show related tables in datagriew.

Hola, soy nuevo en MVC.

[b]

Queria saber como mostrar las tablas relacionadas al buscar un pais que me muestre los paises y las tablas de las ciudades relacionadas.

Lo genere con gii y agregue manualmente las relaciones.

Yo se que el "CountrySearch" deberia cambiarlo pero no se exactamente que debo modicar en ese script y en la vista que debo cambiar?

[/b]

Code sql of me tables




CREATE TABLE IF NOT EXISTS `bdyii`.`Country` (

`id` INT UNSIGNED NOT NULL AUTO_INCREMENT,

`name` VARCHAR(45) NOT NULL,


PRIMARY KEY (`id`))

ENGINE = InnoDB;

 

CREATE TABLE IF NOT EXISTS `bdyii`.`City` (

  `id` INT UNSIGNED NOT NULL AUTO_INCREMENT,

  `name` VARCHAR(45) NOT NULL,

  `country_ID` INT UNSIGNED NOT NULL,


  PRIMARY KEY (`id`))

ENGINE = InnoDB;



model/Country




<?php


namespace app\models;


use Yii;


/**

 * This is the model class for table "country".

 *

 * @property string $id

 * @property string $name

 */

class Country extends \yii\db\ActiveRecord

{

    /**

     * @inheritdoc

     */

    public static function tableName()

    {

        return 'country';

    }


    /**

     * @inheritdoc

     */

    public function rules()

    {

        return [

            [['name'], 'required'],

            [['name'], 'string', 'max' => 45]

        ];

    }


    /**

     * @inheritdoc

     */

    public function attributeLabels()

    {

        return [

            'id' => 'ID',

            'name' => 'Name',

        ];

    }




public function getCitys() {

     return $this->hasMany(City::className(), ['country_ID' => 'id']);

}

    

   

    }






CountrySearch




<?php


namespace app\models;


use Yii;

use yii\base\Model;

use yii\data\ActiveDataProvider;

use app\models\Country;


/**

 * CountrySearch represents the model behind the search form about `app\models\Country`.

 */

class CountrySearch extends Country

{

    /**

     * @inheritdoc

     */

    public function rules()

    {

        return [

            [['id'], 'integer'],

            [['name'], 'safe'],

        ];

    }


    /**

     * @inheritdoc

     */

    public function scenarios()

    {

        // bypass scenarios() implementation in the parent class

        return Model::scenarios();

    }


    /**

     * Creates data provider instance with search query applied

     *

     * @param array $params

     *

     * @return ActiveDataProvider

     */

    public function search($params)

    {

        $query = Country::find();


        $dataProvider = new ActiveDataProvider([

            'query' => $query,

        ]);


        $this->load($params);


        if (!$this->validate()) {

            // uncomment the following line if you do not want to return any records when validation fails

            // $query->where('0=1');

            return $dataProvider;

        }


        $query->andFilterWhere([

            'id' => $this->id,

        ]);


        $query->andFilterWhere(['like', 'name', $this->name]);


        return $dataProvider;

    }

}







view/_search




<?php


use yii\helpers\Html;

use yii\widgets\ActiveForm;


/* @var $this yii\web\View */

/* @var $model app\models\CountrySearch */

/* @var $form yii\widgets\ActiveForm */

?>


<div class="country-search">


    <?php $form = ActiveForm::begin([

        'action' => ['index'],

        'method' => 'get',

    ]); ?>


    <?= $form->field($model, 'id') ?>


    <?= $form->field($model, 'name') ?>


    <div class="form-group">

        <?= Html::submitButton('Search', ['class' => 'btn btn-primary']) ?>

        <?= Html::resetButton('Reset', ['class' => 'btn btn-default']) ?>

    </div>


    <?php ActiveForm::end(); ?>


</div>




model/city




<?php


namespace app\models;


use Yii;


/**

 * This is the model class for table "city".

 *

 * @property string $id

 * @property string $name

 * @property string $country_ID

 */

class City extends \yii\db\ActiveRecord

{

    /**

     * @inheritdoc

     */

    public static function tableName()

    {

        return 'city';

    }


    /**

     * @inheritdoc

     */

    public function rules()

    {

        return [

            [['name', 'country_ID'], 'required'],

            [['country_ID'], 'integer'],

            [['name'], 'string', 'max' => 45]

        ];

    }


    /**

     * @inheritdoc

     */

    public function attributeLabels()

    {

        return [

            'id' => 'ID',

            'name' => 'Name',

            'country_ID' => 'Country  ID',

        ];

    }


    

    

    

public function getCountry() {

     return $this->hasOne(Country::className(), ['id' => 'country_ID']);

}

    

   

    }



Hola d1399, sobre tu consulta, te recomiendo leas este link donde publico eso http://www.yiiframework.com/forum/index.php/topic/68944-buscar-una-edad-segun-una-fecha-de-nacimiento/

Oh no te refieres a esa parte?, donde indico como hacer inner joins, left, o right y mostrarlos en el archivo admin donde genera por default GII, dentro de CGridView, esa parte te puede ayudar a hacer lo que pretendes lml.

Saludos.

Hola, no es una respuesta a la pregunta pero creo que te facilitaría algo.

La idea de tener 2 modelos (country, countrySearch) es separar la parte de las búsquedas que suelen ser especializadas y no cargar a la clase base (en este caso country) con esa lógica.

Esta es la idea para todos los modelos, pero en realidad, hay muchos modelos que son simples y tienen solo 1 search y sencillo. Yo en estos casos solo genero el modelo básico (Country) e implemento en el la función search. La clase es sencilla y para mi es mejor que este todo en 1 archivo, es decir, no creo el countrySearch.

En modelos con un patrón de búsquedas más complejo, con varias funciones de búsqueda, … esta bien hacerlo tal y como lo propone yii.

Luego es hacer lo que te dice shaolin aunque en tu caso llevandolo a yii2.

Algo así en el search.




    public function search($params)

    {

        $query = Country::find()->joinWith('citys');


        $dataProvider = new ActiveDataProvider([

            'query' => $query,

        ]);


        $this->load($params);


        if (!$this->validate()) {

            // uncomment the following line if you do not want to return any records when validation fails

            // $query->where('0=1');

            return $dataProvider;

        }


        $query->andFilterWhere([

            'id' => $this->id,

        ]);


        $query->andFilterWhere(['like', 'country.name', $this->name])

              ->andFilterWhere(['like', 'city.name', $this->city]);


        return $dataProvider;

    }




en country añadir una variable public $city donde cargaría el nombre de la ciudad, y agregarlo a las rules.

Saludos.