Skip to content

Commit

Permalink
[REF][PHP8.1][INTL] Remove dependency on strftime function by using t…
Browse files Browse the repository at this point in the history
…s to generate day full names and abbreviations and month abbreviations

Fix array order and add unit test to lock in fix
  • Loading branch information
seamuslee001 committed Jul 22, 2022
1 parent d97227c commit 8f47f39
Show file tree
Hide file tree
Showing 4 changed files with 72 additions and 34 deletions.
4 changes: 1 addition & 3 deletions CRM/Contribute/Form/ContributionCharts.php
Original file line number Diff line number Diff line change
Expand Up @@ -94,9 +94,7 @@ public function postProcess() {

$chartData = $abbrMonthNames = [];
if (is_array($chartInfoMonthly)) {
for ($i = 1; $i <= 12; $i++) {
$abbrMonthNames[$i] = strftime('%b', mktime(0, 0, 0, $i, 10, 1970));
}
$abbrMonthNames = CRM_Utils_Date::getAbbrMonthNames();

foreach ($abbrMonthNames as $monthKey => $monthName) {
$val = CRM_Utils_Array::value($monthKey, $chartInfoMonthly['By Month'], 0);
Expand Down
2 changes: 1 addition & 1 deletion CRM/Core/Payment/Realex.php
Original file line number Diff line number Diff line change
Expand Up @@ -363,7 +363,7 @@ public function setRealexFields(&$params) {
}

// Create timestamp
$timestamp = strftime('%Y%m%d%H%M%S');
$timestamp = date('YmdHis');
$this->_setParam('timestamp', $timestamp);
}

Expand Down
83 changes: 53 additions & 30 deletions CRM/Utils/Date.php
Original file line number Diff line number Diff line change
Expand Up @@ -161,20 +161,25 @@ public static function format($date, $separator = '', $invalidDate = 0) {
*/
public static function getAbbrWeekdayNames() {
$key = 'abbrDays_' . \CRM_Core_I18n::getLocale();
$days = &\Civi::$statics[__CLASS__][$key];
if (!$days) {
$days = [];
if (empty(\Civi::$statics[__CLASS__][$key])) {
$days = [
0 => ts('Sun'),
1 => ts('Mon'),
2 => ts('Tue'),
3 => ts('Wed'),
4 => ts('Thu'),
5 => ts('Fri'),
6 => ts('Sat'),
];
// First day of the week
$firstDay = Civi::settings()->get('weekBegins');

// set LC_TIME and build the arrays from locale-provided names
// June 1st, 1970 was a Monday
CRM_Core_I18n::setLcTime();
for ($i = $firstDay; count($days) < 7; $i = $i > 5 ? 0 : $i + 1) {
$days[$i] = strftime('%a', mktime(0, 0, 0, 6, $i, 1970));
\Civi::$statics[__CLASS__][$key] = [];
for ($i = $firstDay; count(\Civi::$statics[__CLASS__][$key]) < 7; $i = $i > 5 ? 0 : $i + 1) {
\Civi::$statics[__CLASS__][$key][$i] = $days[$i];
}
}
return $days;
return \Civi::$statics[__CLASS__][$key];
}

/**
Expand All @@ -192,20 +197,25 @@ public static function getAbbrWeekdayNames() {
*/
public static function getFullWeekdayNames() {
$key = 'fullDays_' . \CRM_Core_I18n::getLocale();
$days = &\Civi::$statics[__CLASS__][$key];
if (!$days) {
$days = [];
if (empty(\Civi::$statics[__CLASS__][$key])) {
$days = [
0 => ts('Sunday'),
1 => ts('Monday'),
2 => ts('Tuesday'),
3 => ts('Wednesday'),
4 => ts('Thursday'),
5 => ts('Friday'),
6 => ts('Saturday'),
];
// First day of the week
$firstDay = Civi::settings()->get('weekBegins');

// set LC_TIME and build the arrays from locale-provided names
// June 1st, 1970 was a Monday
CRM_Core_I18n::setLcTime();
for ($i = $firstDay; count($days) < 7; $i = $i > 5 ? 0 : $i + 1) {
$days[$i] = strftime('%A', mktime(0, 0, 0, 6, $i, 1970));
\Civi::$statics[__CLASS__][$key] = [];
for ($i = $firstDay; count(\Civi::$statics[__CLASS__][$key]) < 7; $i = $i > 5 ? 0 : $i + 1) {
\Civi::$statics[__CLASS__][$key][$i] = $days[$i];
}
}
return $days;
return \Civi::$statics[__CLASS__][$key];
}

/**
Expand All @@ -219,19 +229,26 @@ public static function getFullWeekdayNames() {
*/
public static function &getAbbrMonthNames($month = FALSE) {
$key = 'abbrMonthNames_' . \CRM_Core_I18n::getLocale();
$abbrMonthNames = &\Civi::$statics[__CLASS__][$key];
if (!isset($abbrMonthNames)) {

// set LC_TIME and build the arrays from locale-provided names
CRM_Core_I18n::setLcTime();
for ($i = 1; $i <= 12; $i++) {
$abbrMonthNames[$i] = strftime('%b', mktime(0, 0, 0, $i, 10, 1970));
}
if (empty(\Civi::$statics[__CLASS__][$key])) {
\Civi::$statics[__CLASS__][$key] = [
1 => ts('Jan'),
2 => ts('Feb'),
3 => ts('Mar'),
4 => ts('Apr'),
5 => ts('May'),
6 => ts('Jun'),
7 => ts('Jul'),
8 => ts('Aug'),
9 => ts('Sep'),
10 => ts('Oct'),
11 => ts('Nov'),
12 => ts('Dec'),
];
}
if ($month) {
return $abbrMonthNames[$month];
return \Civi::$statics[__CLASS__][$key][$month];
}
return $abbrMonthNames;
return \Civi::$statics[__CLASS__][$key];
}

/**
Expand Down Expand Up @@ -287,7 +304,8 @@ public static function unixTime($string) {

/**
* Create a date and time string in a provided format.
*
* %A - Full day name ('Saturday'..'Sunday')
* %a - abbreviated day name ('Sat'..'Sun')
* %b - abbreviated month name ('Jan'..'Dec')
* %B - full month name ('January'..'December')
* %d - day of the month as a decimal number, 0-padded ('01'..'31')
Expand Down Expand Up @@ -318,6 +336,8 @@ public static function customFormat($dateString, $format = NULL, $dateParts = NU
// 1-based (January) month names arrays
$abbrMonths = self::getAbbrMonthNames();
$fullMonths = self::getFullMonthNames();
$fullWeekdayNames = self::getFullWeekdayNames();
$abbrWeekdayNames = self::getAbbrWeekdayNames();

if (!$format) {
$config = CRM_Core_Config::singleton();
Expand Down Expand Up @@ -381,6 +401,8 @@ public static function customFormat($dateString, $format = NULL, $dateParts = NU
$second = (int) substr($dateString, 12, 2);
}

$dayInt = date('w', strtotime($dateString));

if ($day % 10 == 1 and $day != 11) {
$suffix = 'st';
}
Expand Down Expand Up @@ -414,6 +436,8 @@ public static function customFormat($dateString, $format = NULL, $dateParts = NU
}

$date = [
'%A' => $fullWeekdayNames[$dayInt] ?? NULL,
'%a' => $abbrWeekdayNames[$dayInt] ?? NULL,
'%b' => $abbrMonths[$month] ?? NULL,
'%B' => $fullMonths[$month] ?? NULL,
'%d' => $day > 9 ? $day : '0' . $day,
Expand All @@ -430,7 +454,6 @@ public static function customFormat($dateString, $format = NULL, $dateParts = NU
'%i' => $minute > 9 ? $minute : '0' . $minute,
'%p' => strtolower($type),
'%P' => $type,
'%A' => $type,
'%Y' => $year,
'%s' => str_pad($second, 2, 0, STR_PAD_LEFT),
'%S' => str_pad($second, 2, 0, STR_PAD_LEFT),
Expand Down
17 changes: 17 additions & 0 deletions tests/phpunit/CRM/Utils/DateTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -271,6 +271,8 @@ public function testCustomFormat() {
$this->assertEquals(CRM_Utils_Date::customFormat($dateTime, "%P"), "PM");
$this->assertEquals(CRM_Utils_Date::customFormat($dateTime, "%Y"), "2018");
$this->assertEquals(CRM_Utils_Date::customFormat($dateTime, "%s"), "44");
$this->assertEquals(CRM_Utils_Date::customFormat($dateTime, "%A"), "Thursday");
$this->assertEquals(CRM_Utils_Date::customFormat($dateTime, "%a"), "Thu");
}

/**
Expand All @@ -293,6 +295,8 @@ public function testCustomFormatTs() {
$this->assertEquals(CRM_Utils_Date::customFormatTs($ts, "%p"), "pm");
$this->assertEquals(CRM_Utils_Date::customFormatTs($ts, "%P"), "PM");
$this->assertEquals(CRM_Utils_Date::customFormatTs($ts, "%Y"), "2018");
$this->assertEquals(CRM_Utils_Date::customFormatTs($ts, "%A"), "Thursday");
$this->assertEquals(CRM_Utils_Date::customFormatTs($ts, "%a"), "Thu");
}

/**
Expand Down Expand Up @@ -325,6 +329,19 @@ public function testLocalizeConsts() {
}
}

public function testWeekDayArrayOrder() {
$this->callAPISuccess('Setting', 'create', ['weekBegins' => 1]);
$this->assertEquals([
1 => 'Monday',
2 => 'Tuesday',
3 => 'Wednesday',
4 => 'Thursday',
5 => 'Friday',
6 => 'Saturday',
0 => 'Sunday',
], CRM_Utils_Date::getFullWeekdayNames());
}

/**
* Test formatDate function.
*
Expand Down

0 comments on commit 8f47f39

Please sign in to comment.