batch_6.inc

  1. 8.0.x commands/core/drupal/batch_6.inc
  2. 6.x commands/core/drupal/batch_6.inc
  3. 7.x commands/core/drupal/batch_6.inc
  4. 3.x commands/core/drupal/batch_6.inc
  5. 4.x commands/core/drupal/batch_6.inc
  6. 5.x commands/core/drupal/batch_6.inc

Drupal 6 engine for the Batch API

Functions

Namesort descending Description
_drush_backend_batch_process Main loop for the Drush batch API.
_drush_batch_command Initialize the batch command and call the worker function.
_drush_batch_finished End the batch processing: Call the 'finished' callbacks to allow custom handling of results, and resolve page redirection.
_drush_batch_shutdown Shutdown function: store the batch data for next request, or clear the table if the batch is finished.
_drush_batch_worker Process batch operations

File

commands/core/drupal/batch_6.inc
View source
  1. <?php
  2. /**
  3. * @file
  4. * Drupal 6 engine for the Batch API
  5. */
  6. use Drush\Log\LogLevel;
  7. /**
  8. * Main loop for the Drush batch API.
  9. *
  10. * Saves a record of the batch into the database, and progressively call $command to
  11. * process the operations.
  12. *
  13. * @param command
  14. * The command to call to process the batch.
  15. *
  16. */
  17. function _drush_backend_batch_process($command = 'batch-process', $args, $options) {
  18. $batch =& batch_get();
  19. if (isset($batch)) {
  20. $process_info = array(
  21. 'current_set' => 0,
  22. );
  23. $batch += $process_info;
  24. // Initiate db storage in order to get a batch id. We have to provide
  25. // at least an empty string for the (not null) 'token' column.
  26. db_query("INSERT INTO {batch} (token, timestamp) VALUES ('', %d)", time());
  27. $batch['id'] = db_last_insert_id('batch', 'bid');
  28. $args[] = $batch['id'];
  29. // Actually store the batch data and the token generated form the batch id.
  30. db_query("UPDATE {batch} SET token = '%s', batch = '%s' WHERE bid = %d", drupal_get_token($batch['id']), serialize($batch), $batch['id']);
  31. $finished = FALSE;
  32. while (!$finished) {
  33. $data = drush_invoke_process('@self', $command, $args, $options);
  34. $finished = drush_get_error() || !$data || (isset($data['context']['drush_batch_process_finished']) && $data['context']['drush_batch_process_finished'] == TRUE);
  35. }
  36. }
  37. }
  38. /**
  39. * Initialize the batch command and call the worker function.
  40. *
  41. * Loads the batch record from the database and sets up the requirements
  42. * for the worker, such as registering the shutdown function.
  43. *
  44. * @param id
  45. * The batch id of the batch being processed.
  46. */
  47. function _drush_batch_command($id) {
  48. $batch =& batch_get();
  49. // Retrieve the current state of batch from db.
  50. if ($data = db_result(db_query("SELECT batch FROM {batch} WHERE bid = %d", $id))) {
  51. $batch = unserialize($data);
  52. }
  53. else {
  54. return FALSE;
  55. }
  56. if (!isset($batch['running'])) {
  57. $batch['running'] = TRUE;
  58. }
  59. // Register database update for end of processing.
  60. register_shutdown_function('_drush_batch_shutdown');
  61. if (_drush_batch_worker()) {
  62. _drush_batch_finished();
  63. }
  64. }
  65. /**
  66. * Process batch operations
  67. *
  68. * Using the current $batch process each of the operations until the batch
  69. * has been completed or half of the available memory for the process has been
  70. * reached.
  71. */
  72. function _drush_batch_worker() {
  73. $batch =& batch_get();
  74. $current_set =& _batch_current_set();
  75. $set_changed = TRUE;
  76. timer_start('batch_processing');
  77. while (!$current_set['success']) {
  78. // If this is the first time we iterate this batch set in the current
  79. // request, we check if it requires an additional file for functions
  80. // definitions.
  81. if ($set_changed && isset($current_set['file']) && is_file($current_set['file'])) {
  82. include_once($current_set['file']);
  83. }
  84. $finished = 1;
  85. $task_message = '';
  86. if ((list($function, $args) = reset($current_set['operations'])) && function_exists($function)) {
  87. // Build the 'context' array, execute the function call,
  88. // and retrieve the user message.
  89. $batch_context = array('sandbox' => &$current_set['sandbox'], 'results' => &$current_set['results'], 'finished' => &$finished, 'message' => &$task_message);
  90. // Magic wrap to catch changes to 'message' key.
  91. $batch_context = new DrushBatchContext($batch_context);
  92. // Process the current operation.
  93. call_user_func_array($function, array_merge($args, array(&$batch_context)));
  94. $finished = $batch_context['finished'];
  95. }
  96. if ($finished >= 1) {
  97. // Make sure this step isn't counted double when computing $current.
  98. $finished = 0;
  99. // Remove the operation and clear the sandbox.
  100. array_shift($current_set['operations']);
  101. $current_set['sandbox'] = array();
  102. }
  103. // If the batch set is completed, browse through the remaining sets,
  104. // executing 'control sets' (stored form submit handlers) along the way -
  105. // this might in turn insert new batch sets.
  106. // Stop when we find a set that actually has operations.
  107. $set_changed = FALSE;
  108. $old_set = $current_set;
  109. while (empty($current_set['operations']) && ($current_set['success'] = TRUE) && _batch_next_set()) {
  110. $current_set =& _batch_current_set();
  111. $set_changed = TRUE;
  112. }
  113. // At this point, either $current_set is a 'real' batch set (has operations),
  114. // or all sets have been completed.
  115. // TODO - replace with memory check!
  116. // If we're in progressive mode, stop after 1 second.
  117. if ((memory_get_usage() * 2) >= drush_memory_limit()) {
  118. drush_log(dt("Batch process has consumed in excess of 50% of available memory. Starting new thread"), LogLevel::BATCH);
  119. break;
  120. }
  121. }
  122. // Gather progress information.
  123. // Reporting 100% progress will cause the whole batch to be considered
  124. // processed. If processing was paused right after moving to a new set,
  125. // we have to use the info from the new (unprocessed) one.
  126. if ($set_changed && isset($current_set['operations'])) {
  127. // Processing will continue with a fresh batch set.
  128. $remaining = count($current_set['operations']);
  129. $total = $current_set['total'];
  130. $task_message = '';
  131. }
  132. else {
  133. $remaining = count($old_set['operations']);
  134. $total = $old_set['total'];
  135. }
  136. $current = $total - $remaining + $finished;
  137. $percentage = $total ? floor($current / $total * 100) : 100;
  138. return ($percentage == 100);
  139. }
  140. /**
  141. * End the batch processing:
  142. * Call the 'finished' callbacks to allow custom handling of results,
  143. * and resolve page redirection.
  144. */
  145. function _drush_batch_finished() {
  146. $batch =& batch_get();
  147. // Execute the 'finished' callbacks for each batch set.
  148. foreach ($batch['sets'] as $key => $batch_set) {
  149. if (isset($batch_set['finished'])) {
  150. // Check if the set requires an additional file for functions definitions.
  151. if (isset($batch_set['file']) && is_file($batch_set['file'])) {
  152. include_once($batch_set['file']);
  153. }
  154. if (function_exists($batch_set['finished'])) {
  155. $batch_set['finished']($batch_set['success'], $batch_set['results'], $batch_set['operations']);
  156. }
  157. }
  158. }
  159. // Cleanup the batch table and unset the global $batch variable.
  160. db_query("DELETE FROM {batch} WHERE bid = %d", $batch['id']);
  161. $_batch = $batch;
  162. $batch = NULL;
  163. drush_set_option('drush_batch_process_finished', TRUE);
  164. }
  165. /**
  166. * Shutdown function: store the batch data for next request,
  167. * or clear the table if the batch is finished.
  168. */
  169. function _drush_batch_shutdown() {
  170. if ($batch = batch_get()) {
  171. db_query("UPDATE {batch} SET batch = '%s' WHERE bid = %d", serialize($batch), $batch['id']);
  172. }
  173. }