DST

Daylight Saving Time

According to this server

Sat, 16th Dec 2017, 16:10:25 AEDT Australia/Sydney (1513401025)
This timezone is currently in daylight saving time.
Daylight saving time began on: Sun, 1st Oct 2017, 03:00:00 AEDT
Standard time begins on: Sun, 1st Apr 2018, 03:00:00 AEST
In Sun days, on Sunday morning at 02:00:00 (2:00 AM), the clocks need to be put forward 60 minutes.

I have always thought there would have to be a programatic way of determining when daylight saving started and finished. I know that it’s an arbitrary date and it’s subject to change, but I knew there would be a way to somehow look it up.

I’ve been looking for this before and never really came across anything and even when looking at the date/time functions in php, and even though gettimezone retrieves the current timezone (including whether or not DST is currently in force or not), it didn’t do much to solve the “when does it start next” problem.

Then one day I was playing in the backend of a website and I noticed there was two lines of text under the timezone information that was intriguing:

DST Info

I opened up the trust text editor and went fishing inside the server.

Now, I’m pretty sure I’ve seen timezone_transitions_get before, but for whatever reason, something never clicked. It’s EXACTLY what I was looking for!

In the DateTimeClass there are a myriad of functions to do with what the offset from UTC is, what effect DST has on the timezone, is it in effect now, amongst others; including get_transitions. This returns all the DST transitions for the time zone, past and future.

The only caveat ere is your version of php would have to be reasonably up-to-date in the event that a local government changes when DST will start and finisg. and although that probably wouldn’t be too often, it’s something that still must be considered.

This snippet I’ve created here isn’t perfect, it’s just bits and pieces cobbled together and it does need a good cleaning out. However, I’ve included it here and it’s available to you if you’d like to use it under the MIT license.

add_shortcode('DST_Info', 'mad_dst_info');

function mad_dst_info(){
$r = "
<style>
table {
  border-collapse: collapse;
}
td {
  text-align:center;
  padding:10px;
  border: 2px solid black;
}
</style> \n"  ;


$day    = 1;
$month  = 1;
$year   = 2018;

$time = mktime(12,0,0,$month,$day,$year);

$time = gettimeofday(time(),true);
  
function _t1($arg) {
 return "  <tr><td colspan='2'> $arg </td></tr>\n";
}
function _t2($arg1, $arg2) {
 return "  <tr><td> $arg1 </td><td> $arg2 </td></tr>\n";
}

$my_format="D, jS M Y, H:i:s T ";

$current_offset = timezone_offset_get();
$tzstring = ini_get('date.timezone');
$tzstring = "Australia/Sydney";
date_default_timezone_set($tzstring);

$r .= "<table>";
	$r .= _t1("<h2>According to this server</h2>");
	$r .= _t2( date($my_format, time()) , "$tzstring (".time().")");

	$check_zone_info = true;

    // Set TZ so localtime works.
    date_default_timezone_set($tzstring);
    $now = localtime(time(),true); ////////////////////////////////////////////////////////////////////////time(), true);
    if ( $now['tm_isdst'] ){
		$r .= _t1("This timezone is currently in daylight saving time.");
    } else {
		$r .= _t1("This timezone is currently in standard time.");
    }
    $allowed_zones = timezone_identifiers_list();

    if ( in_array( $tzstring, $allowed_zones) ) {
      $found = false;
      $date_time_zone_selected = new DateTimeZone($tzstring);
      $tz_offset = timezone_offset_get($date_time_zone_selected, date_create());
      $right_now = time(); ///////////////////////////////////////////////////////////////////////////////////time();
      foreach ( timezone_transitions_get($date_time_zone_selected) as $tr) {
        if ( $tr['ts'] > $right_now ) {
            $found = true;

          break;
        }
        $tr_old = $tr;
      }

      if ( $found && $tr['offset'] != "UTC") {

        $message = $tr_old['isdst'] ? 'Daylight saving time began on: ' : 'Standard time began on: ';
          $r .= _t2( "  $message ",date($my_format , $tr_old['ts'] + ( $tz_offset - $tr_old['offset'] )));

        $message = $tr['isdst'] ? 'Daylight saving time begins on: ' : 'Standard time begins on: ';
          $r .= _t2( "  $message ",date($my_format , $tr['ts'] + ( $tz_offset - $tr['offset'] )));
		
		$damxdaystogo = date("D" , $tr['ts']);
		$damdayofweek = date("l" , $tr['ts']);
		$damtimeofday = date("H:i:s (g:i A)" , $tr['ts']);
		$damadjustment = ($tz_offset - $tr['offset'])/60 ;
		$dambackforward = ($damadjustment < 0) ? "back" : "forward";
		$message = "In $damxdaystogo days, on $damdayofweek morning at $damtimeofday, the clocks need to be put <em>$dambackforward</em> $damadjustment minutes.";
		  $r .= _t1( "  $message ");
		
		
      } else {
        $r .= _t1( 'This timezone does not observe daylight saving time.' );
      }
    }

    // Set back to UTC.
    date_default_timezone_set('UTC');
    date_default_timezone_set($tzstring);
	$r .=    "</table>";
  return $r;
}