Source for file File.class.php

Documentation is available at File.class.php

  1. <?php
  2. /**
  3. * XOAD Events File Provider file.
  4. *
  5. * <p>This file defines the {@link XOAD_Events_Storage_File} Class.</p>
  6. * <p>Example:</p>
  7. * <code>
  8. * <?php
  9. *
  10. * require_once('xoad.php');
  11. *
  12. * require_once(XOAD_BASE . '/classes/events/storage/File.class.php');
  13. *
  14. * $storage = new XOAD_Events_Storage_File(['container=filename']);
  15. *
  16. * $storage->postEvent('event', 'class');
  17. *
  18. * ?>
  19. * </code>
  20. *
  21. * @author Stanimir Angeloff
  22. *
  23. * @package XOAD
  24. *
  25. * @subpackage XOAD_Events
  26. *
  27. * @version 0.6.0.0
  28. *
  29. */
  30.  
  31. /**
  32. * XOAD Events Storage File Class.
  33. *
  34. * <p>This class is a {@link XOAD_Events_Storage} successor.</p>
  35. * <p>The class allows you to save events information in a
  36. * flat file.</p>
  37. * <p>Example:</p>
  38. * <code>
  39. * <?php
  40. *
  41. * require_once('xoad.php');
  42. *
  43. * require_once(XOAD_BASE . '/classes/events/storage/File.class.php');
  44. *
  45. * $storage = new XOAD_Events_Storage_File(['container=filename']);
  46. *
  47. * $storage->postEvent('event', 'class');
  48. *
  49. * ?>
  50. * </code>
  51. *
  52. * @author Stanimir Angeloff
  53. *
  54. * @package XOAD
  55. *
  56. * @subpackage XOAD_Events
  57. *
  58. * @version 0.6.0.0
  59. *
  60. */
  61. class XOAD_Events_Storage_File extends XOAD_Events_Storage
  62. {
  63. /**
  64. * Holds the file name where events information is saved.
  65. *
  66. * @access protected
  67. *
  68. * @var string
  69. *
  70. */
  71. var $container = 'EVENTS';
  72.  
  73. /**
  74. * Holds the separator used in the container.
  75. *
  76. * @access protected
  77. *
  78. * @var string
  79. *
  80. */
  81. var $separator = "\t***\t";
  82.  
  83. /**
  84. * Creates a new instance of the {@link XOAD_Events_Storage_File} class.
  85. *
  86. * @access public
  87. *
  88. * @param string $dsn The data source name and parameters to use
  89. * when creating the instance.
  90. *
  91. */
  92. function XOAD_Events_Storage_File($dsn)
  93. {
  94. parent::XOAD_Events_Storage($dsn);
  95. }
  96.  
  97. /**
  98. * Retrieves a static instance of the {@link XOAD_Events_Storage_File} class.
  99. *
  100. * <p>This method overrides {@link XOAD_Events_Storage::getStorage}.</p>
  101. *
  102. * @access public
  103. *
  104. * @param string $dsn The data source name and parameters to use
  105. * when retrieving the instance.
  106. *
  107. * @return object A static instance to the
  108. * {@link XOAD_Events_Storage_File} class.
  109. *
  110. * @static
  111. *
  112. */
  113. function &getStorage($dsn)
  114. {
  115. static $instance;
  116.  
  117. if ( ! isset($instance)) {
  118.  
  119. $instance = new XOAD_Events_Storage_File($dsn);
  120. }
  121.  
  122. return $instance;
  123. }
  124.  
  125. /**
  126. * Gets the absolute path to the container.
  127. *
  128. * @access private
  129. *
  130. * @return string
  131. *
  132. */
  133. function getFileName()
  134. {
  135. if (strpos($this->container, DIRECTORY_SEPARATOR) === 0) {
  136.  
  137. return $this->container;
  138. }
  139.  
  140. if (strlen($this->container) >= 3) {
  141.  
  142. if (
  143. ($this->container{1} == ':') &&
  144. ($this->container{2} == DIRECTORY_SEPARATOR)) {
  145.  
  146. return $this->container;
  147. }
  148. }
  149.  
  150. return XOAD_BASE . '/var/' . $this->container;
  151. }
  152.  
  153. /**
  154. * Posts multiple events to the container.
  155. *
  156. * <p>Valid keys for each event are:</p>
  157. * - event - the event name (case-sensitive);
  158. * - className - the class that is the source of the event;
  159. * - sender - the sender object of the event;
  160. * - data - the data associated with the event;
  161. * - filter - the event filter data (case-insensitive);
  162. * using this key you can post events with
  163. * the same name but with different filter data;
  164. * the client will respond to them individually;
  165. * - time - the event start time (seconds since the Unix
  166. * Epoch (January 1 1970 00:00:00 GMT);
  167. * - lifetime - the event lifetime (in seconds);
  168. *
  169. * @access public
  170. *
  171. * @param array $eventsData Array containing associative arrays
  172. * with information for each event.
  173. *
  174. * @return bool true on success, false otherwise.
  175. *
  176. */
  177. function postMultipleEvents($eventsData)
  178. {
  179. $handle = @fopen($this->getFileName(), 'a');
  180.  
  181. if ( ! $handle) {
  182.  
  183. return false;
  184. }
  185.  
  186. @ignore_user_abort(true);
  187.  
  188. flock($handle, LOCK_EX);
  189.  
  190. foreach ($eventsData as $event) {
  191.  
  192. if ( ! parent::postMultipleEvents($event)) {
  193.  
  194. continue;
  195. }
  196.  
  197. $row = $event['event'];
  198. $row .= $this->separator;
  199.  
  200. $row .= $event['className'];
  201. $row .= $this->separator;
  202.  
  203. $row .= $event['time'];
  204. $row .= $this->separator;
  205.  
  206. $row .= $event['time'] + $event['lifetime'];
  207. $row .= $this->separator;
  208.  
  209. $row .= isset($event['filter']) ? serialize($event['filter']) : 'N;';
  210. $row .= $this->separator;
  211.  
  212. $rowData = array();
  213.  
  214. if (isset($event['sender'])) {
  215.  
  216. $rowData['sender'] = $event['sender'];
  217. }
  218.  
  219. if (isset($event['data'])) {
  220.  
  221. $rowData['data'] = $event['data'];
  222. }
  223.  
  224. $row .= serialize($rowData);
  225.  
  226. $row .= "\n";
  227.  
  228. fwrite($handle, $row);
  229. }
  230.  
  231. flock($handle, LOCK_UN);
  232.  
  233. fclose($handle);
  234.  
  235. @ignore_user_abort(false);
  236.  
  237. return true;
  238. }
  239.  
  240. /**
  241. * Deletes old events from the container.
  242. *
  243. * <p>This method is called before calling {@link filterEvents}
  244. * or {@link filterMultipleEvents} to delete all expired events
  245. * from the container.</p>
  246. *
  247. * @access public
  248. *
  249. * @return bool true on success, false otherwise.
  250. *
  251. */
  252. function cleanEvents()
  253. {
  254. $fileName = $this->getFileName();
  255.  
  256. $containerData = @file($fileName);
  257.  
  258. if (empty($containerData)) {
  259.  
  260. return true;
  261. }
  262.  
  263. $handle = @fopen($fileName, 'a+');
  264.  
  265. if ( ! $handle) {
  266.  
  267. return false;
  268. }
  269.  
  270. $time = parent::cleanEvents();
  271.  
  272. @ignore_user_abort(true);
  273.  
  274. flock($handle, LOCK_EX);
  275.  
  276. ftruncate($handle, 0);
  277.  
  278. foreach ($containerData as $row) {
  279.  
  280. list($dummy, $dummy, $dummy, $endTime, $dummy) = explode($this->separator, $row, 5);
  281.  
  282. $endTime = (double) $endTime;
  283.  
  284. if ($endTime >= $time) {
  285.  
  286. fwrite($handle, $row);
  287. }
  288. }
  289.  
  290. flock($handle, LOCK_UN);
  291.  
  292. fclose($handle);
  293.  
  294. @ignore_user_abort(false);
  295.  
  296. return true;
  297. }
  298.  
  299. /**
  300. * Filters the events in the container using multiple criterias.
  301. *
  302. * <p>Valid keys for each event are:</p>
  303. * - event - the event name (case-sensitive);
  304. * - className - the class that is the source of the event;
  305. * - filter - the event filter data (case-insensitive);
  306. * using this argument you can filter events with
  307. * the same name but with different filter data;
  308. * - time - the event start time (seconds since the Unix
  309. * Epoch (January 1 1970 00:00:00 GMT).
  310. *
  311. * @access public
  312. *
  313. * @param array $eventsData Array containing associative arrays
  314. * with information for each event.
  315. *
  316. * @return array Sequental array that contains all events that match the
  317. * supplied criterias, ordered by time (ascending).
  318. *
  319. */
  320. function filterMultipleEvents($eventsData)
  321. {
  322. $events = array();
  323.  
  324. $containerData = @file($this->getFileName());
  325.  
  326. if (empty($containerData)) {
  327.  
  328. return $events;
  329. }
  330.  
  331. foreach ($eventsData as $event) {
  332.  
  333. if ( ! parent::filterMultipleEvents($event)) {
  334.  
  335. continue;
  336. }
  337.  
  338. foreach ($containerData as $row) {
  339.  
  340. list($eventName, $className, $time, $endTime, $filter, $rowData) = explode($this->separator, $row, 6);
  341.  
  342. $filter = unserialize($filter);
  343.  
  344. $match = (strcmp($eventName, $event['event']) == 0);
  345. $match &= (strcasecmp($className, $event['className']) == 0);
  346. $match &= ($time > $event['time']);
  347.  
  348. if (isset($event['filter'])) {
  349.  
  350. $match &= ($filter == $event['filter']);
  351. }
  352.  
  353. if ($match) {
  354.  
  355. $rowData = unserialize($rowData);
  356.  
  357. $events[] = array(
  358. 'event' => $eventName,
  359. 'className' => $className,
  360. 'filter' => $filter,
  361. 'time' => (double) $time,
  362. 'endTime' => (double) $endTime,
  363. 'eventData' => array(
  364. 'sender' => (isset($rowData['sender']) ? $rowData['sender'] : null),
  365. 'data' => (isset($rowData['data']) ? $rowData['data'] : null)
  366. ));
  367. }
  368. }
  369. }
  370.  
  371. if ( ! empty($events)) {
  372.  
  373. usort($events, array('XOAD_Events_Storage_File', 'sortEvents'));
  374. }
  375.  
  376. return $events;
  377. }
  378.  
  379. /**
  380. * Callback to sort events by time.
  381. *
  382. * @access public
  383. *
  384. * @param array $a Data associated with the first event.
  385. *
  386. * @param array $b Data associated with the second event.
  387. *
  388. * @return int Less than, equal to, or greater than zero if the first
  389. * event's time is considered to be respectively less than,
  390. * equal to, or greater than the second event's time.
  391. *
  392. */
  393. function sortEvents($a, $b)
  394. {
  395. if ($a['time'] == $b['time']) {
  396.  
  397. return 0;
  398. }
  399.  
  400. return (($a['time'] < $b['time']) ? -1 : 1);
  401. }
  402.  
  403. }
  404. ?>

Documentation generated on Sat, 12 Nov 2005 20:24:08 +0200 by phpDocumentor 1.3.0RC3