Skip to content

Instantly share code, notes, and snippets.

@quinncomendant
Created December 21, 2021 03:31
Show Gist options
  • Save quinncomendant/b743dcaf7a7dd172a9066be003911b8f to your computer and use it in GitHub Desktop.
Save quinncomendant/b743dcaf7a7dd172a9066be003911b8f to your computer and use it in GitHub Desktop.
<?php
/*
* Set timezone used internally by PHP. See full list at https://www.php.net/manual/en/timezones.php
*
* @access public
* @param string $tz Timezone, e.g., America/Mexico_City
* @return
* @author Quinn Comendant <[email protected]>
* @since 28 Jan 2019 16:38:38
*/
public function setTimezone($tz)
{
// Set timezone for PHP.
if (date_default_timezone_set($tz)) {
$this->logMsg(sprintf('Using php timezone: %s', $tz), LOG_DEBUG, __FILE__, __LINE__);
} else {
// Failed!
$this->logMsg(sprintf('Failed to set php timezone: %s', $tz), LOG_WARNING, __FILE__, __LINE__);
}
}
/*
* Create a DateTime object from a string and convert its timezone.
*
* @access public
* @param string $datetime A date-time string or unit timestamp, e.g., `now + 60 days` or `1606165903`.
* @param string $from_tz A PHP timezone, e.g., UTC
* @param string $to_tz A PHP timezone, e.g., America/Mexico_City
* @return DateTime A DateTime object ready to use with, e.g., ->format(…).
* @author Quinn Comendant <[email protected]>
* @since 23 Nov 2020 15:08:45
*/
function convertTZ($datetime, $from_tz, $to_tz)
{
if (preg_match('/^\d+$/', $datetime)) {
// It's a timestamp, format as required by DateTime::__construct().
$datetime = "@$datetime";
}
$dt = new DateTime($datetime, new DateTimeZone($from_tz));
$dt->setTimezone(new DateTimeZone($to_tz));
return $dt;
}
/*
* Convert a given date-time string from php_timezone to user_timezone, and return formatted.
*
* @access public
* @param string $datetime A date-time string or unit timestamp, e.g., `now + 60 days` or `1606165903`.
* @param string $format A date format string for DateTime->format(…) or strftime(…). Set to lc_date_format by default.
* @return string A formatted date in the user's timezone.
* @author Quinn Comendant <[email protected]>
* @since 23 Nov 2020 15:13:26
*/
function dateToUserTZ($datetime, $format=null)
{
if (empty($datetime) || in_array($datetime, ['0000-00-00 00:00:00', '0000-00-00', '1000-01-01 00:00:00', '1000-01-01'])) {
// Zero dates in MySQL should never be displayed.
return '';
}
try {
// Create a DateTime object and convert the timezone from server to user.
$dt = $this->convertTZ($datetime, $this->getParam('php_timezone'), $this->getParam('user_timezone'));
} catch (Exception $e) {
$this->logMsg(sprintf('DateTime failed to parse string in %s: %s', __METHOD__, $datetime), LOG_NOTICE, __FILE__, __LINE__);
return '';
}
// By default, we try to use a localized date format. Set lc_date_format to null to use regular date_format instead.
$format = $format ?: $this->getParam('lc_date_format');
if ($format && mb_strpos($format, '%') !== false) {
// The data format is localized for strftime(). It only accepts a timestamp, which are always in UTC, so we hack this by offering the date from the user's timezone in a format without a TZ specified, which is used to a make a timestamp for strftime (we can't use DaateTime->format('U') because that would convert the date back to UTC).
return strftime($format, strtotime($dt->format('Y-m-d H:i:s')));
} else {
// Otherwise use a regular date format.
$format = $format ?: $this->getParam('date_format');
return $dt->format($format);
}
}
/*
* Convert a given date-time string from user_timezone to php_timezone, and formatted as YYYY-MM-DD HH:MM:SS.
*
* @access public
* @param string $datetime A date-time string or unit timestamp, e.g., `now + 60 days` or `1606165903`.
* @param string $format A date format string for DateTime->format(…). Set to 'Y-m-d H:i:s' by default.
* @return string A formatted date in the server's timezone.
* @author Quinn Comendant <[email protected]>
* @since 23 Nov 2020 15:13:26
*/
function dateToServerTZ($datetime, $format='Y-m-d H:i:s')
{
try {
// Create a DateTime object and conver the timezone from server to user.
$dt = $this->convertTZ($datetime, $this->getParam('user_timezone'), $this->getParam('php_timezone'));
} catch (Exception $e) {
$this->logMsg(sprintf('DateTime failed to parse string in %s: %s', __METHOD__, $datetime), LOG_NOTICE, __FILE__, __LINE__);
return '';
}
return $dt->format($format);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment