PageRenderTime 54ms CodeModel.GetById 34ms RepoModel.GetById 0ms app.codeStats 1ms

/Model/Behavior/TimeBehavior.php

https://bitbucket.org/daveschwan/ronin-group
PHP | 241 lines | 108 code | 42 blank | 91 comment | 28 complexity | b8c5f0e118bc303480a151b05fa1e914 MD5 | raw file
Possible License(s): LGPL-2.1, MPL-2.0-no-copyleft-exception, MIT, BSD-3-Clause, Apache-2.0
  1. <?php
  2. App::uses('CakeTime', 'Utility');
  3. class TimeBehavior extends ModelBehavior {
  4. /**
  5. * Settings to configure the behavior
  6. *
  7. * @var array
  8. */
  9. public $settings = array();
  10. /**
  11. * Default settings
  12. * label - The field used to generate the slug from
  13. * separator - the character used to separate the words in the slug
  14. * length - the maximum length of the slug
  15. *
  16. * Note that trigger will temporary bypass update and act like update is set to true.
  17. *
  18. * @var array
  19. */
  20. protected $_defaults = array(
  21. 'timeFields' => array(),
  22. 'defaultTimezone' => 'America/New_York',
  23. 'timezoneModel' => null //must be associated to the main model - leave empty if this model
  24. // 'separator' => '-',
  25. // 'update' => true,
  26. // 'length' => 50,
  27. // 'removeCommonWords' => true
  28. );
  29. /**
  30. * Initiate behaviour
  31. *
  32. * @param object $Model
  33. * @param array $settings
  34. */
  35. public function setup(Model $Model, $settings = array()) {
  36. $this->settings[$Model->alias] = array_merge($this->_defaults, $settings);
  37. }
  38. /**
  39. * Before it validates an item, it
  40. * changes any dates/times to the GMT timezone and
  41. * converts any dates into a correct YYYY-MM-DD HH:MM:SS format
  42. * @param array $options [description]
  43. * @return [type] [description]
  44. */
  45. public function beforeValidate(Model $Model, $options = array()) {
  46. //combine start_date and start_time
  47. if(!empty($Model->data[$Model->alias]['start_date']) && !empty($Model->data[$Model->alias]['start_time'])) {
  48. $Model->data[$Model->alias]['start'] = strftime("%Y-%m-%d", strtotime($Model->data[$Model->alias]['start_date'])) . ' ' . strftime("%H:%M:%S", strtotime($Model->data[$Model->alias]['start_time']));
  49. unset($Model->data[$Model->alias]['start_date']);
  50. unset($Model->data[$Model->alias]['start_time']);
  51. }
  52. //combine end_date and end_time
  53. if(!empty($Model->data[$Model->alias]['end_date']) && !empty($Model->data[$Model->alias]['end_time'])) {
  54. $Model->data[$Model->alias]['end'] = strftime("%Y-%m-%d", strtotime($Model->data[$Model->alias]['end_date'])) . ' ' . strftime("%H:%M:%S", strtotime($Model->data[$Model->alias]['end_time']));
  55. unset($Model->data[$Model->alias]['end_date']);
  56. unset($Model->data[$Model->alias]['end_time']);
  57. }
  58. //set default timezone for a new item
  59. if(empty($Model->data[$Model->alias]['id'])) {
  60. if (empty($Model->data[$Model->alias]['timezone'])) {
  61. $Model->data[$Model->alias]['timezone'] = $this->settings[$Model->alias]['defaultTimezone'];
  62. }
  63. }
  64. //convert all dates/times to GMT(server time)
  65. $this->convertTimeDataToServerTime($Model);
  66. return true;
  67. }
  68. /**
  69. * AfterFind that triggers another method that creates the timezone-altered fields with suffix "_tz"
  70. * @param Model $Model [description]
  71. * @param [type] $results [description]
  72. * @param boolean $primary [description]
  73. * @return [type] [description]
  74. */
  75. public function afterFind(Model $Model, $results, $primary = false) {
  76. //adds timezone-altered fields
  77. if(!empty($results[0][$Model->alias])) {
  78. $results[0] = $this->buildTimeFields($Model, $results[0]);
  79. } else if(!empty($results[$Model->alias])) {
  80. $results = $this->buildTimeFields($Model, $results);
  81. }
  82. return $results;
  83. }
  84. /**
  85. * Goes through the specified timeFields (model setting) and converts
  86. * them to UTC, saving them in `[field]_utc` field
  87. * @param Model $Model [description]
  88. * @return [type] [description]
  89. */
  90. public function convertTimeDataToServerTime(Model $Model) {
  91. $timezone = $this->getTimezone($Model);
  92. if(!empty($timezone)) {
  93. foreach($this->settings[$Model->alias]['timeFields'] as $field) {
  94. if(!empty($Model->data[$Model->alias][$field]) && $Model->data[$Model->alias][$field] != '0000-00-00 00:00:00') {
  95. $Model->data[$Model->alias][$field] = strftime('%Y-%m-%d %H:%M:%S', strtotime($Model->data[$Model->alias][$field]));
  96. $Model->data[$Model->alias][$field . '_utc'] = strftime('%Y-%m-%d %H:%M:%S', strtotime($this->convertToServerTime($Model->data[$Model->alias][$field], $timezone)));
  97. }
  98. }
  99. }
  100. }
  101. /**
  102. * Retrieves a timezone either from the provided timezone or
  103. * by using the provided Model id to retrieve it
  104. * @return [type] [description]
  105. */
  106. public function getTimezone(Model $Model, $data = null) {
  107. if(empty($data) && !empty($Model->data)) {
  108. $data = $Model->data;
  109. }
  110. $timezoneModel = $this->getTimezoneModel($Model);
  111. $timezone = $this->settings[$Model->alias]['defaultTimezone'];
  112. //tries to get the timezone from the provided data (if any)
  113. if(!empty($data[$timezoneModel]['timezone'])) {
  114. $timezone = $data[$timezoneModel]['timezone'];
  115. //otherwise, retrieves the timezone if we have the id
  116. } else if(!empty($data[$Model->alias]['id'])) {
  117. $timezone = $this->getModelTimezone($Model, $data[$Model->alias]['id']);
  118. }
  119. return $timezone;
  120. }
  121. /**
  122. * [getEventTimezone description]
  123. * @param [type] $id [description]
  124. * @return [type] [description]
  125. */
  126. public function getModelTimezone(Model $Model, $id) {
  127. if(empty($id)) {
  128. return false;
  129. }
  130. $timezoneModel = $this->getTimezoneModel($Model);
  131. if($Model->alias == $timezoneModel) {
  132. $Model->id = $id;
  133. $timezone = $Model->field('timezone');
  134. } else {
  135. $Model->id = $id;
  136. $timezoneModelId = $Model->field(strtolower($timezoneModel).'_id');
  137. $Model->$timezoneModel->id = $timezoneModelId;
  138. $timezone = $Model->$timezoneModel->field('timezone');
  139. }
  140. return $timezone;
  141. }
  142. /**
  143. * Gets the model where we're supposed to get the timezone from
  144. * defaults to the current model but is overridden by a specified one
  145. * @param Model $Model [description]
  146. * @return [type] [description]
  147. */
  148. public function getTimezoneModel(Model $Model) {
  149. $timezoneModel = $Model->alias;
  150. if(!empty($this->settings[$Model->alias]['timezoneModel'])) {
  151. $timezoneModel = $this->settings[$Model->alias]['timezoneModel'];
  152. }
  153. return $timezoneModel;
  154. }
  155. /**
  156. * Converts a provided date/time string to the server (GMT) time based on the provided timezone
  157. * @param [type] $dateString [description]
  158. * @param [type] $eventTimezone [description]
  159. * @return [type] [description]
  160. */
  161. public function convertToServerTime($dateString, $timezone) {
  162. return CakeTime::toServer($dateString, $timezone);
  163. }
  164. /**
  165. * Converts a provided GMT date/time string to the event's time based on the provided timezone
  166. * @param [type] $dateString [description]
  167. * @param [type] $eventTimezone [description]
  168. * @return [type] [description]
  169. */
  170. public function convertToTimezone($dateString, $timezone) {
  171. return CakeTime::format(strtotime($dateString), '%Y-%m-%d %H:%M:%S', false, $timezone);
  172. }
  173. /**
  174. * Returns the current time (now) in the timezone provided
  175. * @param [string] $eventTimezone eg: America/Denver
  176. * @return [string] [description]
  177. */
  178. public function getCurrentTimeInTimezone($timezone) {
  179. return CakeTime::convert(time(), $timezone);
  180. }
  181. /**
  182. * creates the timezone-altered fields with suffix "_tz"
  183. * @param Model $Model [description]
  184. * @param [type] $data [description]
  185. * @return [type] [description]
  186. */
  187. public function buildTimeFields(Model $Model, $data) {
  188. $timezone = $this->getTimezone($Model, $data);
  189. foreach($this->settings[$Model->alias]['timeFields'] as $field) {
  190. if(array_key_exists($field, $data[$Model->alias])) {
  191. $data[$Model->alias][$field . '_tz'] = '';
  192. if(!empty($data[$Model->alias][$field]) && !empty($timezone) && $data[$Model->alias][$field] != '0000-00-00 00:00:00') {
  193. $data[$Model->alias][$field . '_tz'] = strftime('%Y-%m-%d %H:%M:%S', strtotime($this->convertToTimezone($data[$Model->alias][$field], $timezone)));
  194. }
  195. }
  196. }
  197. return $data;
  198. }
  199. }