workflow.api.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290
  1. <?php
  2. /**
  3. * @file
  4. * Hooks provided by the workflow module.
  5. */
  6. /**
  7. * Implements hook_workflow().
  8. *
  9. * NOTE: This hook may reside in the implementing module
  10. * or in a module.workflow.inc file.
  11. *
  12. * @param string $op
  13. * The current workflow operation.
  14. * E.g., 'transition permitted', 'transition pre' or 'transition post'.
  15. * @param mixed $id
  16. * The ID of the current state/transition/workflow.
  17. * @param mixed $new_sid
  18. * The state ID of the new state.
  19. * @param object $entity
  20. * The entity whose workflow state is changing.
  21. * @param bool $force
  22. * The caller indicated that the transition should be forced. (bool).
  23. * This is only available on the "pre" and "post" calls.
  24. * @param string $entity_type
  25. * The entity_type of the entity whose workflow state is changing.
  26. * @param string $field_name
  27. * The name of the Workflow Field. Empty in case of Workflow Node.
  28. * This is used when saving a state change of a Workflow Field.
  29. * @param object $transition
  30. * The transition, that contains all of the above.
  31. * @todo D8: remove all other parameters.
  32. *
  33. * @return mixed
  34. * Only 'transition permitted' expects a boolean result.
  35. */
  36. function hook_workflow($op, $id, $new_sid, $entity, $force, $entity_type = '', $field_name = '', $transition = NULL, $user = NULL) {
  37. switch ($op) {
  38. case 'transition permitted':
  39. // This is called in the following situations:
  40. // 1. when building a workflow widget with list of available transitions;
  41. // 2. when executing a transition, just before the 'transition pre';
  42. // 3. when showing a 'revert state' link in a Views display.
  43. // Your module's implementation may return FALSE here and disallow
  44. // the execution, or avoid the presentation of the new State.
  45. // This may be user-dependent.
  46. // As of 7.x-2.3, better use hook_workflow_permitted_state_transitions_alter() in option 1.
  47. // For options 2 and 3, the 'transition pre' gives an alternative.
  48. return TRUE;
  49. case 'transition pre':
  50. // The workflow module does nothing during this operation.
  51. // Implement this hook if you need to change/do something BEFORE anything
  52. // is saved to the database.
  53. // If you return FALSE here, you will veto the transition.
  54. break;
  55. case 'transition post':
  56. // This is called by Workflow Node during update of the state, directly
  57. // after updating {workflow_node}. Workflow Field does not call this,
  58. // since you can call a hook_entity_* event after saving the entity.
  59. // @see https://api.drupal.org/api/drupal/includes%21module.inc/group/hooks/7
  60. break;
  61. case 'transition delete':
  62. // A transition is deleted. Only the first parameter is used.
  63. // $tid = $id;
  64. break;
  65. case 'state delete':
  66. // A state is deleted. Only the first parameter is used.
  67. // $sid = $id;
  68. break;
  69. case 'workflow delete':
  70. // A workflow is deleted. Only the first parameter is used.
  71. // $wid = $id;
  72. break;
  73. }
  74. }
  75. /**
  76. * Implements hook_workflow_history_alter().
  77. *
  78. * Allow other modules to add Operations to the most recent history change.
  79. * E.g., Workflow Revert implements an 'undo' operation.
  80. *
  81. * @param array $variables
  82. * The current workflow history information as an array.
  83. * 'old_sid' - The state ID of the previous state.
  84. * 'old_state_name' - The state name of the previous state.
  85. * 'sid' - The state ID of the current state.
  86. * 'state_name' - The state name of the current state.
  87. * 'history' - The row from the workflow_node_history table.
  88. * 'transition' - a WorkflowTransition object, containing all of the above.
  89. */
  90. function hook_workflow_history_alter(array &$variables) {
  91. // The Workflow module does nothing with this hook.
  92. // For an example implementation, see the Workflow Revert add-on.
  93. $options = array();
  94. $path = '<front>';
  95. // If you want to add additional data, such as an operation link,
  96. // place it in the 'extra' value.
  97. $variables['extra'] = l(t('My new operation: go to frontpage'), $path, $options);
  98. }
  99. /**
  100. * Implements hook_workflow_comment_alter().
  101. *
  102. * Allow other modules to change the user comment when saving a state change.
  103. *
  104. * @param string $comment
  105. * The comment of the current state transition.
  106. * @param array $context
  107. * 'transition' - The current transition itself.
  108. */
  109. function hook_workflow_comment_alter(&$comment, array &$context) {
  110. $transition = $context->transition;
  111. $comment = $transition->uid . 'says: ' . $comment;
  112. }
  113. /**
  114. * Implements hook_workflow_permitted_state_transitions_alter().
  115. *
  116. * @param array $transitions
  117. * An array of allowed transitions from the current state (as provided in
  118. * $context). They are already filtered by the settings in Admin UI.
  119. * @param array $context
  120. * An array of relevant objects. Currently:
  121. * $context = array(
  122. * 'entity_type' => $entity_type,
  123. * 'entity' => $entity,
  124. * 'field_name' => $field_name,
  125. * 'force' => $force,
  126. * 'workflow' => $workflow,
  127. * 'state' => $current_state,
  128. * 'user' => $user,
  129. * 'user_roles' => $roles, // @todo: can be removed in D8, since $user is in.
  130. * );
  131. *
  132. * This hook allows you to add custom filtering of allowed target states, add
  133. * new custom states, change labels, etc.
  134. * It is invoked in WorkflowState::getOptions().
  135. */
  136. function hook_workflow_permitted_state_transitions_alter(array &$transitions, array $context) {
  137. // This example creates a new custom target state.
  138. $values = array(
  139. // Fixed values for new transition.
  140. 'wid' => $context['workflow']->wid,
  141. 'sid' => $context['state']->sid,
  142. // Custom values for new transition.
  143. // The ID must be an integer, due to db-table constraints.
  144. 'target_sid' => '998',
  145. 'label' => 'go to my new fantasy state',
  146. );
  147. $new_transition = new WorkflowConfigTransition($values);
  148. $transitions[] = $new_transition;
  149. }
  150. /**********************************************************************
  151. * Hooks defined by core Form API: hooks to to alter the Workflow Form/Widget.
  152. */
  153. /**
  154. * Alter forms for field widgets provided by other modules.
  155. *
  156. * @param $element
  157. * The field widget form element as constructed by hook_field_widget_form().
  158. * @param $form_state
  159. * An associative array containing the current state of the form.
  160. * @param $context
  161. * An associative array containing the following key-value pairs, matching the
  162. * arguments received by hook_field_widget_form():
  163. * - form: The form structure to which widgets are being attached. This may be
  164. * a full form structure, or a sub-element of a larger form.
  165. * - field: The field structure.
  166. * - instance: The field instance structure.
  167. * - langcode: The language associated with $items.
  168. * - items: Array of default values for this field.
  169. * - delta: The order of this item in the array of subelements (0, 1, 2, etc).
  170. *
  171. * @see hook_field_widget_form()
  172. * @see hook_field_widget_WIDGET_TYPE_form_alter()
  173. */
  174. function hook_field_widget_form_alter(&$element, &$form_state, $context) {
  175. // A hook for changing any widget. Better not use it: it is called on EVERY
  176. // Widget. (Even though the message is only shown once.)
  177. // D7: This hook is introduced in Drupal 7.8.
  178. // workflow_debug(__FILE__, __FUNCTION__, __LINE__, '', '');
  179. // dpm($context['widget']->getPluginId());
  180. }
  181. function hook_field_widget_workflow_default_form_alter(&$element, $form_state, $context) {
  182. // A hook specific for the 'workflow_default' widget.
  183. // D7: This hook is introduced in Drupal 7.8.
  184. // D8: This name is specified in the annotation of WorkflowDefaultWidget.
  185. // workflow_debug(__FILE__, __FUNCTION__, __LINE__, '', '');
  186. // dpm($context['widget']->getPluginId());
  187. // A widget on an entity form.
  188. if ('workflow_default' == $context['widget']->getPluginId()) { // D8-code
  189. // This object contains all you need. You may find it in one of two locations.
  190. /* @var $transition WorkflowTransitionInterface */
  191. $transition = $element['#default_value'];
  192. // An example of customizing/overriding the workflow widget.
  193. // Beware, until now, you must do this twice: on the widget and on the form.
  194. if ($transition->getOwnerId() == 1) {
  195. drupal_set_message('I got you, user 1, you will never schedule again,
  196. and you WILL document each state change!', 'warning');
  197. // Let's prohibit scheduling for user 1.
  198. $element['workflow']['workflow_scheduling']['#access'] = FALSE;
  199. // Let's prohibit scheduling for user 1.
  200. if ($element['workflow']['workflow_comment']['#access'] == TRUE) {
  201. $element['workflow']['workflow_comment']['#required'] = TRUE;
  202. }
  203. }
  204. }
  205. }
  206. /**
  207. * Implements hook_form_BASE_FORM_ID_alter().
  208. *
  209. * Use this hook to alter the form.
  210. * It is only suited if you only use View Page or Workflow Tab.
  211. * If you change the state on the Node Form (Edit modus), you need the hook
  212. * hook_form_alter(). See below for more info.
  213. */
  214. function hook_form_workflow_transition_form_alter(&$form, &$form_state, $form_id) {
  215. // Get the Entity.
  216. $entity = $form['workflow']['workflow_entity']['#value'];
  217. $entity_type = $form['workflow']['workflow_entity_type']['#value'];
  218. // Use the complicated form, which is suited for all Entity types.
  219. // For nodes only: $entity_type = 'node'; $entity_bundle = $entity->type;
  220. list(, , $entity_bundle) = entity_extract_ids($entity_type, $entity);
  221. // Get the current State ID.
  222. $sid = workflow_node_current_state($entity, $entity_type, $field_name = NULL);
  223. // Get the State object, if needed.
  224. $state = workflow_state_load($sid);
  225. // Change the form, depending on the state ID.
  226. // In the upcoming version 7.x-2.4, States should have a machine_name, too.
  227. if ($entity_type == 'node' && $entity_bundle == 'MY_NODE_TYPE') {
  228. switch ($state->sid) {
  229. case '2':
  230. // Change form element, form validate and form submit for state '2'.
  231. break;
  232. case '3':
  233. // Change form element, form validate and form submit for state '3'.
  234. break;
  235. }
  236. }
  237. }
  238. /**
  239. * Implements hook_form_alter().
  240. *
  241. * Use this hook to alter the form on a Node Form, Comment Form (Edit page).
  242. */
  243. function hook_form_alter(&$form, $form_state, $form_id) {
  244. // Get the Entity.
  245. $entity = $form['#entity'];
  246. $entity_type = $form['#entity_type'];
  247. // Use the complicated form, which is suited for all Entity Types.
  248. list(, , $entity_bundle) = entity_extract_ids($entity_type, $entity);
  249. // Discover if this is the correct form.
  250. // ...
  251. // Get the current state and act upon it.
  252. // .. copy code from the hook above.
  253. }
  254. /*
  255. * Implements hook_field_attach_form().
  256. */
  257. function workflow_field_attach_form($entity_type, $entity, &$form, &$form_state, $langcode){
  258. // @see http://drupal.stackexchange.com/questions/101857/difference-between-hook-form-alter-and-hook-field-attach-form
  259. }