How to use mysqlDateTime class

Best Atoum code snippet using mysqlDateTime

Event.php

Source:Event.php Github

copy

Full Screen

1<?php2/**3 * @brief Calendar Event Model4 *5 * @copyright (c) 2001 - SVN_YYYY Invision Power Services, Inc.6 *7 * @package IPS Social Suite8 * @subpackage Calendar9 * @since 7 Jan 201410 * @version SVN_VERSION_NUMBER11 */12namespace IPS\calendar;13/* To prevent PHP errors (extending class does not exist) revealing path */14if ( !defined( '\IPS\SUITE_UNIQUE_KEY' ) )15{16 header( ( isset( $_SERVER['SERVER_PROTOCOL'] ) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0' ) . ' 403 Forbidden' );17 exit;18}19/**20 * Calendar Event Model21 */22class _Event extends \IPS\Content\Item implements23\IPS\Content\Permissions,24\IPS\Content\Tags,25\IPS\Content\Reputation,26\IPS\Content\Followable,27\IPS\Content\ReportCenter,28\IPS\Content\ReadMarkers,29\IPS\Content\Hideable, \IPS\Content\Featurable, \IPS\Content\Lockable,30\IPS\Content\Shareable,31\IPS\Content\Searchable,32\IPS\Content\Embeddable33{34 /**35 * @brief Application36 */37 public static $application = 'calendar';38 39 /**40 * @brief Module41 */42 public static $module = 'calendar';43 44 /**45 * @brief Database Table46 */47 public static $databaseTable = 'calendar_events';48 49 /**50 * @brief Database Prefix51 */52 public static $databasePrefix = 'event_';53 54 /**55 * @brief Multiton Store56 */57 protected static $multitons;58 59 /**60 * @brief Node Class61 */62 public static $containerNodeClass = 'IPS\calendar\Calendar';63 64 /**65 * @brief Comment Class66 */67 public static $commentClass = 'IPS\calendar\Event\Comment';68 69 /**70 * @brief Review Class71 */72 public static $reviewClass = 'IPS\calendar\Event\Review';73 74 /**75 * @brief Database Column Map76 */77 public static $databaseColumnMap = array(78 'container' => 'calendar_id',79 'author' => 'member_id',80 'title' => 'title',81 'content' => 'content',82 'num_comments' => 'comments',83 'unapproved_comments' => 'queued_comments',84 'hidden_comments' => 'hidden_comments',85 'num_reviews' => 'reviews',86 'unapproved_reviews' => 'unapproved_reviews',87 'hidden_reviews' => 'hidden_reviews',88 'last_comment' => 'last_comment',89 'last_review' => 'last_review',90 'date' => 'saved',91 'updated' => 'lastupdated',92 'rating' => 'rating',93 'approved' => 'approved',94 'approved_by' => 'approved_by',95 'approved_date' => 'approved_on',96 'featured' => 'featured',97 'locked' => 'locked',98 'ip_address' => 'ip_address',99 'cover_photo' => 'cover_photo',100 'cover_photo_offset' => 'cover_offset',101 );102 103 /**104 * @brief Title105 */106 public static $title = 'calendar_event';107 108 /**109 * @brief Icon110 */111 public static $icon = 'calendar';112 113 /**114 * @brief Form Lang Prefix115 */116 public static $formLangPrefix = 'event_';117 118 /**119 * @brief Reputation Type120 */121 public static $reputationType = 'event_id';122 123 /**124 * @brief Cover Photo Storage Extension125 */126 public static $coverPhotoStorageExtension = 'calendar_Events';127 /**128 * @brief Cached date objects129 */130 protected $dateObjects = array( 'start' => NULL, 'end' => NULL );131 132 /**133 * @brief [Content] Key for hide reasons134 */135 public static $hideLogKey = 'calendar-event';136 /**137 * @brief RSVP statuses138 */139 const RSVP_NO = 0;140 const RSVP_YES = 1;141 const RSVP_MAYBE = 2;142 143 /**144 * Columns needed to query for search result / stream view145 *146 * @return array147 */148 public static function basicDataColumns()149 {150 $return = parent::basicDataColumns();151 $return[] = 'event_recurring';152 $return[] = 'event_start_date';153 $return[] = 'event_end_date';154 $return[] = 'event_all_day';155 return $return;156 }157 158 /**159 * Set the title160 *161 * @param string $title Title162 * @return void163 */164 public function set_title( $title )165 {166 $this->_data['title'] = $title;167 $this->_data['title_seo'] = \IPS\Http\Url::seoTitle( $title );168 }169 /**170 * Get SEO name171 *172 * @return string173 */174 public function get_title_seo()175 {176 if( !$this->_data['title_seo'] )177 {178 $this->title_seo = \IPS\Http\Url::seoTitle( $this->title );179 $this->save();180 }181 return $this->_data['title_seo'] ?: \IPS\Http\Url::seoTitle( $this->title );182 }183 /**184 * Get the album HTML, if there is one associated185 *186 * @return string187 */188 public function get__album()189 {190 if( \IPS\Application::appIsEnabled( 'gallery' ) AND $this->album )191 {192 try193 {194 $album = \IPS\gallery\Album::loadAndCheckPerms( $this->album );195 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'gallery.css', 'gallery', 'front' ) );196 if ( \IPS\Theme::i()->settings['responsive'] )197 {198 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'gallery_responsive.css', 'gallery', 'front' ) );199 }200 return \IPS\Theme::i()->getTemplate( 'browse', 'gallery', 'front' )->miniAlbum( $album );201 }202 catch( \OutOfRangeException $e ){}203 catch( \UnderflowException $e ){}204 }205 return '';206 }207 /**208 * Get the recurring event text209 *210 * @return string211 */212 public function get__recurring_text()213 {214 $recurringData = \IPS\calendar\Icalendar\ICSParser::parseRrule( $this->recurring );215 /* If the event does not repeat, just return */216 if( !$recurringData['event_repeat'] )217 {218 return '';219 }220 /* Hold parameters to sprintf() into the language string */221 $params = array();222 /* Figure out the basic language string */223 $langString = "recur_human_" . $recurringData['event_repeats'];224 if( $recurringData['event_repeat_freq'] > 1 )225 {226 $langString = $langString . '_multi';227 $params[] = $recurringData['event_repeat_freq'];228 }229 230 /* If recurring weekly, take days into account */231 if( $recurringData['event_repeats'] == 'weekly' )232 {233 $days = array();234 foreach( \IPS\calendar\Date::getDayNames() as $day )235 {236 if( $recurringData['repeat_freq_on_' . $day['ical'] ] )237 {238 $days[] = $day['full'];239 }240 }241 if( count( $days ) )242 {243 $langString = $langString . '_days';244 $params[] = \IPS\Member::loggedIn()->language()->formatList( $days );245 }246 }247 /* Finally, reflect the ending data */248 if( $recurringData['repeat_end_occurrences'] )249 {250 $params[] = \IPS\Member::loggedIn()->language()->addToStack( 'recur_human__occurrences', FALSE, array( 'pluralize' => array( $recurringData['repeat_end_occurrences'] ) ) );251 }252 elseif( $recurringData['repeat_end_date'] )253 {254 $params[] = \IPS\Member::loggedIn()->language()->addToStack( 'recur_human__until', FALSE, array( 'sprintf' => array( $recurringData['repeat_end_date']->localeDate() ) ) );255 }256 else257 {258 $params[] = \IPS\Member::loggedIn()->language()->addToStack('recur_human__forever');259 }260 return \IPS\Member::loggedIn()->language()->addToStack( $langString, FALSE, array( 'sprintf' => $params ) );261 }262 /**263 * @brief Cached occurrences - this may or may not satisfy a query to nextOccurrence()264 */265 protected $parsedOccurrences = array();266 /**267 * Find occurrences of an event within a supplied date range268 *269 * @param \IPS\calendar\Date $startDate Date to start from270 * @param \IPS\calendar\Date $endDate Date to end at271 * @return array272 */273 public function findOccurrences( $startDate, $endDate )274 {275 $results = array();276 if( !$this->recurring )277 {278 return $results;279 }280 /* Parse out our recurrence data */281 $recurringData = \IPS\calendar\Icalendar\ICSParser::parseRrule( $this->recurring );282 if( !$recurringData['event_repeat'] )283 {284 return $results;285 }286 /* If this event starts after our ending range, it doesn't qualify */287 if( $this->_start_date->mysqlDatetime( FALSE ) > $endDate->mysqlDatetime( FALSE ) )288 {289 return $results;290 }291 /* If the recurrences have an end date, and the end date is before our start range, it doesn't qualify */292 if( $recurringData['repeat_end_date'] !== NULL AND $recurringData['repeat_end_date']->mysqlDatetime( FALSE ) < $startDate->mysqlDatetime( FALSE ) )293 {294 /* Actually, this isn't true...I had an event that "ended" on March 24 but because it was a recurring ranged event, the last occurrence was March 22-March 25 */295 //return $results;296 }297 /* Return the results we found after storing them */298 $this->parsedOccurrences = static::_findOccurances( $this->_start_date, $this->_end_date, $startDate, $endDate, $recurringData );299 return $this->parsedOccurrences;300 }301 302 /**303 * Get occurances304 *305 * @param \IPS\calendar\Date $eventStart Event start date306 * @param \IPS\calendar\Date $eventEnd Event end date307 * @param \IPS\calendar\Date $startDate Date to start from308 * @param \IPS\calendar\Date $endDate Date to end at309 * @param array $recurringData Reccurance data310 */311 public static function _findOccurances( $eventStart, $eventEnd, $startDate, $endDate, $recurringData )312 {313 $instances = array();314 $occurrences = 0;315 $keyword = NULL;316 $results = array();317 switch( $recurringData['event_repeats'] )318 {319 case 'daily':320 $keyword = "days";321 break;322 case 'weekly':323 /* Get the days we repeat on */324 $_repeatDays = array();325 foreach( \IPS\calendar\Date::getDayNames() as $day )326 {327 if( $recurringData['repeat_freq_on_' . $day['ical'] ] == TRUE )328 {329 $_repeatDays[] = $day['english'];330 }331 }332 /* If not repeating only on specific days then we have a normal recurring event */333 if( !count($_repeatDays) )334 {335 $keyword = 'weeks';336 }337 else338 {339 $date = $eventStart;340 $eDate = $eventEnd;341 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR342 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR343 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )344 )345 {346 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );347 }348 349 /* Figure out which of teh days is next. For example, if the start date is a Wednesday, and the350 event repeats every Monday and Friday, we need to start with Friday (not Monday) because that's351 when the first occurance is */352 $nextTimes = array();353 foreach ( $_repeatDays as $repeatDay )354 {355 $nextTimes[ $repeatDay ] = $date->adjust( "next {$repeatDay}" )->getTimestamp();356 }357 asort( $nextTimes );358 $nextTimes = array_keys( $nextTimes );359 $nextDay = array_shift( $nextTimes );360 /* Do we have an occurrences limit? */361 if( $recurringData['repeat_end_occurrences'] )362 {363 while( $occurrences < $recurringData['repeat_end_occurrences'] )364 {365 $date = $date->adjust( "next {$nextDay}" );366 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "next {$nextDay}" ) : NULL;367 $occurrences++;368 /* Figure out the next day this occurs on */369 $nextDay = next( $_repeatDays );370 if( $nextDay === FALSE )371 {372 reset( $_repeatDays );373 $nextDay = current( $_repeatDays );374 }375 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR376 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR377 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )378 )379 {380 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );381 }382 }383 }384 /* Do we have an end date for the recurrences? */385 else if( $recurringData['repeat_end_date'] )386 {387 while( $date->mysqlDatetime( FALSE ) < $recurringData['repeat_end_date']->mysqlDatetime( FALSE ) )388 {389 $date = $date->adjust( "next {$nextDay}" );390 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "next {$nextDay}" ) : NULL;391 /* Figure out the next day this occurs on */392 $nextDay = next( $_repeatDays );393 if( $nextDay === FALSE )394 {395 reset( $_repeatDays );396 $nextDay = current( $_repeatDays );397 }398 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR399 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR400 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )401 )402 {403 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );404 }405 }406 }407 /* Recurs indefinitely... the most fun type... */408 else409 {410 while( $date->mysqlDatetime( FALSE ) < $endDate->mysqlDatetime( FALSE ) )411 {412 $date = $date->adjust( "next {$nextDay}" );413 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "next {$nextDay}" ) : NULL;414 /* Figure out the next day this occurs on */415 $nextDay = next( $_repeatDays );416 if( $nextDay === FALSE )417 {418 reset( $_repeatDays );419 $nextDay = current( $_repeatDays );420 }421 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR422 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR423 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )424 )425 {426 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );427 }428 }429 }430 }431 break;432 case 'monthly':433 $keyword = "months";434 break;435 case 'yearly':436 $keyword = "years";437 break;438 }439 /* Normal recurrence checks */440 if( $keyword !== NULL )441 {442 $date = $eventStart;443 $eDate = $eventEnd;444 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR445 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR446 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )447 )448 {449 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );450 }451 /* Do we have an occurrences limit? */452 if( $recurringData['repeat_end_occurrences'] )453 {454 while( $occurrences < $recurringData['repeat_end_occurrences'] )455 {456 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR457 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR458 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )459 )460 {461 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );462 }463 $date = $date->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" );464 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" ) : NULL;465 $occurrences++;466 }467 }468 /* Do we have an end date for the recurrences? */469 else if( $recurringData['repeat_end_date'] )470 {471 $endDateToUse = ( $endDate->mysqlDatetime( FALSE ) < $recurringData['repeat_end_date']->mysqlDatetime( FALSE ) ) ? $endDate : $recurringData['repeat_end_date'];472 while( $date->mysqlDatetime( FALSE ) <= $endDateToUse->mysqlDatetime( FALSE ) )473 {474 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR475 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR476 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )477 )478 {479 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );480 }481 $date = $date->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" );482 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" ) : NULL;483 }484 }485 /* Recurs indefinitely... the most fun type... */486 else487 {488 while( $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) )489 {490 if( ( $date->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $date->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR491 ( $eDate !== NULL AND $eDate->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) <= $endDate->mysqlDatetime( FALSE ) ) OR492 ( $eDate !== NULL AND $date->mysqlDatetime( FALSE ) <= $startDate->mysqlDatetime( FALSE ) AND $eDate->mysqlDatetime( FALSE ) >= $endDate->mysqlDatetime( FALSE ) )493 )494 {495 $results[] = array( 'startDate' => $date, 'endDate' => $eDate );496 }497 $date = $date->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" );498 $eDate = ( $eDate !== NULL ) ? $eDate->adjust( "+{$recurringData['event_repeat_freq']} {$keyword}" ) : NULL;499 }500 }501 }502 503 return $results;504 }505 /**506 * Find the next occurrence of an event starting from a specified start point507 *508 * @param \IPS\calendar\Date $date Date to start from509 * @param string $type Type of date to check against (startDate or endDate)510 * @return \IPS\calendar\Date|NULL511 */512 public function nextOccurrence( $date, $type='startDate' )513 {514 /* If the event is not recurring, there is only one occurrence */515 if( !$this->recurring )516 {517 return ( $type === 'startDate' ) ? $this->_start_date : $this->_end_date;518 }519 /* This is typically called after findOccurrences() using the same start date, so try the cached array first */520 if( count( $this->parsedOccurrences ) )521 {522 foreach( $this->parsedOccurrences as $occurrence )523 {524 if( $occurrence[ $type ] AND $occurrence[ $type ]->mysqlDatetime( FALSE ) >= $date->mysqlDatetime( FALSE ) )525 {526 return $occurrence[ $type ];527 }528 }529 }530 /* Get the occurrences over the next year then and try from there. We go back one month to start with to account for the event stream. */531 foreach( $this->findOccurrences( $date->adjust( "-1 month" ), $date->adjust( "+2 years" ) ) as $occurrence )532 {533 if( $occurrence[ $type ] AND $occurrence[ $type ]->mysqlDatetime( FALSE ) >= $date->mysqlDatetime( FALSE ) )534 {535 return $occurrence[ $type ];536 }537 }538 /* No? Then just return NULL */539 return NULL;540 }541 /**542 * Return the last occurrence of a recurring event543 *544 * @param string $type Type of date to check against (startDate or endDate)545 * @return \IPS\calendar\Date546 */547 public function lastOccurrence( $type='startDate' )548 {549 /* If the event is not recurring, there is only one occurrence */550 if( !$this->recurring )551 {552 return ( $type === 'startDate' ) ? $this->_start_date : $this->_end_date;553 }554 /* This is typically called after findOccurrences() using the same start date, so try the cached array first */555 if( count( $this->parsedOccurrences ) )556 {557 $last = end( $this->parsedOccurrences );558 return ( isset( $last[ $type ] ) ) ? $last[ $type ] : NULL;559 }560 /* Get the occurrences over the next year then and try from there */561 $date = \IPS\calendar\Date::getDate();562 foreach( $this->findOccurrences( $date, $date->adjust( "+2 years" ) ) as $occurrence )563 {564 if( $occurrence[ $type ] AND $occurrence[ $type ]->mysqlDatetime( FALSE ) >= $date->mysqlDatetime( FALSE ) )565 {566 return $occurrence[ $type ];567 }568 }569 $date = \IPS\calendar\Date::getDate();570 $occurrences = $this->findOccurrences( $date->adjust( "-2 years" ), $date );571 $occurrence = array_pop( $occurrences );572 if( $occurrence[ $type ] )573 {574 return $occurrence[ $type ];575 }576 /* Fall back to the defined start date */577 return $this->_start_date;578 }579 /**580 * @brief RSVP attendees581 */582 protected $attendees = NULL;583 /**584 * Get the RSVP attendees585 *586 * @param int|NULL $type Type of RSVP attendees to count, or NULL for all587 * @param int|NULL $limit Maximum number of attendees to return, or NULL for all. Only available when $type is specified.588 * @return array589 * @throws \BadMethodCallException590 * @throws \InvalidArgumentException591 */592 public function attendees( $type=NULL, $limit=NULL )593 {594 /* RSVP enabled? */595 if( !$this->rsvp )596 {597 throw new \BadMethodCallException;598 }599 /* You can only limit results if retrieving a specific type */600 if( $type === NULL AND $limit !== NULL )601 {602 throw new \InvalidArgumentException;603 }604 /* Do we already have attendee list cached? */605 if( $this->attendees === NULL )606 {607 /* Fetch RSVP data and pass to template */608 $this->attendees = array( 0 => array(), 1 => array(), 2 => array() );609 foreach( \IPS\Db::i()->select( '*', 'calendar_event_rsvp', array( "rsvp_event_id=?", $this->id ) )->join( 'core_members', 'calendar_event_rsvp.rsvp_member_id=core_members.member_id' ) as $attendee )610 {611 $this->attendees[ $attendee['rsvp_response'] ][ $attendee['rsvp_member_id'] ] = \IPS\Member::constructFromData( $attendee );612 }613 }614 /* Return requested type and limit */615 if( $type !== NULL )616 {617 $results = $this->attendees[ $type ];618 if( $limit !== NULL )619 {620 return array_slice( $results, 0, $limit, FALSE );621 }622 else623 {624 return $results;625 }626 }627 return $this->attendees;628 }629 /**630 * Get the RSVP attendee count631 *632 * @param int|NULL $type Type of RSVP attendees to count, or NULL for all633 * @return int634 * @throws \BadMethodCallException635 */636 public function attendeeCount( $type=NULL )637 {638 $attendees = $this->attendees( $type );639 if( $type !== NULL )640 {641 return count( $attendees );642 }643 else644 {645 return ( count( $attendees[0] ) + count( $attendees[1] ) + count( $attendees[2] ) );646 }647 }648 /**649 * Get the start date for display650 *651 * @return \IPS\calendar\Date652 */653 public function get__start_date()654 { 655 if( $this->dateObjects['start'] === NULL )656 {657 $this->dateObjects['start'] = \IPS\calendar\Date::parseTime( $this->start_date, $this->all_day ? FALSE : TRUE );658 }659 660 return $this->dateObjects['start'];661 }662 /**663 * Get the end date for display664 *665 * @return \IPS\calendar\Date|NULL666 */667 public function get__end_date()668 {669 if( $this->dateObjects['end'] === NULL AND $this->end_date )670 {671 $this->dateObjects['end'] = \IPS\calendar\Date::parseTime( $this->end_date, $this->all_day ? FALSE : TRUE );672 }673 return $this->dateObjects['end'];674 }675 /**676 * @brief Cached URLs677 */678 protected $_url = array();679 680 /**681 * @brief URL Base682 */683 public static $urlBase = 'app=calendar&module=calendar&controller=event&id=';684 685 /**686 * @brief URL Base687 */688 public static $urlTemplate = 'calendar_event';689 690 /**691 * @brief SEO Title Column692 */693 public static $seoTitleColumn = 'title_seo';694 695 /**696 * Get URL for last comment page697 *698 * @return \IPS\Http\Url699 */700 public function lastCommentPageUrl()701 {702 return parent::lastCommentPageUrl()->setQueryString( 'tab', 'comments' );703 }704 705 /**706 * Get URL for last review page707 *708 * @return \IPS\Http\Url709 */710 public function lastReviewPageUrl()711 {712 return parent::lastCommentPageUrl()->setQueryString( 'tab', 'reviews' );713 }714 /**715 * Get template for content tables716 *717 * @return callable718 */719 public static function contentTableTemplate()720 {721 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'calendar.css', 'calendar' ) );722 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'calendar_responsive.css', 'calendar' ) );723 return array( \IPS\Theme::i()->getTemplate( 'global', 'calendar' ), 'rows' );724 }725 /**726 * HTML to manage an item's follows 727 *728 * @return callable729 */730 public static function manageFollowRows()731 {732 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'calendar.css', 'calendar' ) );733 \IPS\Output::i()->cssFiles = array_merge( \IPS\Output::i()->cssFiles, \IPS\Theme::i()->css( 'calendar_responsive.css', 'calendar' ) );734 return array( \IPS\Theme::i()->getTemplate( 'global', 'calendar', 'front' ), 'manageFollowRow' );735 }736 737 /**738 * Are comments supported by this class?739 *740 * @param \IPS\Member\NULL $member The member to check for or NULL fto not check permission741 * @return int742 */743 public static function supportsComments( \IPS\Member $member = NULL )744 { 745 return parent::supportsComments() and ( !$member or \IPS\calendar\Calendar::countWhere( 'read', $member, array( 'cal_allow_comments=1' ) ) );746 }747 748 /**749 * Are reviews supported by this class?750 *751 * @param \IPS\Member\NULL $member The member to check for or NULL to not check permission752 * @return int753 */754 public static function supportsReviews( \IPS\Member $member = NULL )755 {756 return parent::supportsReviews() and ( !$member or \IPS\calendar\Calendar::countWhere( 'read', $member, array( 'cal_allow_reviews=1' ) ) );757 }758 /**759 * Get available comment/review tabs760 *761 * @return array762 */763 public function commentReviewTabs()764 {765 $tabs = array();766 if ( $this->container()->allow_reviews )767 {768 $tabs['reviews'] = \IPS\Member::loggedIn()->language()->pluralize( \IPS\Member::loggedIn()->language()->get( 'event_review_count' ), array( $this->mapped('num_reviews') ) );769 }770 if ( $this->container()->allow_comments )771 {772 $tabs['comments'] = \IPS\Member::loggedIn()->language()->pluralize( \IPS\Member::loggedIn()->language()->get( 'event_comment_count' ), array( $this->mapped('num_comments') ) );773 }774 return $tabs;775 }776 777 /**778 * Get comment/review output779 *780 * @param string $tab Active tab781 * @return string782 */783 public function commentReviews( $tab )784 {785 if ( $tab === 'reviews' )786 {787 return \IPS\Theme::i()->getTemplate('view')->reviews( $this );788 }789 elseif( $tab === 'comments' )790 {791 return \IPS\Theme::i()->getTemplate('view')->comments( $this );792 }793 794 return '';795 }796 797 /**798 * Should new items be moderated?799 *800 * @param \IPS\Member $member The member posting801 * @param \IPS\Node\Model $container The container802 * @return bool803 */804 public static function moderateNewItems( \IPS\Member $member, \IPS\Node\Model $container = NULL )805 {806 if ( $container and $container->moderate and !$member->group['g_avoid_q'] )807 {808 return TRUE;809 }810 811 return parent::moderateNewItems( $member, $container );812 }813 814 /**815 * Should new comments be moderated?816 *817 * @param \IPS\Member $member The member posting818 * @return bool819 */820 public function moderateNewComments( \IPS\Member $member )821 {822 $commentClass = static::$commentClass;823 return $this->container()->comment_moderate and !$member->group['g_avoid_q'];824 }825 826 /**827 * Should new reviews be moderated?828 *829 * @param \IPS\Member $member The member posting830 * @return bool831 */832 public function moderateNewReviews( \IPS\Member $member )833 {834 $reviewClass = static::$reviewClass;835 return $this->container()->review_moderate and !$member->group['g_avoid_q'];836 }837 /**838 * Can view users who have RSVP'd?839 *840 * @param \IPS\Member|NULL $member The member to check or NULL for currently logged in member841 * @return bool842 */843 public function canViewRsvps( \IPS\Member $member = NULL )844 {845 return $this->can( 'rsvp', $member );846 }847 848 /**849 * Get elements for add/edit form850 *851 * @param \IPS\Content\Item|NULL $item The current item if editing or NULL if creating852 * @param int $container Container (e.g. forum) ID, if appropriate853 * @return array854 */855 public static function formElements( $item=NULL, \IPS\Node\Model $container=NULL )856 {857 $newDefault = date( 'Y-m-d' );858 $allDay = FALSE;859 if( \IPS\Request::i()->y AND \IPS\Request::i()->m AND \IPS\Request::i()->d )860 {861 $newDefault = \IPS\Request::i()->y . '-' . \IPS\Request::i()->m . '-' . \IPS\Request::i()->d;862 $allDay = TRUE;863 }864 /* We are using a custom template to provide an optimal experience for the user instead of a basic linear top-down form elements for the date fields */865 $dateValues = array(866 'single_day' => $item ? !$item->end_date : TRUE,867 'start_date' => $item ? \IPS\calendar\Date::parseTime( $item->start_date, $item->all_day ? FALSE : TRUE ) : \IPS\calendar\Date::parseTime( $newDefault ),868 'end_date' => ( $item AND $item->end_date ) ? \IPS\calendar\Date::parseTime( $item->end_date, $item->all_day ? FALSE : TRUE ) : NULL,869 'all_day' => $item ? $item->all_day : $allDay,870 'event_repeat' => $item ? $item->recurring : FALSE,871 'event_timezone' => \IPS\Member::loggedIn()->timezone ? \IPS\Member::loggedIn()->timezone : 'GMT',872 'start_time' => $item ? \IPS\calendar\Date::parseTime( $item->start_date, $item->all_day ? FALSE : TRUE )->format( 'H:i' ) : \IPS\calendar\Date::parseTime( $newDefault )->format( 'H:i' ),873 'end_time' => ( $item AND $item->end_date ) ? \IPS\calendar\Date::parseTime( $item->end_date, $item->all_day ? FALSE : TRUE )->format( 'H:i' ) : NULL,874 'event_repeats' => NULL, /* Daily, weekly, monthly, yearly */875 'event_repeat_freq' => NULL, /* Repeat every 1 day, 2 days, 3 days, etc. */876 'repeat_end_occurrences' => NULL, /* Ends after x occurrences */877 'repeat_end_date' => NULL, /* Ends on x date (which is separate from the event end date - e.g. jan 9 2014 3pm to jan 10 2014 3pm, repeat annually until jan 9 2019) */878 );879 foreach( \IPS\calendar\Date::getDayNames() as $day )880 {881 $dateValues['repeat_freq_on_' . $day['ical'] ] = NULL; /* If repeating weekly, this is the days of the week as checkboxes (e.g. repeat every wed, fri and sat) */882 }883 /* Figure out the recurrence data if we are editing */884 if( $item AND $item->recurring )885 {886 try887 {888 $dateValues = array_merge( $dateValues, \IPS\calendar\Icalendar\ICSParser::parseRrule( $item->recurring, 'UTC' ) );889 }890 catch( \InvalidArgumentException $e ){}891 }892 $return['dates'] = new \IPS\Helpers\Form\Custom( 'event_dates', $dateValues, FALSE, array( 'getHtml' => function( $element )893 {894 return \IPS\Theme::i()->getTemplate( 'submit' )->datesForm( $element->name, $element->value, \IPS\calendar\Date::getTimezones(), $element->error );895 } ), function( $val )896 {897 /* Anything but Chrome, basically, falls back to a text input and submitter might submit 22.00 instead of 22:00 */898 if( isset( $val['start_time'] ) )899 {900 $val['start_time'] = str_replace( '.', ':', $val['start_time'] );901 }902 if( isset( $val['end_time'] ) )903 {904 $val['end_time'] = str_replace( '.', ':', $val['end_time'] );905 }906 try907 {908 $start = \IPS\calendar\Date::createFromForm( $val['start_date'], ( ( !isset( $val['all_day'] ) OR !$val['all_day'] ) ? $val['start_time'] : NULL ), ( isset( $val['all_day'] ) AND $val['all_day'] ) ? 'UTC' : $val['event_timezone'] )->format( 'Y-m-d H:i' );909 }910 catch( \Exception $e )911 {912 throw new \DomainException( "invalid_start_date" );913 }914 $end = null;915 if( isset( $val['end_date'] ) AND $val['end_date'] )916 {917 if( !isset( $val['single_day'] ) OR !$val['single_day'] )918 {919 if ( !isset( $val['all_day'] ) OR !$val['all_day'] OR $val['end_date'] != $val['start_date'] )920 {921 try922 {923 $end = \IPS\calendar\Date::createFromForm( $val['end_date'], ( ( !isset( $val['all_day'] ) OR !$val['all_day'] ) ? $val['end_time'] : NULL ), ( isset( $val['all_day'] ) AND $val['all_day'] ) ? 'UTC' : $val['event_timezone'] )->format( 'Y-m-d H:i' );924 }925 catch( \Exception $e )926 {927 throw new \DomainException( "invalid_end_date" );928 }929 }930 }931 }932 /* Check the dates */933 if( $start === NULL )934 {935 throw new \DomainException( "invalid_start_date" );936 }937 try938 {939 \IPS\calendar\Date::parseTime( $start, FALSE );940 }941 catch( \InvalidArgumentException $e )942 {943 throw new \DomainException( "invalid_start_date" );944 }945 if( $end )946 {947 if ( $end < $start )948 {949 throw new \DomainException( 'end_date_before_start' );950 }951 try952 {953 \IPS\calendar\Date::parseTime( $start, FALSE );954 }955 catch( \InvalidArgumentException $e )956 {957 throw new \DomainException( "invalid_end_date" );958 }959 }960 961 }, NULL, NULL, 'event_dates' );962 963 /* Init */964 $return['calendar'] = new \IPS\Helpers\Form\Node( static::$formLangPrefix . 'container', $container ? $container->id : ( isset( \IPS\Request::i()->id ) ? \IPS\Request::i()->id : NULL ), TRUE, array(965 'url' => \IPS\Http\Url::internal( 'app=calendar&module=calendar&controller=submit', 'front', 'calendar_submit' ),966 'class' => 'IPS\calendar\Calendar',967 'permissionCheck' => 'add',968 'togglePerm' => 'askrsvp',969 'toggleIds' => array( 'event_rsvp' ),970 ) );971 /* Get default elements */972 $return = array_merge( $return, parent::formElements( $item, $container ) );973 974 /* Event description */975 $return['description'] = new \IPS\Helpers\Form\Editor( 'event_content', $item ? $item->content : NULL, TRUE, array( 'app' => 'calendar', 'key' => 'Calendar', 'autoSaveKey' => 'calendar-event', 'attachIds' => ( $item === NULL ? NULL : array( $item->id ) ) ) );976 /* Cover photo and location */977 $return['header'] = new \IPS\Helpers\Form\Upload( 'event_cover_photo', ( $item AND $item->cover_photo ) ? \IPS\File::get( 'calendar_Events', $item->cover_photo ) : NULL, FALSE, array( 'image' => TRUE, 'storageExtension' => 'calendar_Events' ) );978 $return['location'] = new \IPS\Helpers\Form\Address( 'event_location', ( $item AND $item->location ) ? \IPS\GeoLocation::buildFromJson( $item->location ) : NULL, FALSE, array( 'minimize' => TRUE, 'requireFullAddress' => FALSE ) );979 /* Gallery album association */980 if( \IPS\Application::appIsEnabled( 'gallery' ) )981 {982 $return['album'] = new \IPS\Helpers\Form\Node( 'event_album', ( $item AND $item->album ) ? $item->album : NULL, FALSE, array( 983 'url' => \IPS\Http\Url::internal( 'app=calendar&module=calendar&controller=submit', 'front', 'calendar_submit' ),984 'class' => 'IPS\gallery\Album',985 'permissionCheck' => 'add',986 ) );987 }988 /* Event - request RSVP */989 $return['rsvp'] = new \IPS\Helpers\Form\YesNo( 'event_rsvp', $item ? $item->rsvp : NULL, FALSE, array( 'togglesOn' => array( 'event_rsvp_limit' ) ), NULL, NULL, NULL, 'event_rsvp' );990 $return['rsvplimit'] = new \IPS\Helpers\Form\Number( 'event_rsvp_limit', $item ? $item->rsvp_limit : -1, FALSE, array( 'unlimited' => -1 ), NULL, NULL, NULL, 'event_rsvp_limit' );991 return $return;992 }993 /**994 * Process created object BEFORE the object has been created995 *996 * @param array $values Values from form997 * @return void998 */999 protected function processBeforeCreate( $values )1000 {1001 /* Post key is very much needed because...bacon */1002 $this->post_key = isset( $values['post_key'] ) ? $values['post_key'] : md5( uniqid() );1003 parent::processBeforeCreate( $values );1004 }1005 /**1006 * Process create/edit form1007 *1008 * @param array $values Values from form1009 * @return void1010 */1011 public function processForm( $values )1012 { 1013 /* Anything but Chrome, basically, falls back to a text input and submitter might submit 22.00 instead of 22:00 */1014 if( isset( $values['event_dates']['start_time'] ) )1015 {1016 $values['event_dates']['start_time'] = str_replace( '.', ':', $values['event_dates']['start_time'] );1017 }1018 if( isset( $values['event_dates']['end_time'] ) )1019 {1020 $values['event_dates']['end_time'] = str_replace( '.', ':', $values['event_dates']['end_time'] );1021 }1022 /* Calendar */1023 $this->calendar_id = ( $values[ static::$formLangPrefix . 'container' ] instanceof \IPS\Node\Model ) ? $values[ static::$formLangPrefix . 'container' ]->_id : intval( $values[ static::$formLangPrefix . 'container' ] );1024 /* Start and end dates */1025 $this->start_date = \IPS\calendar\Date::createFromForm( $values['event_dates']['start_date'], ( ( !isset( $values['event_dates']['all_day'] ) OR !$values['event_dates']['all_day'] ) ? $values['event_dates']['start_time'] : NULL ), ( isset( $values['event_dates']['all_day'] ) AND $values['event_dates']['all_day'] ) ? 'UTC' : $values['event_dates']['event_timezone'] )->format( 'Y-m-d H:i' );1026 $this->end_date = null;1027 if( isset( $values['event_dates']['end_date'] ) AND $values['event_dates']['end_date'] )1028 {1029 if( !isset( $values['event_dates']['single_day'] ) OR !$values['event_dates']['single_day'] )1030 {1031 if ( !isset( $values['event_dates']['all_day'] ) OR !$values['event_dates']['all_day'] OR $values['event_dates']['end_date'] != $values['event_dates']['start_date'] )1032 {1033 $this->end_date = \IPS\calendar\Date::createFromForm( $values['event_dates']['end_date'], ( ( !isset( $values['event_dates']['all_day'] ) OR !$values['event_dates']['all_day'] ) ? $values['event_dates']['end_time'] : NULL ), ( isset( $values['event_dates']['all_day'] ) AND $values['event_dates']['all_day'] ) ? 'UTC' : $values['event_dates']['event_timezone'] )->format( 'Y-m-d H:i' );1034 }1035 }1036 else if( ( !isset( $values['event_dates']['all_day'] ) OR !$values['event_dates']['all_day'] ) AND $values['event_dates']['end_time'] != $values['event_dates']['start_time'] )1037 {1038 $this->end_date = \IPS\calendar\Date::createFromForm( $values['event_dates']['start_date'], $values['event_dates']['end_time'], ( isset( $values['event_dates']['all_day'] ) AND $values['event_dates']['all_day'] ) ? 'UTC' : $values['event_dates']['event_timezone'] )->format( 'Y-m-d H:i' );1039 }1040 }1041 else if( ( !isset( $values['event_dates']['all_day'] ) OR !$values['event_dates']['all_day'] ) AND $values['event_dates']['end_time'] != $values['event_dates']['start_time'] )1042 {1043 $this->end_date = \IPS\calendar\Date::createFromForm( $values['event_dates']['start_date'], $values['event_dates']['end_time'], ( isset( $values['event_dates']['all_day'] ) AND $values['event_dates']['all_day'] ) ? 'UTC' : $values['event_dates']['event_timezone'] )->format( 'Y-m-d H:i' );1044 }1045 /* Now set all day flag */1046 $this->all_day = (int) ( isset( $values['event_dates']['all_day'] ) AND $values['event_dates']['all_day'] );1047 /* Need to set recurring values */1048 $this->recurring = \IPS\calendar\Icalendar\ICSParser::buildRrule( $values['event_dates'] );1049 /* Set content */1050 if ( !$this->_new )1051 {1052 $oldContent = $this->content;1053 }1054 $this->content = $values['event_content'];1055 if ( !$this->_new )1056 {1057 $this->sendAfterEditNotifications( $oldContent );1058 }1059 /* Cover photo */1060 $this->cover_photo = ( $values['event_cover_photo'] !== NULL ) ? $values['event_cover_photo']->url : NULL;1061 /* Set location */1062 $this->location = ( $values['event_location'] !== NULL ) ? json_encode( $values['event_location'] ) : NULL;1063 /* Gallery album association */1064 if( \IPS\Application::appIsEnabled( 'gallery' ) AND $values['event_album'] instanceof \IPS\gallery\Album )1065 {1066 $this->album = $values['event_album']->_id;1067 }1068 else1069 {1070 $this->album = NULL;1071 }1072 /* RSVP options */1073 $this->rsvp = $values['event_rsvp'];1074 $this->rsvp_limit = $values['event_rsvp_limit'];1075 /* Get the normal stuff */1076 parent::processForm( $values );1077 }1078 /**1079 * Process created object AFTER the object has been created1080 *1081 * @param \IPS\Content\Comment|NULL $comment The first comment1082 * @param array $values Values from form1083 * @return void1084 */1085 protected function processAfterCreate( $comment, $values )1086 {1087 parent::processAfterCreate( $comment, $values );1088 /* And claim attachments */1089 \IPS\File::claimAttachments( 'calendar-event', $this->id );1090 }1091 /**1092 * Delete Record1093 *1094 * @return void1095 */1096 public function delete()1097 {1098 parent::delete();1099 \IPS\Db::i()->delete( 'calendar_event_rsvp', array( 'rsvp_event_id=?', $this->id ) );1100 1101 /* We should not delete maps for imported events, because we do not want to reimport them */1102 //\IPS\Db::i()->delete( 'calendar_import_map', array( 'import_event_id=?', $this->id ) );1103 }1104 /**1105 * Return the map for the event, if location is specified1106 *1107 * @param int $width Width1108 * @param int $heigth Height1109 * @return string1110 * @note \BadMethodCallException can be thrown if the google maps integration is shut off - don't show any error if that happens.1111 */1112 public function map( $width, $height )1113 {1114 if( $this->location )1115 {1116 try1117 {1118 return \IPS\GeoLocation::buildFromJson( $this->location )->map()->render( $width, $height );1119 }1120 catch( \BadMethodCallException $e ){}1121 }1122 return '';1123 }1124 /**1125 * Retrieve events to show based on a provided start and end date, optionally filtering by a supplied calendar1126 *1127 * @param \IPS\calendar\Date $startDate Date to start from1128 * @param \IPS\calendar\Date|NULL $endDate Cut off date for events. NULL accepted as a possible value only if $formatEvents is set to FALSE.1129 * @param \IPS\calendar\Calendar|NULL|array $calendar Calendar to filter by1130 * @param int|null $limit Maximum number of events to return (only supported when not formatting events)1131 * @param bool $formatEvents Whether or not to format events into a structured array1132 * @return \IPS\Patterns\ActiveRecordIterator1133 * @throws \InvalidArgumentException1134 * @see \IPS\Content\_Item::getItemsWithPermission()1135 */1136 public static function retrieveEvents( $startDate, $endDate=NULL, $calendar=NULL, $limit=NULL, $formatEvents=TRUE, $member=NULL )1137 {1138 $where = array();1139 if( $calendar !== NULL )1140 {1141 if ( is_array( $calendar ) )1142 {1143 $where[] = array( \IPS\Db::i()->in( 'event_calendar_id', $calendar ) );1144 }1145 1146 else1147 {1148 $where[] = array( 'event_calendar_id=?', (int) $calendar->_id );1149 }1150 }1151 if( $endDate === NULL AND $formatEvents === TRUE )1152 {1153 throw new \InvalidArgumentException;1154 }1155 /* Load member */1156 if ( $member === NULL )1157 {1158 $member = \IPS\Member::loggedIn();1159 }1160 /* Get timezone adjusted versions of start/end time */1161 $startDateTimezone = \IPS\calendar\Date::parseTime( $startDate->mysqlDatetime() );1162 $endDateTimezone = ( $endDate !== NULL ) ? \IPS\calendar\Date::parseTime( $endDate->mysqlDatetime() ) : NULL;1163 if ( $member->timezone )1164 {1165 $startDateTimezone->setTimezone( new \DateTimeZone( 'UTC' ) );1166 if( $endDateTimezone !== NULL )1167 {1168 $endDateTimezone->setTimezone( new \DateTimeZone( 'UTC' ) );1169 }1170 }1171 /* First we get the non recurring events based on the timestamps */1172 $nonRecurring = array();1173 $nonRecurring[] = array( 'event_recurring IS NULL' );1174 if( $endDate !== NULL AND $startDate == $endDate )1175 {1176 $nonRecurring[] = array( 1177 '( 1178 ( event_end_date IS NULL AND DATE( event_start_date ) = ? AND event_all_day=1 )1179 OR1180 ( event_end_date IS NOT NULL AND DATE( event_start_date ) <= ? AND DATE( event_end_date ) >= ? AND event_all_day=1 )1181 OR1182 ( event_end_date IS NULL AND event_start_date >= ? AND event_start_date <= ? AND event_all_day=0 )1183 OR1184 ( event_end_date IS NOT NULL AND event_start_date <= ? AND event_end_date >= ? AND event_all_day=0 )1185 )',1186 $startDate->mysqlDatetime( FALSE ),1187 $endDate->mysqlDatetime( FALSE ),1188 $startDate->mysqlDatetime( FALSE ),1189 $startDateTimezone->mysqlDatetime(),1190 $startDateTimezone->adjust('+1 day')->mysqlDatetime(),1191 $endDateTimezone->adjust('+1 day')->mysqlDatetime(),1192 $startDateTimezone->mysqlDatetime()1193 );1194 }1195 elseif( $endDate !== NULL )1196 {1197 $nonRecurring[] = array( 1198 '( 1199 ( event_end_date IS NULL AND DATE( event_start_date ) >= ? AND DATE( event_start_date ) <= ? AND event_all_day=1 )1200 OR1201 ( event_end_date IS NOT NULL AND DATE( event_start_date ) <= ? AND DATE( event_end_date ) >= ? AND event_all_day=1 )1202 OR1203 ( event_end_date IS NULL AND event_start_date >= ? AND event_start_date <= ? AND event_all_day=0 )1204 OR1205 ( event_end_date IS NOT NULL AND event_start_date <= ? AND event_end_date >= ? AND event_all_day=0 )1206 )',1207 $startDate->mysqlDatetime( FALSE ),1208 $endDate->mysqlDatetime( FALSE ),1209 $endDate->mysqlDatetime( FALSE ),1210 $startDate->mysqlDatetime( FALSE ),1211 $startDateTimezone->mysqlDatetime(),1212 $endDateTimezone->mysqlDatetime(),1213 $endDateTimezone->mysqlDatetime(),1214 $startDateTimezone->mysqlDatetime()1215 );1216 }1217 else1218 {1219 $nonRecurring[] = array( 1220 "( 1221 ( DATE( event_start_date ) >= ? AND event_all_day=1 )1222 OR1223 ( event_start_date >= ? AND event_all_day=0 )1224 OR 1225 ( event_end_date IS NOT NULL AND DATE( event_start_date ) <= ? AND DATE( event_end_date ) >= ? AND event_all_day=1 ) 1226 OR1227 ( event_end_date IS NOT NULL AND event_start_date <= ? AND event_end_date >= ? AND event_all_day=0 ) 1228 )",1229 $startDate->mysqlDatetime( FALSE ),1230 $startDateTimezone->mysqlDatetime(),1231 $startDate->mysqlDatetime( FALSE ),1232 $startDate->mysqlDatetime( FALSE ),1233 $startDateTimezone->adjust('+1 day')->mysqlDatetime(),1234 $startDateTimezone->mysqlDatetime()1235 );1236 }1237 /* Get the non-recurring events */1238 $events = \IPS\calendar\Event::getItemsWithPermission( array_merge( $where, $nonRecurring ), 'event_start_date ASC', NULL, 'read', NULL, 0, $member );1239 /* We need to make sure ranged events repeat each day that they occur on */1240 $formattedEvents = array();1241 if( $formatEvents )1242 {1243 foreach( $events as $event )1244 {1245 /* Is this a ranged event? */1246 if( $event->_end_date !== NULL AND $event->_start_date->mysqlDatetime( FALSE ) < $event->_end_date->mysqlDatetime( FALSE ) )1247 {1248 $date = $event->_start_date;1249 while( $date->mysqlDatetime( FALSE ) < $event->_end_date->mysqlDatetime( FALSE ) )1250 {1251 $formattedEvents[ $date->mysqlDatetime( FALSE ) ]['ranged'][ $event->id ] = $event;1252 $date = $date->adjust( '+1 day' );1253 }1254 $formattedEvents[ $event->_end_date->mysqlDatetime( FALSE ) ]['ranged'][ $event->id ] = $event;1255 }1256 else1257 {1258 if( $event->all_day )1259 {1260 $formattedEvents[ \IPS\calendar\Date::parseTime( $event->start_date, FALSE )->mysqlDatetime( FALSE ) ]['single'][ $event->id ] = $event;1261 }1262 else1263 {1264 $formattedEvents[ $event->_start_date->mysqlDatetime( FALSE ) ]['single'][ $event->id ] = $event;1265 }1266 }1267 }1268 }1269 else1270 {1271 $formattedEvents = iterator_to_array( $events );1272 }1273 /* Now get the recurring events.... */1274 $recurringEvents = \IPS\calendar\Event::getItemsWithPermission( array_merge( $where, array( array( 'event_recurring IS NOT NULL' ) ) ), 'event_start_date ASC', NULL, 'read', NULL, 0, $member );1275 /* Loop over any results */1276 foreach( $recurringEvents as $event )1277 {1278 /* Find occurrences within our date range (if any) */1279 $occurrences = $event->findOccurrences( $startDate, ( $endDate ? $endDate : $startDate->adjust( "+2 years" ) ) );1280 /* Do we have any? */1281 if( count( $occurrences ) )1282 {1283 /* Are we formatting events? If so, place into the array as appropriate. */1284 if( $formatEvents )1285 {1286 foreach( $occurrences as $occurrence )1287 {1288 /* Is this a ranged repeating event? */1289 if( $occurrence['endDate'] !== NULL )1290 {1291 $date = $occurrence['startDate'];1292 while( $date->mysqlDatetime( FALSE ) < $occurrence['endDate']->mysqlDatetime( FALSE ) )1293 {1294 $formattedEvents[ $date->mysqlDatetime( FALSE ) ]['ranged'][ $event->id ] = $event;1295 $date = $date->adjust( '+1 day' );1296 }1297 $formattedEvents[ $occurrence['endDate']->mysqlDatetime( FALSE ) ]['ranged'][ $event->id ] = $event;1298 }1299 else1300 {1301 $formattedEvents[ $occurrence['startDate']->mysqlDatetime( FALSE ) ]['single'][ $event->id ] = $event;1302 }1303 }1304 }1305 /* Otherwise we only want one instance of the event in our final array */1306 else1307 {1308 $formattedEvents[] = $event;1309 }1310 }1311 }1312 /* Resort non-formatted events */1313 if( $formatEvents === FALSE )1314 {1315 /* @note: Error suppressor is needed due to PHP bug https://bugs.php.net/bug.php?id=50688 */1316 @usort( $formattedEvents, function( $a, $b ) use ( $startDate )1317 {1318 if ( $a->nextOccurrence( $startDate, 'startDate' )->mysqlDatetime() == $b->nextOccurrence( $startDate, 'startDate' )->mysqlDatetime() )1319 {1320 return 0;1321 }1322 1323 return ( $a->nextOccurrence( $startDate, 'startDate' )->mysqlDatetime() < $b->nextOccurrence( $startDate, 'startDate' )->mysqlDatetime() ) ? -1 : 1;1324 } );1325 /* Limiting? */1326 if( $limit !== NULL )1327 {1328 $formattedEvents = array_slice( $formattedEvents, 0, $limit, TRUE );1329 }1330 }1331 return $formattedEvents;1332 }1333 1334 /**1335 * Cover Photo1336 *1337 * @return \IPS\Helpers\CoverPhoto1338 */1339 public function coverPhoto()1340 {1341 $photo = parent::coverPhoto();1342 $photo->overlay = \IPS\Theme::i()->getTemplate( 'view', 'calendar' )->coverPhotoOverlay( $this );1343 return $photo;1344 }1345 /**1346 * Get HTML for search result display1347 *1348 * @return callable1349 */1350 public function approvalQueueHtml( $ref=NULL, $container, $title )1351 {1352 return \IPS\Theme::i()->getTemplate( 'modcp', 'calendar', 'front' )->approvalQueueItem( $this, $ref, $container, $title );1353 }1354 1355 /**1356 * Blurb ("On [date] in [calendar])1357 *1358 * @return string1359 */1360 public function eventBlurb()1361 {1362 $startDate = NULL;1363 $endDate = NULL;1364 $startTime = NULL;1365 $endTime = NULL;1366 1367 /* Start date */1368 if ( $startDate = $this->nextOccurrence( \IPS\calendar\Date::getDate(), 'startDate' ) )1369 {1370 $endDate = $this->nextOccurrence( $startDate, 'endDate' );1371 }1372 else1373 {1374 $startDate = $this->lastOccurrence( 'startDate' );1375 $endDate = $this->lastOccurrence( 'endDate' );1376 }1377 1378 /* Start time */1379 if ( !$this->all_day )1380 {1381 $startTime = $startDate->localeTime( FALSE );1382 if ( $endDate )1383 {1384 $endTime = $endDate->localeTime( FALSE );1385 }1386 }1387 1388 /* Put all that together */1389 $startDate = $startTime ? \IPS\Member::loggedIn()->language()->addToStack( 'blurb_date_with_time', FALSE, array( 'sprintf' => array( $startDate->calendarDate(), $startTime ) ) ) : $startDate->calendarDate();1390 $endDate = $endDate ? ( $endTime ? \IPS\Member::loggedIn()->language()->addToStack( 'blurb_date_with_time', FALSE, array( 'sprintf' => array( $endDate->calendarDate(), $endTime ) ) ) : $endDate->calendarDate() ) : NULL;1391 $calendar = "<a href='{$this->container()->url()}'>{$this->container()->_title}</a>";1392 return $endDate ? \IPS\Member::loggedIn()->language()->addToStack( 'blurb_start_and_end', FALSE, array( 'htmlsprintf' => array( $startDate, $endDate, $calendar ) ) ) : \IPS\Member::loggedIn()->language()->addToStack( 'blurb_start_only', FALSE, array( 'htmlsprintf' => array( $startDate, $calendar ) ) );1393 }1394 1395 /* !Embeddable */1396 1397 /**1398 * Get content for embed1399 *1400 * @param array $params Additional parameters to add to URL1401 * @return string1402 */1403 public function embedContent( $params )1404 {1405 return \IPS\Theme::i()->getTemplate( 'global', 'calendar' )->embedCalendar_event( $this, $this->url()->setQueryString( $params ) );1406 }1407 1408 /**1409 * Get snippet HTML for search result display1410 *1411 * @param array $indexData Data from the search index1412 * @param array $authorData Basic data about the author. Only includes columns returned by \IPS\Member::columnsForPhoto()1413 * @param array $itemData Basic data about the item. Only includes columns returned by item::basicDataColumns()1414 * @param array|NULL $containerData Basic data about the container. Only includes columns returned by container::basicDataColumns()1415 * @param array $reputationData Array of people who have given reputation and the reputation they gave1416 * @param int|NULL $reviewRating If this is a review, the rating1417 * @param string $view 'expanded' or 'condensed'1418 * @return callable1419 */1420 public static function searchResultSnippet( array $indexData, array $authorData, array $itemData, array $containerData = NULL, array $reputationData, $reviewRating, $view )1421 {1422 $startDate = \IPS\calendar\Date::parseTime( $itemData['event_start_date'], $itemData['event_all_day'] ? FALSE : TRUE );1423 $endDate = $itemData['event_end_date'] ? \IPS\calendar\Date::parseTime( $itemData['event_end_date'], $itemData['event_all_day'] ? FALSE : TRUE ) : NULL;1424 $nextOccurance = $startDate;1425 if ( $itemData['event_recurring'] )1426 {1427 $occurances = \IPS\calendar\Event::_findOccurances( $startDate, $endDate, $startDate->adjust( "-1 month" ), $startDate->adjust( "+2 years" ), \IPS\calendar\Icalendar\ICSParser::parseRrule( $itemData['event_recurring'] ) );1428 foreach( $occurances as $occurrence )1429 {1430 if( $occurrence['startDate'] AND $occurrence['startDate']->mysqlDatetime( FALSE ) >= $startDate->mysqlDatetime( FALSE ) )1431 {1432 $nextOccurance = $occurrence['startDate'];1433 break;1434 }1435 }1436 }1437 1438 return \IPS\Theme::i()->getTemplate( 'global', 'calendar', 'front' )->searchResultEventSnippet( $indexData, $itemData, $nextOccurance, $startDate, $endDate, $itemData['event_all_day'], $view == 'condensed' );1439 }1440}...

Full Screen

Full Screen

m991231_235959_insert_test_users.php

Source:m991231_235959_insert_test_users.php Github

copy

Full Screen

1<?php2use common\helpers\MySqlDateTime;3use yii\db\Migration;4class m991231_235959_insert_test_users extends Migration5{6 public function safeUp()7 {8 $this->batchInsert('{{user}}',9 ['id','uuid' ,'employee_id','first_name','last_name' ,'username','email' ,'active','locked','last_changed_utc' ,'last_synced_utc' ,'require_mfa','review_profile_after' ,'nag_for_mfa_after' ,'nag_for_method_after' ,'manager_email' ],[10 [ 1 ,'2b2d424e-8cb0-49c7-8c0b-7f660340f5fa','11111' ,'Testy' ,'Testerson' ,'a' ,'primaryA@example.org','yes' ,'no' , MySqlDateTime::now(), MySqlDateTime::now(),'no' , MySqlDateTime::today(), MySqlDateTime::today(), MySqlDateTime::today(),'managerA@example.org' ],11 [ 2 ,'2b2d424e-8cb0-49c7-8c0b-7f660340f5fb','22222' ,'Firsty' ,'Firsterson','b' ,'primaryB@example.org','yes' ,'no' , MySqlDateTime::now(), MySqlDateTime::now(),'no' , MySqlDateTime::today(), MySqlDateTime::today(), MySqlDateTime::today(),'managerB@example.org' ],12 ]);13 $this->batchInsert('{{password}}',14 ['id','user_id','hash' ,'created_utc' ,'expires_on' ,'grace_period_ends_on' ],[15 [ 1 , 1 ,'$2y$10$rKbAp0M8gewGpQKhD.U6qOSGDlMqKFkxK9tQZ15SZoieqYHYNsD/y', MySqlDateTime::now(), MySqlDateTime::relative('+1 year'), MySqlDateTime::relative('+1 year')], // password is 'a'16 ]);17 $this->batchInsert('{{invite}}',18 ['id','user_id','uuid' ,'created_utc' ,'expires_on' ],[19 [ 1 , 2 ,'2b2d424e-8cb0-49c7-8c0b-7f6603INVITE', MySqlDateTime::now(), MySqlDateTime::relative('+1 year')],20 ]);21 $this->update('{{user}}', ['current_password_id' => 1], 'id=1');22 }23 public function safeDown()24 {25 $this->delete('{{password}}', [26 'user_id' => [1]27 ]);28 $this->delete('{{invite}}', [29 'user_id' => [2]30 ]);31 $this->delete('{{user}}', [32 'id' => [1, 2]33 ]);34 }35}...

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1$mysqlDateTime = new mysqlDateTime();2$mysqlDateTime->now();3$mysqlDateTime->date();4$mysqlDateTime->time();5$mysqlDateTime->format('Y-m-d H:i:s');6$mysqlDateTime->format('Y-m-d');7$mysqlDateTime->format('H:i:s');8$mysqlDateTime->format('Y-m-d H:i:s');9$mysqlDateTime->format('Y-m-d');10$mysqlDateTime->format('H:i:s');11$mysqlDateTime->format('Y-m-d H:i:s');12$mysqlDateTime->format('Y-m-d');13$mysqlDateTime->format('H:i:s');14$mysqlDateTime->format('Y-m-d H:i:s');15$mysqlDateTime->format('Y-m-d');16$mysqlDateTime->format('H:i:s');17$mysqlDateTime->format('Y-m-d H:i:s');18$mysqlDateTime->format('Y-m-d');19$mysqlDateTime->format('H:i:s');20$mysqlDateTime->format('Y-m-d H:i:s');21$mysqlDateTime->format('Y-m-d');22$mysqlDateTime->format('H:i:s');23$mysqlDateTime->format('Y-m-d H:i:s');24$mysqlDateTime->format('Y-m-d');25$mysqlDateTime->format('H:i:s');26$mysqlDateTime->format('Y-m-d H

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1require_once 'mysqlDateTime.class.php';2$mysqlDateTime = new mysqlDateTime();3$mysqlDateTime->getDateTime();4$mysqlDateTime->getDate();5$mysqlDateTime->getTime();6$mysqlDateTime->getTimestamp();7$mysqlDateTime->getDateTime(4);8$mysqlDateTime->getDate(4);9$mysqlDateTime->getTime(4);10$mysqlDateTime->getTimestamp(4);11$mysqlDateTime->getDateTime(4,30);12$mysqlDateTime->getDate(4,30);13$mysqlDateTime->getTime(4,30);14$mysqlDateTime->getTimestamp(4,30);15$mysqlDateTime->getDateTime(4,30,30);16$mysqlDateTime->getDate(4,30,30);17$mysqlDateTime->getTime(4,30,30);18$mysqlDateTime->getTimestamp(4,30,30);19$mysqlDateTime->getDateTime(4,30,30,30);20$mysqlDateTime->getDate(4,30

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1require_once('mysqlDateTime.php');2use Atoum\mysqlDateTime as mysqlDateTime;3$mysqlDateTimeObj = new mysqlDateTime();4$timestamp = $mysqlDateTimeObj->getTimestamp();5echo 'Current timestamp: '.$timestamp;6$mysqlDateTime = $mysqlDateTimeObj->getMysqlDateTime();7echo 'Current mysql datetime: '.$mysqlDateTime;8$mysqlDate = $mysqlDateTimeObj->getMysqlDate();9echo 'Current mysql date: '.$mysqlDate;10$mysqlTime = $mysqlDateTimeObj->getMysqlTime();11echo 'Current mysql time: '.$mysqlTime;12$mysqlDateTime = $mysqlDateTimeObj->getMysqlDateTime('d-m-Y H:i:s');13echo 'Current mysql datetime in a specific format: '.$mysqlDateTime;14$mysqlDate = $mysqlDateTimeObj->getMysqlDate('d-m-Y');15echo 'Current mysql date in a specific format: '.$mysqlDate;16$mysqlTime = $mysqlDateTimeObj->getMysqlTime('H:i:s');17echo 'Current mysql time in a specific format: '.$mysqlTime;18$mysqlDateTime = $mysqlDateTimeObj->getMysqlDateTime('d-m-Y H:i:s', 'Asia/Kolkata');19echo 'Current mysql datetime in a specific format: '.$mysqlDateTime;20$mysqlDate = $mysqlDateTimeObj->getMysqlDate('d-m-Y', 'Asia/Kolkata');21echo 'Current mysql date in a specific format: '.$mysqlDate;22$mysqlTime = $mysqlDateTimeObj->getMysqlTime('H:i:s', 'Asia/Kolkata');23echo 'Current mysql time in a specific format: '.$mysqlTime;

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1require_once 'mysqlDateTime.php';2$date = new mysqlDateTime();3$date->setDate(2011, 12, 31);4$date->setTime(23, 59, 59);5echo $date->getMysqlDateTime();6echo $date->getMysqlDate();7echo $date->getMysqlTime();8echo $date->getMysqlTimestamp();9echo $date->getDateTime();10echo $date->getDate();11echo $date->getTime();12echo $date->getTimestamp();

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1require_once 'mysqlDateTime.class.php';2$mysqlDateTime = new mysqlDateTime();3$now = $mysqlDateTime->getNow();4$today = $mysqlDateTime->getToday();5$currentTime = $mysqlDateTime->getCurrentTime();6$year = $mysqlDateTime->getYear();7$month = $mysqlDateTime->getMonth();8$day = $mysqlDateTime->getDay();9$hour = $mysqlDateTime->getHour();10$minute = $mysqlDateTime->getMinute();11$second = $mysqlDateTime->getSecond();12$weekDay = $mysqlDateTime->getWeekDay();13$weekDayName = $mysqlDateTime->getWeekDayName();14$monthName = $mysqlDateTime->getMonthName();15$timeZone = $mysqlDateTime->getTimeZone();16$timeZoneName = $mysqlDateTime->getTimeZoneName();17$timeZoneOffset = $mysqlDateTime->getTimeZoneOffset();18$timeZoneAbbreviation = $mysqlDateTime->getTimeZoneAbbreviation();19$timeZoneDST = $mysqlDateTime->getTimeZoneDST();20$timeZoneDSTOffset = $mysqlDateTime->getTimeZoneDSTOffset();21$timeZoneDSTAbbreviation = $mysqlDateTime->getTimeZoneDSTAbbreviation();22$timeZoneDSTStart = $mysqlDateTime->getTimeZoneDSTStart();23$timeZoneDSTEnd = $mysqlDateTime->getTimeZoneDSTEnd();24$timeZoneDSTTransition = $mysqlDateTime->getTimeZoneDSTTransition();25$timeZoneDSTOffset = $mysqlDateTime->getTimeZoneDSTOffset();

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1require_once 'mysqlDateTime.class.php';2$mysqlDateTime = new mysqlDateTime('2011-06-29 13:00:00');3echo $mysqlDateTime->getDateTime();4require_once 'mysqlDateTime.class.php';5$mysqlDateTime = new mysqlDateTime();6echo $mysqlDateTime->getDateTime();7require_once 'mysqlDateTime.class.php';8$mysqlDateTime = new mysqlDateTime('2011/06/29 13:00:00');9echo $mysqlDateTime->getDateTime();10require_once 'mysqlDateTime.class.php';11$mysqlDateTime = new mysqlDateTime('2011-06-29');12echo $mysqlDateTime->getDateTime();13require_once 'mysqlDateTime.class.php';14$mysqlDateTime = new mysqlDateTime('2011-06-29 13:00:00');15echo $mysqlDateTime->getDateTime('d/m/Y H:i:s');16require_once 'mysqlDateTime.class.php';17$mysqlDateTime = new mysqlDateTime('2011-06-29 13:00:00');18echo $mysqlDateTime->getDateTime('d/m/Y');19require_once 'mysqlDateTime.class.php';20$mysqlDateTime = new mysqlDateTime('2011-06-29 13:00:00');21echo $mysqlDateTime->getDateTime('d/m/Y', '2011-06-29 12:00:00');

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();2$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();3$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();4$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();5$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();6$mysqlDateTime = new \atoum\atoum\tools\dateTime\mysqlDateTime();

Full Screen

Full Screen

mysqlDateTime

Using AI Code Generation

copy

Full Screen

1$mysqlDateTime = new mysqlDateTime();2echo $mysqlDateTime->getDateTime();3echo $mysqlDateTime->getDate();4echo $mysqlDateTime->getTime();5$mysqlDateTime = new mysqlDateTime();6echo $mysqlDateTime->getDateTime();7echo $mysqlDateTime->getDate();8echo $mysqlDateTime->getTime();

Full Screen

Full Screen

Automation Testing Tutorials

Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.

LambdaTest Learning Hubs:

YouTube

You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.

Run Atoum automation tests on LambdaTest cloud grid

Perform automation testing on 3000+ real desktop and mobile devices online.

Most used methods in mysqlDateTime

Run Selenium Automation Tests on LambdaTest Cloud Grid

Trigger Selenium automation tests on a cloud-based Grid of 3000+ real browsers and operating systems.

Test now for Free

Try LambdaTest Now !!

Get 100 minutes of automation test minutes FREE!!

Next-Gen App & Browser Testing Cloud

Was this article helpful?

Helpful

NotHelpful