yangi

Yii2 da formalar bilan samari ishlash

Yii2 da formalar bilan samari ishlash

Yii2 framevorkida gii moduli orqali kopgina koelarni avtomatik tarzda yasash mumkin. Shu jumladan ma'lumotlarni bazaga formalar orqali kiritish ham ana shu modul orqali qilinishi mumkin. Ammo bazadagi jadval qanchalik katta bo'lsa va ma'lumotlar to'g'ri yoki noto'g'ri ekanligi tekshiruvchi operatsiyalar qancha ko'p bo'lsa, Yii2 yasagan kod shunchalik chalkashib ketadi. Mana shuning uchun men bu maqolamda qanday qilib modellarni yengilashtirish usulini ko'rsatib o'tmoqchiman.

Birinchi bo'lib gii yodamida oddiygina CRUD yasab olishimiz kerak. CRUD bu Create, Retrieve, Update va Delete ya'ni Kiritish, Olish. O'zgartirish va O'chirish degani. CRUD bu bazadagi ma'lumotlarni ustida manipulyatsiya qilish uchun termin. Hop, birinchi bo'lib gii modulga kirin va u yerdan "CRUD Generator" bo'limini tanlang.

So'ng u yerdan model va controller nomalarini kiriting.

Men bu yerda misol tariqasida Clients degan modelni oldim. Siz xohlagan modelda ishlashingiz mumkin.

Tasavvur qilamiz, Clientdan bizga kerakli bo'lgan ma'lumotlar Ismi va Familiyasi, Kategoriyasi (Yani Donalik yoki Ko'pmartalik xaridor), Mashinasini Brendi va Modeli, tug'ilgan yili kerak bo'ladi. Demak, Gii yordamida Controller va View generatsiya qildik endi ularni ko'zdan kechirib chiqamiz. Bizni faqat actionCreate va actionUpdate qiziqtiradi shuning uchun faqat ularga nazar solamiz.

ClientController:

public function actionCreate()
{
    $model = new Clients();
    if ($model->load(Yii::$app->request->post()) && $model->save()) {
        return $this->redirect(['view', 'id' => $model->id]);
    } else {
        return $this->render('create', [
            'model' => $model,
        ]);
    }
}


public function actionUpdate($id)
{
    $model = $this->findModel($id);
    if ($model->load(Yii::$app->request->post()) && $model->save()) {
        return $this->redirect(['view', 'id' => $model->id]);
    } else {
        return $this->render('update', [
        'model' => $model,
        ]);
    }
}

client view:

<div class="clients-form">

<?php $form = ActiveForm::begin(); ?>

<?= $form->field($model, 'first_name')->textInput(['maxlength' => true]) ?>

<?= $form->field($model, 'last_name')->textInput(['maxlength' => true]) ?>
 
<?= $form->field($model, 'category_id')->textInput() ?>

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

<?= $form->field($model, 'car_model_id')->textInput() ?>
 
<?= $form->field($model, 'dob')->textInput() ?>

<div class="form-group">
<?= Html::submitButton($model->isNewRecord ? 'Create' : 'Update', ['class' => $model->isNewRecord ? 'btn btn-success' : 'btn btn-primary']) ?>
</div>

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

</div>

Ko'rib turganingizdek Gii modul kerakli kodni yasab berdi. Ammo muammo shundaki Client modelida tekshirish juda ko'p. Shu jumladan bu modelga juda ko'p relation (ya boshga modellar bilan bog'lanmalar) yozilgan shuning uchun model juda ham "semirib" ketgan. Yana dob (yani tug'ilgan kuni) menda interger sifatida bazada saqlanadi negaligini keyingi maqolalarimda tushuntirib beraman. Bu o'z navbatida saqlash va o'zgartirishda muammolar keltirib chiqaradi. Shuning uchun Validatsiya (yani ma'lumotlar to'g'ri yoki noto'g'ri ekanligini tekshirish) uchun javobgar kodni boshqa Classga olib o'tish ma'qullanadi. Ya'ni Sizning Model ma'lumotlarni saqlash mobaynida tekshirmaydi, ammo buni boshqa classga yuklaydi.

Buning uchun models degan papkani ichida yangi papka ochamiz va uni nomini forms deb nomlaymiz.

Ichiga yangi ClientForm.php degan file yasaymiz.

!!! Diqqat fileni yasagach namespace ni to'g'rilab app\models\forms; deb qo'ying, bo'lmasa Yii2 bu classingizni ko'rmasligi mumkin. Demak, boshladik.

Fileni eng boshiga:

namespace app\models\forms;

deb yozing So'ng Fileni nomi qanday bo'lsa huddi shunday qilib class yaratamiz va uni yii\base\Model dan meros qilamiz.

class ClientForm extends Model
{
}

So'ng, kerakli bo'lgan ma'lumotlar uchun o'zgaruvchilar (yani inglizcha qilib aytganda properties) yasaymiz.

Bizga Ism, Familiya, Kategoriya, Mashina brendi va modeli va tug'ilgan kun kerak. Yana baza bilan bo'glanish uchun private model (yani Shaxshiy yani klassdan tashqariga chiqmaydigan o'zgaruvchi) va Id (bazadagi ma'lumotni ajratuvchi o'zgaruvchi) kiritamiz.

class ClientForm extends Model
{
    public $id; 
    public $first_name; //Ism
    public $last_name; //Familya
    public $category_id; //Kategoriya
    public $car_brand; //Mashina Brendi
    public $car_model; //Mashina Modeli
    public $dob; //Tu'gilgan kun
    private $model;// Baza bilan bo'glovchi model.
}

O'zgaruvchilarni kiritgandan so'ng biz birinchi navbatda Baza bilan bo'glanishni amalga oshirishimiz kerak. Shuning uchin __constructor metodini chaqiramiz. Ammo Klassimiz yii\base\Model dan meros olgani uchun unda allaqachon __constructor metodi bor shuning uchin uni chaqirganda meros olgan klassni __constructirini buzib qo'ymaslik kerak. Ya'ni mana bunday.

Bu meros qilingan klassni __constructori

public function __construct(array $config = [])
{
    parent::__construct($config);
}

Biz unga yangi paramert qo'shamiz.

public function __construct($model,array $config = [])
{
   $this->setModel($model);
   parent::__construct($config); 
<span class="redactor-invisible-space">
}</span>

Bu yerda setModel metodi konstruktrordan berilgan modelni olib, uni formani o'zgartiruvchilariga beradi. Ya'ni model yordamida forma o'zgaruvchilari ma'lumot oladi. Bu method create va update qilinayotganda formaga kerakli ma'lumotlarni beradi.

Bu setModel methodini ko'rinishi.

public function setModel($model)
{
  $this->id=$model->id;
  $this->first_name=$model->first_name;
  $this->last_name=$model->last_name;
  $this->category_id=$model->category_id;
  $this->car_brand=$model->car_brand;
  $this->car_model=$model->car_model;
  $this->dob=$model->dob;

  $this->model=$model;
}

Keyingi qiladigan ishimiz bu qoidalarni yozish (yani yii2da rules). Qoidalar formadan kelayotgan ma'lumotlarni tekshirib, xatolarini foydalanuvchiga ko'rsatadi. Qoidalar yozish oson, buning uchun rules degan method chaqiriladi va uning ichiga massiv kiritirladi. Mana bunday qilib.

public function rules()
{
  return [
    //Sining qoidalaringiz. 
  ];
}

Bu massiv ichiga gii allaqachon sizga yozib bergan modellardagi rules degan methodini ko'chirib olib tashlab yasagan formadagi massiv ichiga qo'yishingiz kerak.

!!! Diqqat siz Yii2ning Gii moduli yasagan modellardan rules degan methodni olib tashlashingiz kerak aks holda ma'lumotlar kiritilayotgan paytda yoki uni o'zgartirish paytida sizga xatolik berib, ruxsat bermasligi mumkin.

Demak, endi biz rules methodini ichiga bizga kerakli bo'lgan qoidalarni kiritishimiz kerak. Birinchi bo'lib biz qaysi o'zgaruvchilar majburiy va qaysilari majburiy emasligini aniqlashimiz kerak. Tasavvur qilamiz mendagi misolda tug'ilgan kunni kiritish majburiy emas qolganlari majburiy. Buning uchun men required (yani majburiy) degan qoidani ishlataman.

Mana:

public function rules()
{
  return
  [
    [ [ 'first_name','last_name','category_id','car_brand','car_model' ],'required' ],
  ];
}

Bu bilan men tug'ilgan kundan boshqa barcha o'zgaruvchilar majburiy deb ko'rsatdim. Endi navbar har bir o'zgaruvchilarni bitta-bittalab tekshirish kerak. Demak, first_name va last_name bular so'zdan tashkil topgan va uzunligi 32 ta harfdan oshmashligi kerak. category_id bazadagi kategoriyalardan biri bo'lishi kerak, agar boshqasi bo'lsa xatolik berishi kerak. Mashina brendi faqat Chevrolet, Dewoo va Ravon, modeli esa faqat Matiz, Nexia, Lacetti va Malibuni qabul qiladi deb olsak. Va tug'ilgan kun date formatida bo'lishi kerak. Mana bunday qilib:

public function rules()
{
  return
  [
    [ [ 'first_name','last_name','category_id','car_brand','car_model' ],'required' ],
    [ [ 'first_name','last_name' ], 'string', 'max'=>32 ],
    [ [ 'category_id' ], 'exist', 'skipOnError' => true, 'targetClass' => Category::className(), 'targetAttribute' => ['category_id' => 'id']],
    [ [ 'car_brand' ],'in', 'range'=>['Dewoo','Chevrolet','Ravon'] ],
    [ [ 'car_model' ],'in', 'range'=>['Matiz','Naxia','Lacetti','Malibu'] ],
    [ [ 'dob' ], 'date', 'format' => 'php:Y-m-d' ]
  ];
}

Hop, qoidalarni kiritib oldik. endi bu qoidalardan o'tgandan keyin ma'lumotlarni bazaga kiritish kerak. Buning uchun save degan method yasashimiz kerak.

public function save()
{
  if (!$this->validate())
  {
    return false;
  }

  $client=$this->model;
  $client->first_name=$this->first_name;
  $client->last_name=$this->last_name;
  $client->category_id=$this->category_id;
  $client->car_brand=$this->car_brand;
  $client->car_model=$this->car_model;
  if($this->dob!==null)
  {
    $client->dob=strtotime($this->dob);
  }
  $client->save();
  $this->id=$client->id;
 
  return true;
}

$this->validate method bizga kelayotgan ma'lumotlarni qoida bo'yicha tekshirish uchun kerak. Agar qoidalardan o'tmasa, return false qaytadi va ma'lumotlar bazaga saqlanmasdan o'tadi. Agar qoidalardan o'tsa unda bazaga kiritiladi va return true qaytadi. return true qaytsa bu degani ish bajarildi va index pagega yoki view page redirect qilsa bo'ladi. Controller ham buday ko'rinishga keladi.

public function actionCreate()
{
  $model=new ClientForm(new Client());
  if($model->load(Yii::$app->request->post())&&$model->save())
  {
     return $this->redirect(['view','id'=>$model->id]);
  }
  return $this->render('create',['model'=>$model]);
}

public function actionUpdate()
{
  $model=new ClientForm($this->findModel($id));
  if($model->load(Yii::$app->request->post())&&$model->save())
  {
    return $this->redirect(['view','id'=>$model->id]);
  }
  return $this->render('create',['model'=>$model]);
}

Mana bo'ldi, endi formani o'zingiz xohlagandek qilib o'zgartirishingiz mumkin. Bu yechim sizga kodingizni yengillashtirishda yordam beradi degan umiddaman.

Agar taklif yoki savollaringiz bo'lsa, izohlarda yozib qoldiring va bu maqolani baholang. Etiboringiz uchun rahmat. !!!


Keyingi maqolalarda nimalar haqida bilmoqchisiz shun ham yozing.

yii2 gii forms 20-Dekabr 12:05 2377

Vakhobov Ziyavuddin - Texnoman foydalanuvchisi

Muallif haqida

Vakhobov Ziyavuddin PHP da Yii2 Laravel va Symfonyda ishliman.


Qiziq bo‘ladi:


Birinchi bo‘ling!

Iltimos, fikr bildirish uchun saytga kiring yoki ro‘yxatdan o‘ting!