queue_ui.module 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290
  1. <?php
  2. /**
  3. * @file queue_ui.module
  4. */
  5. define('QUEUE_UI_BASE', 'admin/config/system/queue-ui');
  6. /**
  7. * Implements hook_permission().
  8. */
  9. function queue_ui_permission() {
  10. return array(
  11. 'admin queue_ui' => array(
  12. 'title' => t('Administer queues'),
  13. 'description' => t('View, run, and delete queues'),
  14. ),
  15. );
  16. }
  17. /**
  18. * Implements hook_menu().
  19. */
  20. function queue_ui_menu() {
  21. $items[QUEUE_UI_BASE] = array(
  22. 'title' => 'Queue manager',
  23. 'description' => 'View and manage queues',
  24. 'page callback' => 'drupal_get_form',
  25. 'page arguments' => array('queue_ui_page'),
  26. 'access arguments' => array('admin queue_ui'),
  27. 'file' => 'queue_ui.pages.inc',
  28. );
  29. $items[QUEUE_UI_BASE . '/inspect/%'] = array(
  30. 'title' => 'View Queue: @name',
  31. 'title arguments' => array('@name' => 5),
  32. 'page callback' => 'queue_ui_view_queue',
  33. 'page arguments' => array(5),
  34. 'access arguments' => array('admin queue_ui'),
  35. 'type' => MENU_NORMAL_ITEM,
  36. 'file' => 'queue_ui.forms.inc',
  37. );
  38. // View item callback for Queue UI.
  39. $items[QUEUE_UI_BASE . '/%/view/%queue_ui_queue_item'] = array(
  40. 'title' => 'View Queue Item',
  41. 'description' => 'View the details of an individual queue item',
  42. 'page callback' => 'queue_ui_view_queue_item',
  43. 'page arguments' => array(4, 6),
  44. 'access arguments' => array('admin queue_ui'),
  45. 'type' => MENU_NORMAL_ITEM,
  46. 'file' => 'queue_ui.forms.inc',
  47. );
  48. // Release item callback for Queue UI.
  49. $items[QUEUE_UI_BASE . '/%/release/%queue_ui_queue_item'] = array(
  50. 'title' => 'Release items',
  51. 'page callback' => 'drupal_get_form',
  52. 'page arguments' => array('queue_ui_release_item_form', 4, 6),
  53. 'access arguments' => array('admin queue_ui'),
  54. 'file' => 'queue_ui.forms.inc',
  55. );
  56. // Delete item callback for Queue UI.
  57. $items[QUEUE_UI_BASE . '/%/delete/%queue_ui_queue_item'] = array(
  58. 'title' => 'Release items',
  59. 'page callback' => 'drupal_get_form',
  60. 'page arguments' => array('queue_ui_delete_item_form', 4, 6),
  61. 'access arguments' => array('admin queue_ui'),
  62. 'file' => 'queue_ui.forms.inc',
  63. );
  64. return $items;
  65. }
  66. /**
  67. * Wildcard loader for queue_ui_queue.
  68. */
  69. function queue_ui_queue_load($name) {
  70. return DrupalQueue::get($name);
  71. }
  72. /**
  73. * Wildcard loader for queue item.
  74. *
  75. * @param $queue_item
  76. * The item id of the queue item to load.
  77. */
  78. function queue_ui_queue_item_load($queue_item) {
  79. // @TODO - add validation of queue_item.
  80. return $queue_item;
  81. }
  82. // @todo remove before prod
  83. function queue_ui_test() {
  84. $queue = DrupalQueue::get('queue ui test_me');
  85. $queue->createQueue();
  86. $num = mt_rand(0,99);
  87. for ($i = 0; $i < $num; $i++) {
  88. $queue->createItem(time());
  89. }
  90. }
  91. /**
  92. * Retrieve the QueueUI object for the class a particular queue is implemented as.
  93. *
  94. * @param $queue_name
  95. * The name of the queue to retrieve the QueueUI class for.
  96. * @return mixte
  97. * The QueueUI object for the relevant queue class, or FALSE if not found.
  98. */
  99. function _queue_ui_queueclass($queue_name){
  100. $queue = DrupalQueue::get($queue_name);
  101. $class = get_class($queue);
  102. return QueueUI::get('QueueUI' . $class);
  103. }
  104. /**
  105. * Implements hook_queue_class_info.
  106. *
  107. * @return array of class information definitions.
  108. */
  109. function queue_ui_queue_class_info() {
  110. // Implement queue class info definitions for core Drupal queue classes.
  111. return array(
  112. 'SystemQueue' => array(
  113. 'title' => t('System Queue (database Queue)'),
  114. 'inspect' => TRUE,
  115. 'operations' => array(
  116. 'view',
  117. 'release',
  118. 'delete',
  119. 'deleteall'),
  120. ),
  121. 'MemoryQueue' => array(
  122. 'title' => t('Memory queue (non-reliable)'),
  123. 'inspect' => FALSE,
  124. ),
  125. );
  126. }
  127. /**
  128. * Gets queues class info defined with hook_queue_class_info().
  129. *
  130. * @param string $class
  131. * The class name to retrieve
  132. *
  133. * @return Array of queue classes information.
  134. */
  135. function queue_ui_get_queue_class_info($class) {
  136. $classes = &drupal_static(__FUNCTION__);
  137. if (!isset($classes)) {
  138. // Invoke hook_queue_class_info().
  139. $classes = module_invoke_all('queue_class_info');
  140. }
  141. return $classes[$class];
  142. }
  143. /**
  144. * Get the names of queues.
  145. *
  146. * @param Array of queue names suitable for DrupalQueue::get();
  147. */
  148. function queue_ui_queue_names() {
  149. $result = db_query("SELECT DISTINCT name FROM {queue}");
  150. return $result->fetchAll();
  151. }
  152. /**
  153. * Get queues.
  154. *
  155. * @return Array of queues indexed by name and containing queue object and number
  156. * of items.
  157. */
  158. function queue_ui_queues() {
  159. $queues = array();
  160. $queue_names = queue_ui_queue_names();
  161. if (!empty($queue_names)) {
  162. // Build array of queues indexed by name with number of items.
  163. foreach ($queue_names as $name) {
  164. $queue = DrupalQueue::get($name->name);
  165. $class = get_class($queue);
  166. $queues[$class][$name->name] = array(
  167. 'queue' => $queue,
  168. 'items' => $queue->numberOfItems(),
  169. );
  170. }
  171. }
  172. return $queues;
  173. }
  174. /**
  175. * Get queues defined with hook_queue_info().
  176. *
  177. * @return Array of queues indexed by name and containing
  178. */
  179. function queue_ui_defined_queues() {
  180. $queues = &drupal_static(__FUNCTION__);
  181. if (!isset($queues)) {
  182. // Invoke hook_queue_info().
  183. $queues = module_invoke_all('queue_info');
  184. }
  185. return $queues;
  186. }
  187. /**
  188. * Implements hook_cron().
  189. */
  190. function queue_ui_cron() {
  191. // Retrieve queues set for cron processing.
  192. $defs = queue_ui_defined_queues();
  193. if (!empty($defs)) {
  194. foreach ($defs as $name => $definition) {
  195. $queue = DrupalQueue::get($name);
  196. // A cron callback must be defined and there must be items in the queue.
  197. if (isset($definition['cron']) && is_object($queue) && $queue->numberOfItems()) {
  198. $active = variable_get('queue_ui_cron_' . $name, FALSE);
  199. if ($active) {
  200. // Pass $queue to cron callback for processing.
  201. $function = $definition['cron']['callback'];
  202. // Definitions can define arguments.
  203. $args = isset($definition['cron']['callback']) ? $definition['cron']['callback'] : NULL;
  204. $function($queue, $args);
  205. }
  206. }
  207. }
  208. }
  209. }
  210. // @todo remove before prod
  211. function queue_ui_queue_info() {
  212. return array(
  213. 'queue ui test_me' => array(
  214. 'title' => t('Test queue'),
  215. 'batch' => array(
  216. 'operations' => array(array('queue_ui_batch_test', array())),
  217. 'finished' => 'queue_ui_batch_finished',
  218. 'title' => t('Processing test queue'),
  219. ),
  220. 'cron' => array(
  221. 'callback' =>'queue_ui_test_process',
  222. ),
  223. ),
  224. );
  225. }
  226. function queue_ui_test_process($queue) {
  227. $count = $queue->numberOfItems();
  228. for ($i = 0; $i < 20 && $count > 0; $i++) {
  229. $item = $queue->claimItem(20); // Lease time.
  230. if ($item) {
  231. // We would do some processing, if this were REAL.
  232. $queue->deleteItem($item);
  233. $count--;
  234. }
  235. }
  236. }
  237. function queue_ui_batch_test($queue, &$context) {
  238. if (empty($context['sandbox'])) {
  239. $context['sandbox']['progress'] = 0;
  240. $context['sandbox']['current'] = 0;
  241. $context['sandbox']['max'] = $queue->numberOfItems();
  242. }
  243. for ($i = 0; $i < 20 && $context['sandbox']['current'] < $context['sandbox']['max']; $i++) {
  244. $item = $queue->claimItem(20); // Lease time.
  245. if ($item) {
  246. // We would do some processing, if this were REAL.
  247. $queue->deleteItem($item);
  248. }
  249. $context['sandbox']['progress']++;
  250. $context['sandbox']['current']++;
  251. }
  252. if ($context['sandbox']['progress'] != $context['sandbox']['max']) {
  253. $context['finished'] = $context['sandbox']['progress'] / $context['sandbox']['max'];
  254. }
  255. }
  256. function queue_ui_batch_finished($success, $results, $operations) {
  257. if ($success) {
  258. $message = 'success';
  259. }
  260. else {
  261. $message = t('An error occured @todo.');
  262. }
  263. drupal_set_message($message);
  264. }