Plugin Directory

Changeset 1532350


Ignore:
Timestamp:
11/11/2016 03:39:01 PM (9 years ago)
Author:
loushou
Message:
  • [tweak] changing how we handle DST timestamps display again

loushou

Location:
opentickets-community-edition/trunk
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • opentickets-community-edition/trunk/inc/core/post-type.class.php

    r1529668 r1532350  
    14291429                            'meta' => array( // setup the meta to save
    14301430                                self::$o->{'meta_key.capacity'} => $tmp->capacity, // max occupants
    1431                                 self::$o->{'meta_key.end'} => $tmp->end, // end time, for lookup and display purposes later
    1432                                 self::$o->{'meta_key.start'} => $tmp->start, // start time for lookup and display purposes later
     1431                                self::$o->{'meta_key.end'} => QSOT_Utils::make_non_dst( $tmp->end ), // end time, for lookup and display purposes later
     1432                                self::$o->{'meta_key.start'} => QSOT_Utils::make_non_dst( $tmp->start ), // start time for lookup and display purposes later
    14331433                                self::$o->{'meta_key.purchase_limit'} => $tmp->purchase_limit, // the specific child event purchase limit
    14341434                            ),
     
    15031503                            'meta' => array( // set the meta
    15041504                                self::$o->{'meta_key.capacity'} => $tmp->capacity, // occupant capacity
    1505                                 self::$o->{'meta_key.end'} => $tmp->end, // event end date/time for later lookup and display
    1506                                 self::$o->{'meta_key.start'} => $tmp->start, // event start data/time for later lookup and display
     1505                                self::$o->{'meta_key.end'} => QSOT_Utils::make_non_dst( $tmp->end ), // event end date/time for later lookup and display
     1506                                self::$o->{'meta_key.start'} => QSOT_Utils::make_non_dst( $tmp->start ), // event start data/time for later lookup and display
    15071507                                self::$o->{'meta_key.purchase_limit'} => $tmp->purchase_limit, // the specific child event purchase limit
    15081508                            ),
     
    15461546                        'meta' => array( // set meta
    15471547                            self::$o->{'meta_key.capacity'} => $item->capacity, // occupant copacity
    1548                             self::$o->{'meta_key.end'} => $item->end, // end data for lookup and display
    1549                             self::$o->{'meta_key.start'} => $item->start, // start date for lookup and display
     1548                            self::$o->{'meta_key.end'} => QSOT_Utils::make_non_dst( $item->end ), // end data for lookup and display
     1549                            self::$o->{'meta_key.start'} => QSOT_Utils::make_non_dst( $item->start ), // start date for lookup and display
    15501550                            self::$o->{'meta_key.purchase_limit'} => $tmp->purchase_limit, // the specific child event purchase limit
    15511551                        ),
  • opentickets-community-edition/trunk/inc/sys/pages/system-status.page.php

    r1396507 r1532350  
    118118            )
    119119        );
     120        $this->register_tool(
     121            'tsFix',
     122            array(
     123                'name' => __( 'Update Start and End times to site Timezone', 'opentickets-community-edition' ),
     124                'description' => __( 'If you are having time display issues, use this tool to match the event times to the correct timezone.', 'opentickets-community-edition' ),
     125                'function' => array( &$this, 'tool_tsFix' ),
     126                'messages' => array(
     127                    'updated-tses' => $this->_updatedw( __( 'Updated all the start and end times for all events, to be in the correct timezone.', 'opentickets-community-edition' ) ),
     128                ),
     129            )
     130        );
    120131    }
    121132
     
    921932    }
    922933
     934    // cycle through all events, and update the timezone of the start and end times to match the site timezone
     935    public function tool_tsFix( $result, $args ) {
     936        // check that the repair can run
     937        if ( ! $this->_verify_action_nonce( 'tsFix' ) )
     938            return $result;
     939
     940        // update all the event times to use the same tz as the site (non-dst)
     941        QSOT_Utils::normalize_event_times();
     942
     943        // update and return the results data
     944        $result[1]['performed'] = 'updated-tses';
     945        $result[0] = true;
     946        return $result;
     947    }
     948
     949
    923950    // empty all files from a directory (skips subdirs)
    924951    protected function _empty_dir( $path ) {
  • opentickets-community-edition/trunk/inc/sys/utils.php

    r1529668 r1532350  
    8080     * @return string new date formatted string using the 'c' date format
    8181     */
    82     public static function to_c( $ymd, $relative_to_date=false, $dst_adjust=true ) {
     82    public static function to_c( $ymd, $dst_adjust=true ) {
    8383        static $off = false;
    8484        // if we are already in c format, then use it
    8585        if ( false !== strpos( $ymd, 'T' ) )
    86             return $dst_adjust ? self::dst_adjust( $ymd, $relative_to_date ) : $ymd;
     86            return $dst_adjust ? self::dst_adjust( $ymd ) : $ymd;
    8787
    8888        // if we dont match the legacy format, then bail
    8989        if ( ! preg_match( '#\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}#', $ymd ) )
    90             return $dst_adjust ? self::dst_adjust( $ymd, $relative_to_date ) : $ymd;
     90            return $dst_adjust ? self::dst_adjust( $ymd ) : $ymd;
    9191
    9292        // if we never loaded offset before, do it now
     
    9595
    9696        $out = str_replace( ' ', 'T', $ymd ) . $off;
    97         return $dst_adjust ? self::dst_adjust( $out, $relative_to_date ) : $out;
     97        return $dst_adjust ? self::dst_adjust( $out ) : $out;
    9898    }
    9999
     
    107107     * @return string a modified timestamp that has an adjusted timezone portion
    108108     */
    109     public static function dst_adjust( $string, $relative_to_date=false ) {
    110         static $tz_string = null;
    111         $relative_to_date = ! $relative_to_date ? date( 'c' ) : $relative_to_date;
    112         $relative_ts = strtotime( $relative_to_date );
    113         $relative_ts = $relative_ts ? $relative_ts : time();
    114         // only grab the tiemzone string once
    115         if ( null === $tz_string )
    116             $tz_string = get_option( 'timezone_string', 'UTC' );
    117 
    118         // store current tz and update to proper one for daylight savign calc
    119         $orig = date_default_timezone_get();
     109    public static function dst_adjust( $string ) {
     110        // first... assume ALL incoming timestamps are from the NON-DST timezone.
     111        // then... adjust it if we are currently DST
     112
     113        // get the parts of the supplied time string
     114        preg_match( '#^(?P<date>\d{4}-\d{2}-\d{2})(?:T| )(?P<time>\d{2}:\d{2}:\d{2})(?P<tz>.*)?$#', $string, $match );
     115
     116        // if we dont have a date or time, bail now
     117        if ( ! isset( $match['date'], $match['time'] ) )
     118            return $string;
     119       
     120        // if the tz is not set, then default to current SITE non-dst offset
     121        if ( ! isset( $match['tz'] ) )
     122            $match['tz'] = self::non_dst_tz_offset();
     123
     124        // adjust the offset based on whether this is dst or not
     125        $match['tz'] = self::_dst_adjust( $match['tz'] );
     126
     127        // reconstitute the string and return
     128        return $match['date'] . 'T' . $match['time'] . $match['tz'];
     129    }
     130
     131    // determine if currently in dst time
     132    public static function in_dst( $time=null ) {
     133        // update to the site timezone
     134        $tz_string = get_option( 'timezone_string', 'UTC' );
     135        $orig_tz_string = date_default_timezone_get();
    120136        if ( $tz_string )
    121137            date_default_timezone_set( $tz_string );
    122138
    123         // get the parts of the timezone
    124         preg_match( '#^(?P<date>\d{4}-\d{2}-\d{2})T(?P<time>\d{2}:\d{2}:\d{2})(?P<tz>.*)$#', $string, $match );
    125 
    126         // if the timezone is set, then possibly adjust it
    127         if ( isset( $match['date'], $match['time'], $match['tz'] ) ) {
    128             // etract the pieces of the timestamp
    129             $date = $match['date'];
    130             $time = $match['time'];
    131             $off = $match['tz'];
    132 
    133             $current_dst = date( 'I', time() );
    134             $relative_dst = date( 'I', $relative_ts );
    135             $diff = $relative_dst - $current_dst;
    136             // adjust for dst. we need to adjust for NOW being dst, not then
    137             if ( $diff ) {
    138                 preg_match( '#^(?P<hour>[-+]\d{2}):(?P<minute>\d{2})$#', $off, $match );
    139                 if ( isset( $match['hour'], $match['minute'] ) ) {
    140                     $new_hour = intval( $match['hour'] ) - $diff;
    141                     // "spring forward" means the offset is increased by one hour
    142                     $off = sprintf(
    143                         '%s%02s%02s',
    144                         $new_hour < 0 ? '-' : '+',
    145                         abs( $new_hour ),
    146                         $match['minute']
    147                     );
    148                 }
     139        $time = null === $time ? time() : $time;
     140        // get the current dst status
     141        $dst_status = date( 'I', $time );
     142
     143        // restore the timezone before this calc
     144        date_default_timezone_set( $orig_tz_string );
     145
     146        return apply_filters( 'qsot-is-dst', !! $dst_status, $time );
     147    }
     148
     149    // get the non-DST timezone
     150    public static function non_dst_tz_offset() {
     151        static $offset = null;
     152        // do this once per page load
     153        if ( null !== $offset )
     154            return $offset;
     155
     156        // update to the site timezone
     157        $tz_string = get_option( 'timezone_string', 'UTC' );
     158        $orig_tz_string = date_default_timezone_get();
     159        if ( $tz_string )
     160            date_default_timezone_set( $tz_string );
     161
     162        // get the current offset and dst status
     163        $current_offset = date( 'P' );
     164        $dst_status = date( 'I' );
     165
     166        // calculate the appropriate offset based on the current one and the dst flag
     167        $offset = self::_dst_adjust( $current_offset, $dst_status );
     168
     169        // restore the timezone before this calc
     170        date_default_timezone_set( $orig_tz_string );
     171
     172        return $offset;
     173    }
     174
     175    // accept a mysql or 'c' formatted timestamp, and make it use the current non-dst SITE timezone
     176    public static function make_non_dst( $string ) {
     177        static $offset = null;
     178        if ( null === $offset )
     179            $offset = self::non_dst_tz_offset();
     180
     181        // check if the timestamp is valid
     182        if ( ! preg_match( '#^(\d{4}-\d{2}-\d{2})(?:T| )(\d{2}:\d{2}:\d{2}).*$#', $string ) )
     183            return $string;
     184
     185        // first remove an existing timezone
     186        $string = preg_replace( '#^(\d{4}-\d{2}-\d{2})(?:T| )(\d{2}:\d{2}:\d{2}).*$#', '\1T\2', $string );
     187
     188        // add the SITE offset to the base string, and return
     189        return $string . $offset;
     190    }
     191
     192    // adjust a timezone offset to account for DST, to get the non-DST timezone
     193    protected static function _dst_adjust( $offset, $dst=null ) {
     194        $dst = null === $dst ? self::in_dst() : !!$dst;
     195        // if it is a dst time offset
     196        if ( $dst ) {
     197            preg_match( '#^(?P<hour>[-+]\d{2}):(?P<minute>\d{2})$#', $offset, $match );
     198            if ( isset( $match['hour'], $match['minute'] ) ) {
     199                $new_hour = intval( $match['hour'] ) + 1;
     200                // "spring forward" means the offset is increased by one hour
     201                $offset = sprintf(
     202                    '%s%02s%02s',
     203                    $new_hour < 0 ? '-' : '+',
     204                    abs( $new_hour ),
     205                    $match['minute']
     206                );
    149207            }
    150 
    151             // create the updated timestamp
    152             $string = $date . 'T' . $time . $off;
    153208        }
    154209
    155         // restore tz
    156         date_default_timezone_set( $orig );
    157 
    158         return $string;
     210        return $offset;
     211    }
     212
     213    // test dst calcs
     214    protected static function test_dst_calc() {
     215        function yes_dst() { return true; }
     216        function no_dst() { return false; }
     217
     218        $ts1 = '2016-09-12T14:30:00-08:00';
     219        $ts2 = '2016-11-12T14:30:00-08:00';
     220
     221        add_filter( 'qsot-is-dst', 'yes_dst' );
     222        var_dump( QSOT_Utils::to_c( $ts1, 1 ), QSOT_Utils::to_c( $ts2, 1 ) );
     223        $time = QSOT_Utils::gmt_timestamp( QSOT_Utils::to_c( $ts1, 1 ), 'from' );
     224        $time2 = QSOT_Utils::gmt_timestamp( QSOT_Utils::to_c( $ts2, 1 ), 'from' );
     225        date_default_timezone_set( 'Etc/GMT-1' );
     226        var_dump( '09-12-dst', date( 'D, F jS, Y g:ia', $time ) );
     227        var_dump( '11-12-dst', date( 'D, F jS, Y g:ia', $time ) );
     228
     229        remove_filter( 'qsot-is-dst', 'yes_dst' );
     230        add_filter( 'qsot-is-dst', 'no_dst' );
     231        var_dump( QSOT_Utils::to_c( $ts1, 1 ), QSOT_Utils::to_c( $ts2, 1 ) );
     232        $time = QSOT_Utils::gmt_timestamp( QSOT_Utils::to_c( $ts1, 1 ), 'from' );
     233        $time2 = QSOT_Utils::gmt_timestamp( QSOT_Utils::to_c( $ts2, 1 ), 'from' );
     234        date_default_timezone_set( 'UTC' );
     235        var_dump( '09-12-nodst', date( 'D, F jS, Y g:ia', $time ) );
     236        var_dump( '11-12-nodst', date( 'D, F jS, Y g:ia', $time ) );
    159237    }
    160238
     
    168246     * @return int a unix-timestamp, adjusted so that it produces accurrate local times for the server
    169247     */
    170     public static function local_timestamp( $date, $relative_to_date=false, $dst_adjust=true ) {
    171         return self::gmt_timestamp( self::to_c( $date, $relative_to_date, $dst_adjust ), 'from' );
     248    public static function local_timestamp( $date, $dst_adjust=true ) {
     249        return self::gmt_timestamp( self::to_c( $date, $dst_adjust ), 'from' );
     250    }
     251
     252    // code to update all the site event start and end times to the same timezone as the SITE, in non-dst, is currently set to
     253    public static function normalize_event_times() {
     254        // get current site timeoffset
     255        $offset = self::non_dst_tz_offset();
     256
     257        $perpage = 1000;
     258        $pg_offset = 1;
     259        // get a list of all the event ids to update. throttle at 1000 per cycle
     260        $args = array(
     261            'post_type' => 'qsot-event',
     262            'post_status' => array( 'any', 'trash' ),
     263            'post_parent__not_in' => array( 0 ),
     264            'fields' => 'ids',
     265            'posts_per_page' => $perpage,
     266            'paged' => $pg_offset,
     267        );
     268
     269        // grab the next 1000
     270        while ( $event_ids = get_posts( $args ) ) {
     271            // inc page for next iteration
     272            $pg_offset++;
     273            $args['paged'] = $pg_offset;
     274
     275            // cycle through all results
     276            while ( is_array( $event_ids ) && count( $event_ids ) ) {
     277                // get the next event_id to update
     278                $event_id = array_shift( $event_ids );
     279
     280                // get the start and end time of this event from db
     281                $start = get_post_meta( $event_id, '_start', true );
     282                $end = get_post_meta( $event_id, '_end', true );
     283                $orig_values = array( 'start' => $start, 'end' => $end );
     284
     285                // normalize each time so that it does not include an offset
     286                $start = preg_replace( '#^(\d{4}-\d{2}-\d{2})(?:T| )(\d{2}:\d{2}:\d{2}).*$#', '\1T\2', $start );
     287                $end = preg_replace( '#^(\d{4}-\d{2}-\d{2})(?:T| )(\d{2}:\d{2}:\d{2}).*$#', '\1T\2', $end );
     288
     289                // update each time to include the correct offset
     290                $start .= $offset;
     291                $end .= $offset;
     292
     293                // save both times in the new format
     294                update_post_meta( $event_id, '_start', $start );
     295                update_post_meta( $event_id, '_end', $end );
     296                // save original bad values for posterity
     297                add_post_meta( $event_id, '_tsFix_update', $orig_values );
     298            }
     299        }
     300
     301        // add a record of the last time this ran
     302        update_option( '_last_run_otce_normalize_event_times', time() );
    172303    }
    173304}
  • opentickets-community-edition/trunk/launcher.php

    r1529668 r1532350  
    44 * Plugin URI:  http://opentickets.com/
    55 * Description: Event Management and Online Ticket Sales Platform
    6  * Version:     2.5.2
     6 * Version:     2.5.3
    77 * Author:      Quadshot Software LLC
    88 * Author URI:  http://quadshot.com/
     
    5454            'fctm' => 'fc',
    5555            'always_reserve' => 0,
    56             'version' => '2.5.2',
     56            'version' => '2.5.3',
    5757            'min_wc_version' => '2.6.1',
    5858            'core_post_type' => 'qsot-event',
  • opentickets-community-edition/trunk/opentickets.php

    r1373382 r1532350  
    6161        register_activation_hook(self::$o->core_file, array(__CLASS__, 'activation'));
    6262        add_action( 'upgrader_process_complete', array( __CLASS__, 'maybe_activation_on_upgrade' ), 10, 2 );
     63        add_action( 'admin_init', array( __CLASS__, 'maybe_update_event_timestamps' ), 100 );
    6364
    6465        add_action('woocommerce_email_classes', array(__CLASS__, 'load_custom_emails'), 2);
     
    748749        // run the activation sequence
    749750        self::activation();
     751    }
     752
     753    // on admin load, check if we need to update all the event timestamps now. if so, do it
     754    public static function maybe_update_event_timestamps() {
     755        // find out the last time the timestamp updater ran
     756        $last_run = get_option( '_last_run_otce_normalize_event_times', '' );
     757
     758        // if it never ran, do it now
     759        if ( ! $last_run )
     760            QSOT_Utils::normalize_event_times();
    750761    }
    751762
  • opentickets-community-edition/trunk/readme.txt

    r1529668 r1532350  
    171171
    172172== Changelog ==
     173
     174= 2.5.3 - Nov/11/2016 =
     175* [tweak] changing how we handle DST timestamps display again
    173176
    174177= 2.5.2 - Nov/7/2016 =
Note: See TracChangeset for help on using the changeset viewer.