ILIAS  release_8 Revision v8.19
All Data Structures Namespaces Files Functions Variables Modules Pages
class.ilTimeZone.php
Go to the documentation of this file.
1 <?php
2 
3 declare(strict_types=1);
4 /*
5  +-----------------------------------------------------------------------------+
6  | ILIAS open source |
7  +-----------------------------------------------------------------------------+
8  | Copyright (c) 1998-2006 ILIAS open source, University of Cologne |
9  | |
10  | This program is free software; you can redistribute it and/or |
11  | modify it under the terms of the GNU General Public License |
12  | as published by the Free Software Foundation; either version 2 |
13  | of the License, or (at your option) any later version. |
14  | |
15  | This program is distributed in the hope that it will be useful, |
16  | but WITHOUT ANY WARRANTY; without even the implied warranty of |
17  | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
18  | GNU General Public License for more details. |
19  | |
20  | You should have received a copy of the GNU General Public License |
21  | along with this program; if not, write to the Free Software |
22  | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. |
23  +-----------------------------------------------------------------------------+
24 */
25 
39 {
40  public const UTC = 'UTC';
41 
42  public static array $instances = array();
43  public static array $valid_tz = array();
44 
45  protected static string $default_timezone = '';
46  protected static string $current_timezone = '';
47  protected static string $server_timezone = '';
48 
49  protected ilLogger $log;
50  protected string $timezone = "UTC";
51 
56  private function __construct(string $a_timezone)
57  {
58  global $DIC;
59 
60  $this->log = $DIC->logger()->cal();
61 
62  if ($a_timezone) {
63  $this->timezone = $a_timezone;
64  } else {
65  $this->timezone = self::_getDefaultTimeZone();
66  }
67 
68  if (!self::$server_timezone) {
69  self::$server_timezone = self::_getDefaultTimeZone();
70  }
71 
72  if (!self::$default_timezone) {
73  self::_getDefaultTimeZone();
74  }
75  }
76 
77  public function __sleep()
78  {
79  return array('timezone');
80  }
81 
82  public function __wakeup()
83  {
84  global $DIC;
85  $this->log = $DIC->logger()->cal();
86  }
87 
88  public function getIdentifier(): string
89  {
90  return $this->timezone;
91  }
92 
97  public static function _getInstance(string $a_tz = ''): ilTimeZone
98  {
99  if (!$a_tz) {
100  $a_tz = self::_getDefaultTimeZone();
101  }
102 
103  $instance = self::$instances[$a_tz] ?? (self::$instances[$a_tz] = new ilTimeZone($a_tz));
104 
105  // Validate timezone if it is not validated before
106  if (!array_key_exists($instance->getIdentifier(), self::$valid_tz)) {
107  if (!$instance->validateTZ()) {
108  throw new ilTimeZoneException('Unsupported timezone given.');
109  }
110  self::$valid_tz[$instance->getIdentifier()] = true;
111  }
112 
113  // now validate timezone setting
114  return $instance;
115  }
116 
120  public function switchTZ(): bool
121  {
122  try {
123  self::_switchTimeZone($this->timezone);
124  return true;
125  } catch (ilTimeZoneException $exc) {
126  // Shouldn't happen since this has been checked during initialisation
127  $this->log->warning(': Unsupported timezone given: Timzone: ' . $this->timezone);
128  return false;
129  }
130  }
131 
135  public function restoreTZ(): bool
136  {
137  try {
138  self::_switchTimeZone(self::$default_timezone);
139  return true;
140  } catch (ilTimeZoneException $e) {
141  // Shouldn't happen since this has been checked during initialisation
142  $this->log->warning(': Unsupported timezone given: Timzone: ' . $this->timezone);
143  return false;
144  }
145  }
146 
147  public function validateTZ(): bool
148  {
149  // this is done by switching to the current tz
150  if ($this->switchTZ() and $this->restoreTZ()) {
151  return true;
152  }
153  return false;
154  }
155 
156  protected static function _switchTimeZone(string $a_timezone): bool
157  {
158  global $DIC;
159 
160  $logger = $DIC->logger()->cal();
161  if (self::$current_timezone == $a_timezone) {
162  return true;
163  }
164 
165  // PHP >= 5.2.0
166  if (function_exists('date_default_timezone_set')) {
167  if (!date_default_timezone_set($a_timezone)) {
168  $logger->info('Invalid timezone given. Timezone: ' . $a_timezone);
169  throw new ilTimeZoneException('Invalid timezone given');
170  }
171  #$ilLog->write(__METHOD__.': Switched timezone to: '.$a_timezone);
172  self::$current_timezone = $a_timezone;
173  return true;
174  }
175  if (!putenv('TZ=' . $a_timezone)) {
176  $logger->warning('Cannot set TZ environment variable. Please register TZ in php.ini (safe_mode_allowed_env_vars). Timezone');
177  throw new ilTimeZoneException('Cannot set TZ environment variable.');
178  }
179  self::$current_timezone = $a_timezone;
180  return true;
181  }
182 
183  public static function _setDefaultTimeZone(string $a_tz): void
184  {
185  // Save the server timezone, since there is no way to read later.
186  if (!self::$server_timezone) {
187  self::$server_timezone = self::_getDefaultTimeZone();
188  }
189  self::$default_timezone = $a_tz;
190  }
191 
192  public static function _restoreDefaultTimeZone(): void
193  {
194  self::$default_timezone = self::$server_timezone;
195  self::_switchTimeZone(self::$default_timezone);
196  }
197 
201  public static function _getDefaultTimeZone(): string
202  {
203  if (strlen(self::$default_timezone)) {
204  return self::$default_timezone;
205  }
206  // PHP >= 5.2.0
207  // php throws a warning date_default_timezone_get relies on os determination. There is no way to check if this could happen.
208  if (function_exists('date_default_timezone_get') and $tz = date_default_timezone_get()) {
209  return self::$default_timezone = $tz;
210  }
211  // PHP ini option (PHP >= 5.1.0)
212  if ($tz = ini_get('date.timezone')) {
213  return self::$default_timezone = $tz;
214  }
215  // is $_ENV['PHP_TZ'] set ?
216  if ($tz = getenv('PHP_TZ')) {
217  return self::$default_timezone = $tz;
218  }
219  // is $_ENV['TZ'] set ?
220  if ($tz = getenv('TZ')) {
221  return self::$default_timezone = $tz;
222  }
223  if (strlen($tz = date('T'))) {
224  return self::$default_timezone = $tz;
225  }
226  return self::$default_timezone = self::UTC;
227  }
228 
232  public static function initDefaultTimeZone(ilIniFile $ini): string
233  {
234  $tz = $ini->readVariable('server', 'timezone');
235  if (!strlen($tz)) {
236  $tz = self::_getDefaultTimeZone();
237  }
238  if (!strlen($tz)) {
239  $tz = 'UTC';
240  }
241  date_default_timezone_set($tz);
242  return $tz;
243  }
244 }
static _getDefaultTimeZone()
Calculate and set default time zone.
static _getInstance(string $a_tz='')
get instance by timezone
switchTZ()
Switch timezone to given timezone.
static initDefaultTimeZone(ilIniFile $ini)
Initialize default timezone from system settings.
static array $instances
restoreTZ()
Restore default timezone.
static _restoreDefaultTimeZone()
static _setDefaultTimeZone(string $a_tz)
global $DIC
Definition: feed.php:28
static string $default_timezone
Class for TimeZone exceptions.
static string $current_timezone
static array $valid_tz
readVariable(string $a_group, string $a_var_name)
reads a single variable from a group
static _switchTimeZone(string $a_timezone)
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
$ini
Definition: raiseError.php:4
static string $server_timezone
__construct(string $a_timezone)
Create new timezone object If no timezone is given, the default server timezone is chosen...