21

I am trying to output dates in the Italian format using date() as follows:

<?php 
    setlocale(LC_ALL, 'it_IT');
    echo date("D d M Y", $row['eventtime']); 
?>

However, it is still coming out in the English format. What else could I do? Is there something wrong?

The solution has to be script specific and not server-wide.

Dharman
  • 30,962
  • 25
  • 85
  • 135
Shadi Almosri
  • 11,678
  • 16
  • 58
  • 80

4 Answers4

43

date() is not locale-aware. You should use strftime() and its format specifiers to output locale-aware dates (from the date() PHP manual):

To format dates in other languages, you should use the setlocale() and strftime() functions instead of date().

Regarding Anti Veeranna's comment: he is absolutely right, since you have to be very careful with setting locales as they are sometimes not limited to the current script scope. The best way would be:

$oldLocale = setlocale(LC_TIME, 'it_IT');
echo utf8_encode( strftime("%a %d %b %Y", $row['eventtime']) );
setlocale(LC_TIME, $oldLocale);
Flygenring
  • 3,818
  • 1
  • 32
  • 39
Stefan Gehrig
  • 82,642
  • 24
  • 155
  • 189
  • 3
    Keep in mind that setlocale is not script specific, it is thread specific, so it is possible that the locale changes 'underneath' you. http://ee.php.net/setlocale explains it too. – Anti Veeranna Jul 11 '09 at 20:32
  • 1
    It is not even just thread specific, it's process specific. So you might change other running PHP instances, too. (http://www.php.net/manual/en/function.setlocale.php#refsect1-function.setlocale-notes) – apfelbox Feb 09 '13 at 12:19
  • 1
    `strftime` is deprecates since PHP 8.1. See here for an updated answer: https://stackoverflow.com/a/73250691/1671294 – MrSnoozles Aug 05 '22 at 13:47
14

I found that setlocale isn't reliable, as it is set per process, not per thread (the manual mentions this). This means other running scripts can change the locale at any time. A solution is using IntlDateFormatter from the intl php extension.

$fmt = new \IntlDateFormatter('it_IT', NULL, NULL);
$fmt->setPattern('d MMMM yyyy HH:mm'); 
// See: http://userguide.icu-project.org/formatparse/datetime for pattern syntax
echo $fmt->format(new \DateTime()); 

If it doesn't work you might need to:

  • Install intl php extension (ubuntu example): sudo apt-get install php5-intl

  • Install the locale you want to use: sudo locale-gen it_IT

Simon Epskamp
  • 8,813
  • 3
  • 53
  • 58
  • 1
    This solution is more reliable than the accepted answer (having `intl` php extension installed and the appropriate locale available) – clami219 Apr 23 '20 at 16:51
  • Since strftime is depreciated in php8.0, IntlDateFormatter is a great solution! It can also be written shorter like this (including the timezone (if required) and pattern in the object call): $fmt = new \IntlDateFormatter('it_IT', NULL, NULL, 'Europe/Rome', NULL, 'd MMMM yyyy HH:mm'); – LaZza Oct 12 '22 at 16:03
4

it_IT locale has to be installed/enabled by your server admin, otherwise this will not work.

So, Jonathan's solution is probably the best.

Anti Veeranna
  • 11,485
  • 4
  • 42
  • 63
0

About the article on http://www.phpnews.it/articoli/ottenere-date-in-italiano/response, the blog suggest an alternative method, but the code is not working, here is the correct code:

function timestamp_to_date_italian($date)
    {       
        $months = array(
                '01' => 'Gennaio', 
                '02' => 'Febbraio', 
                '03' => 'Marzo', 
                '04' => 'Aprile',
                '05' => 'Maggio', 
                '06' => 'Giugno', 
                '07' => 'Luglio', 
                '08' => 'Agosto',
                '09' => 'Settembre', 
                '10' => 'Ottobre', 
                '11' => 'Novembre',
                '12' => 'Dicembre');

        list($day, $month, $year) = explode('-',date('d-m-Y', $date));      
        return $day . ' ' . $months[$month] . ' ' . $year;

    }
Sunchaser
  • 319
  • 2
  • 15