2

I have a date in MySQL format and I want to display the date localized into my user county date format.

I would like to know if there is a way to get the format by a country's ISO code, something like:

$mysql_date = '2017-12-31';
echo print_localized_date($mysql_date,'it'); // 31/12/2017
echo print_localized_date($mysql_date,'de'); // 31.12.2017
echo print_localized_date($mysql_date,'us'); // 12/31/2017

I know I could directly pass the format but our site potentially sells all over the world and I should consider every date format.

Another solutions could be storing into my country table a column with the PHP date format string, in that case is there a resource from which I could get that information, hopefully a CSV or a SQL dump?

I use Laravel and Carbon but I don't see a solution in that library, for instance moment.j has exactly what I'm looking for: ["moment.js Multiple Locale Support][1] but in JavaScript, I need it in PHP.

Machavity
  • 30,841
  • 27
  • 92
  • 100
Rocco Milluzzo
  • 997
  • 8
  • 16

3 Answers3

8

That's what the IntlDateFormatter from the intl extension is for:

$fmt = new IntlDateFormatter(
    'it_IT',
    IntlDateFormatter::SHORT,
    IntlDateFormatter::NONE,
    'Europe/Rome',
    IntlDateFormatter::GREGORIAN
);

$mysql_date = '2017-12-31';
$date = new DateTime($mysql_date);

echo $fmt->format($date);
31/12/17
deceze
  • 510,633
  • 85
  • 743
  • 889
0

An example of how this can be done is using PHPs setlocale function like so:

setlocale(LC_TIME, "de_DE"); //sets to German locale
$today = strftime("%A, %e %B %Y"); //outputs the current time in this locale, to a string 
setlocale(LC_TIME, "en_GB"); //revert the locale back to the page standard (in my case GB).  

Combined with strftime function this will give you completely locale aware dates and times in PHP.

From reading similar questions on this topic, using the above method seems to be the easiest way of doing it, however the comment by Terminus is a good point -- Why not let the Front End deal with this Front End problem?


A complete function solution:

NOTE: You should return the timestamp as a direct 9timestamp from the MySQL data column](https://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html#function_unix-timestamp), using:

SELECT ..., UNIX_TIMESTAMP(`date_column`) AS timeStampDate, ... FROM ...

This is far more efficient that getting PHP to generate DateTime objects or otherwise need to post-process the date string to get the same value. But once this value is reached, the use the following function:

function print_localized_date($timestamp, $locale){
    if($timestamp > 0 && !empty($locale)){
        //grab current locale
        $currentLocale = setlocale(LC_TIME, 0);
        // set to new locale.
        setlocale(LC_TIME, $locale);
        // format the date string however you wish, using the timestamp
        $today = strftime("%A, %e %B %Y", $timestamp);
        // revert to the current locale now date string is formatted.
        setlocale(LC_TIME, $currentLocale);
        // tidy up (probably un-needed)
        unset(currentLocale);
        // return the date value string.   
        return $today;
    }
    return false;
}

$timestamp = 1496061088;
$locale = "it_IT.UTF-8"; 
print print_localized_date($timestamp, $locale);
/***
 * prints lunedì, 29 maggio 2017 
 ***/
Community
  • 1
  • 1
Martin
  • 22,212
  • 11
  • 70
  • 132
  • `utf8_encode` is a bad idea, especially unconditionally. You should use the UTF-8 variant of the locale, e.g. `it_IT.UTF-8` (system dependent). Unless you specify the desired encoding this way, it's a crapshoot what encoding you'll get, and `utf8_encode` will mangle the output into garbage. – deceze May 29 '17 at 12:36
  • @deceze thanks for the headsup on that, I was unaware I could force to UTF-8 within the locale definition. Example updated. Cheers – Martin May 29 '17 at 12:38
  • @Martin Thanks for the answer, but I don't want to print "lunedì, 29 maggio 2017" and I know there are many solutions for that I want the "numeric date format" it => 29/05/2017, de => 29.05.2017, us => 05/29/2017 – Rocco Milluzzo May 29 '17 at 12:44
  • @RoccoMilluzzo then simply change the syntax in `strftme` to suite your needs. I do state this in the answer. I used the above syntax to clearly illustrate the change taking place. – Martin May 29 '17 at 13:10
  • @Martin Yes but I need to change the format basing on user country, so I would need a country to php_date_format conversion database/helper or an integrated solution like I got in the marked answer – Rocco Milluzzo May 29 '17 at 13:18
-1

I would go with Carbon and "setLocale()".

setlocale(LC_TIME, config('app.locale')); // or 'en' ..
Carbon::now()->format('l j F Y H:i:s');

Or just call setLocale on a central place, like in der regsister() method of AppServiceProvider

opHASnoNAME
  • 20,224
  • 26
  • 98
  • 143
  • 1
    Thanks for the answer, but I don't want to print text date and I know there are many solutions for that I want the "numeric date format" it => 29/05/2017, de => 29.05.2017, us => 05/29/2017 – Rocco Milluzzo May 29 '17 at 12:45