5

I have a table with column for_date saved by type integer in database. In order to show for_date with format DateTime, I used ActiveForm with code:

<?= $form->field($model, 'for_date')->textInput([
    'class' => 'form-control datepicker',
    'value' => $model->for_date ? date(Yii::$app->params['dateFormat'], $model->for_date) : date(Yii::$app->params['dateFormat'], time()),
    'placeholder' => 'Time'])
    ->label('Attendance Date') ?>

But when I create and save, Yii informed This field must be integer

In model file, I had 2 functions below to convert before validate, but it's still error.

public function beforeValidate(){
    if(!is_int($this->for_date)){
        $this->for_date = strtotime($this->for_date);
        $this->for_date = date('d/M/Y', $this->for_date);
    }
    return parent::beforeValidate();
}

public function afterFind(){
    $this->for_date = \Yii::t('app', Yii::$app->formatter->asDate($this->for_date));
    $this->for_date = date('d/M/Y', $this->for_date);
    return parent::afterFind();
}

How can I make it right to save into database with integer?

Francis
  • 279
  • 1
  • 5
  • 16
  • 1
    I would leave it as `int` in the model and use getter and setter. The error message you get comes most likely from your rule settings. So you could change your validator there. – chris--- Oct 13 '15 at 08:02

2 Answers2

0

According to your code for_date is still in a date format after beforeValidate runs due to the line:

$this->for_date = date('d/M/Y', $this->for_date);

Remove this line and it should work.

You will however still have problems e.g formatting of the date or someone entering an invalid date e.g 30/02/2015.

I would suggest creating a separate property e.g. for_date_display and adding a date rule for this. Then in a beforeSave convert this date into a timestamp and set for_date to this value as follows:

public $for_date_display;
...

public function afterFind() {
    $this->for_date_display = \Yii::t('app', Yii::$app->formatter->asDate($this->for_date))
}

public function beforeSave($insert = true) {
    $this->for_date = strtotime($this->for_date_display);
    return parent::beforeSave($insert);
}
topher
  • 13,854
  • 5
  • 51
  • 67
  • Why have a function beforeSave? – Francis Oct 14 '15 at 07:44
  • 1
    Because `for_date` will not be entered/edited directly by the users. They edit `for_date_display` and this needs to be transformed for saving in the database. – topher Oct 14 '15 at 07:53
0

I found solution. In the Model Search (my case is AttendanceSearch.php), find rules function and move for_date from line have integer to below lines have safe

My Code:

public function rules()
    {
        return [
            [['id', 'user_id', 'project_id', 'commit_time', 'workload_type'], 'integer'],
            [['comment', 'for_date'], 'safe'],
        ];
    }
Francis
  • 279
  • 1
  • 5
  • 16