How To Set Date Format Globally

Hello I need to show the date format in all views and input forms as dd-mm-yy.

I am able to do it with specific attributes. But that appears to be duplicating the work in all places.

I am looking for a way, where I can set the date format globally so that the date is displayed in the format as dd-mm-yy without the need to apply the date format at so many places.

Thanks.

In Yii 1.13, I override afterFind and beforeSave in the model:




    protected function beforeSave()

    {

        $this->training_date = date('Y-m-d', CDateTimeParser::parse($this->training_date, 'dd-MM-yyyy'));

        return parent::beforeSave();

    }


    protected function afterFind()

    {

        $this->training_date = Yii::app()->dateFormatter->format('dd-MM-yyyy', $this->training_date);

        return parent::afterFind();

    }



I’m not sure if there is a better way, but this has worked fine for me. I assume there is something similar in Yii 2.

@ trond thanks.

I am employing somewhat similar method. The problem is say you have 20 forms with 5 date fields in each, then using this method, you have to create hundred methods.

so is it the correct approach?

if I need dd-mm-yy throughout my application, then will it not be better to declare the same at one place that all date fields will be of the format dd-mm-yy.

Thanks once again.

I do not quite what you mean here. Can you be more specific?

I guess there are a couple of other approaches as well:

  1. Override CDateFormatter

  2. Have a database table for your global system configuration where you can set the global date format.

Note that this code is in the model - not in the views.

You only need to update for each model used with the beforeSave and afterFind handlers.

So if all your views use the same model, you only need to update that model.

One line per field that needs to be massaged (plus the call to the parent class) in each handler.

I understand, just take for example, I have a model for club membership, which will have attributes for date of birth, date of marriage, spouse date of birth, date of joining, due date for club dues, last payment date etc. so for each of this element you need to write the code, which necessarily appears to be duplication of code.

I wanted to know if there is a way better way to avoid this duplication of code.

That is not duplication of code friend. There is no other way. You need to do this for each and every datetime/timestamp model attributes.

Firstly take a look at this lovely behavior that auto updates your timestamp attributes.

Secondly there is another way to combine behavior and auto-coversion but i do not think its worth the overhead

I guess it is a matter of taste, which alternative one prefers.

You should be creating a helper/class function and calling that in your views. Something like:




// class file

class MyTime {

    public static function displayTime($time, $format = "d-m-y") {

        return date($format, strtotime($time));

    }

}






// view file

<?= MyTime::displayTime($model->date); ?>



You should NOT be modifying the data in the database or the model. Store it like you normally would (e.g., timestamp or YYYY-MM-DD to fit mysql’s date format) and leave it as is.

No writing duplicate functions, no fudging of the data. Remember, the model is meant to interact with the database and the view is meant to display the data to the user. Keep them separate!

Your application design should dictate these (how you want to present data for numbers, dates etc.).

Though, there is no standard way to do this… a few design recommendations to sequentially list down, if I understand your needs:

[list=1]

[*] Configuration: Store the date/number format defaults for your app in one place. You could design an UI or probably use Yii Application Config.

[*] Conversion: Create a helper class to read this config and convert your attributes. To a large extent, you can use in your helper, the [font="Courier New"]yii\i18n\Formatter[/font] class which handles intl/locale specific formatting.

[*] Forms: Create a reusable widget for form inputs that validates your attributes for format from the config (in step 1).

[*] Validation: For attribute validation, you need to use inbuilt ‘date’ validator to use prescribed format as read from your config in step 1.

[/list]

Yes… you can enhance this by creating traits/behaviors or extending grid data columns, which could even minimize further coding, but its upto you to decide.

You can refer my new extension yii2-datecontrol which handles this easily. Refer documentation and usage.