/** * {@inheritdoc} */ public function buildConfigurationForm(array $form, FormStateInterface $form_state) { $form = []; // If we are on admin/config/system/actions and use CREATE AN ADVANCED ACTION // Then $context only contains: // - $context['actions_label'] = "Change workflow state of post to new state" // - $context['actions_type'] = "entity" // // If we are on a VBO action form, then $context only contains: // - $context['entity_type'] = "node" // - $context['view'] = "(Object) view" // - $context['settings'] = "array()" // @todo: test with multiple workflows per entity. $wids = workflow_get_workflow_names(); $wid = array_keys($wids)[0]; // Get the common Workflow, or create a dummy Workflow. $workflow = $wid ? Workflow::load($wid) : Workflow::create(['id' => 'dummy_action', 'label' => 'dummy_action']); $current_state = $workflow->getCreationState(); /* // @TODO D8-port // Show the current state and the Workflow form to allow state changing. // N.B. This part is replicated in hook_node_view, workflow_tab_page, workflow_vbo. if ($workflow) { $field = _workflow_info_field($field_name, $workflow); $field_name = $field['field_name']; $field_id = $field['id']; $instance = field_info_instance($entity_type, $field_name, $entity_bundle); // Hide the submit button. VBO has its own 'next' button. $instance['widget']['settings']['submit_function'] = ''; if (!$field_id) { // This is a Workflow Node workflow. Set widget options as in v7.x-1.2 $field['settings']['widget']['comment'] = isset($workflow->options['comment_log_tab']) ? $workflow->options['comment_log_tab'] : 1; // vs. ['comment_log_node']; $field['settings']['widget']['current_status'] = TRUE; // As stated above, the options list is probably very long, so let's use select list. $field['settings']['widget']['options'] = 'select'; // Do not show the default [Update workflow] button on the form. $instance['widget']['settings']['submit_function'] = ''; } } // Add the form/widget to the formatter, and include the nid and field_id in the form id, // to allow multiple forms per page (in listings, with hook_forms() ). // Ultimately, this is a wrapper for WorkflowDefaultWidget. // $form['workflow_current_state'] = workflow_state_formatter($entity_type, $entity, $field, $instance); $form_id = implode('_', array( 'workflow_transition_form', $entity_type, $entity_id, $field_id )); */ $transition = $this->getTransitionForConfiguration($current_state); // Add the WorkflowTransitionForm to the page. // Here, not the $element is added, but the entity form. $element = []; // Just to be explicit. $element['#default_value'] = $transition; $form += WorkflowTransitionElement::transitionElement($element, $form_state, $form); // Remove the transition: generates an error upon saving the action definition. unset($form['workflow_transition']); // Todo D8: add the entity form. //$form = \Drupal::getContainer()->get('entity.form_builder')->getForm($transition, 'add'); // Remove the action button. The Entity itself has one. //unset($element['actions']); // Make adaptations for VBO-form: $entity = $transition->getTargetEntity(); $field_name = $transition->getFieldName(); $force = $this->configuration['force']; // Override the options widget. $form['to_sid']['#description'] = t('Please select the state that should be assigned when this action runs.'); // Add Field_name. @todo?? Add 'field_name' to WorkflowTransitionElement? $form['field_name'] = array('#type' => 'select', '#title' => t('Field name'), '#description' => t('Choose the field name.'), '#options' => _workflow_info_field_names($entity), '#default_value' => $field_name, '#required' => TRUE, '#weight' => -20); // Add Force. @todo?? Add 'force' to WorkflowTransitionElement? $form['force'] = array('#type' => 'checkbox', '#title' => t('Force transition'), '#description' => t('If this box is checked, the new state will be assigned even if workflow permissions disallow it.'), '#default_value' => $force, '#weight' => -19); // Change comment field. $form['comment'] = array('#title' => t('Message'), '#description' => t('This message will be written into the workflow history log when the action runs. You may include the following variables: %state, %title, %user.')) + $form['comment']; return $form; }
/** * {@inheritdoc} * * Implements workflow_transition() -> WorkflowDefaultWidget::submit(). * * Overrides submit(array $form, array &$form_state). * Contains 2 extra parameters for D7 * * @param array $form * @param array $form_state * @param array $items * The value of the field. * @param bool $force * TRUE if all access must be overridden, e.g., for Rules. * * @return int * If update succeeded, the new State Id. Else, the old Id is returned. * * This is called from function _workflowfield_form_submit($form, &$form_state) * It is a replacement of function workflow_transition($entity, $to_sid, $force, $field) * It performs the following actions; * - save a scheduled action * - update history * - restore the normal $items for the field. * @todo: remove update of {node_form} table. (separate task, because it has features, too) */ public function massageFormValues(array $values, array $form, FormStateInterface $form_state) { $user = workflow_current_user(); // @todo #2287057: verify if submit() really is only used for UI. If not, $user must be passed. // Set the new value. // Beware: We presume cardinality = 1 !! // The widget form element type has transformed the value to a // WorkflowTransition object at this point. We need to convert it // back to the regular 'value' string format. foreach ($values as &$item) { if (!empty($item)) { // } && $item['value'] instanceof DrupalDateTime) { // The following can NOT be retrieved from the WorkflowTransition. /* @var $entity EntityInterface */ $entity = $form_state->getFormObject()->getEntity(); /* @var $transition \Drupal\workflow\Entity\WorkflowTransitionInterface */ $transition = $item['workflow_transition']; $field_name = $transition->getFieldName(); // N.B. Use a proprietary version of copyFormValuesToEntity, // where $entity/$transition is passed by reference. // $this->copyFormValuesToEntity($entity, $form, $form_state); /* @var $transition \Drupal\workflow\Entity\WorkflowTransitionInterface */ $transition = WorkflowTransitionElement::copyFormItemValuesToEntity($transition, $form, $item); // Try to execute the transition. Return $from_sid when error. if (!$transition) { // This should not be possible (perhaps when testing/developing). drupal_set_message(t('Error: the transition from %from_sid to %to_sid could not be generated.'), 'error'); // The current value is still the previous state. $to_sid = $from_sid; } else { // The transition may be scheduled or not. Save the result, and // rely upon hook workflow_entity_insert/update($entity) in // file workflow.module to save/execute the transition. // - validate option; add hook to let other modules change comment. // - add to history; add to watchdog // Return the new State ID. (Execution may fail and return the old Sid.) // Get the new value from an action button if set in the workflow settings. $action_info = _workflow_transition_form_get_triggering_button($form_state); if ($field_name == $action_info['field_name']) { $transition->to_sid->value = $action_info['to_sid']; } $force = FALSE; // @TODO D8-port: add to form for usage in VBO. // Now, save/execute the transition. $from_sid = $transition->getFromSid(); $force = $force || $transition->isForced(); if (!$transition->isAllowed($user, $force)) { // Transition is not allowed. $to_sid = $from_sid; } elseif (!$entity || !$entity->id()) { // Entity is inserted. The Id is not yet known. // So we can't yet save the transition right now, but must rely on // function/hook workflow_entity_insert($entity) in file workflow.module. // $to_sid = $transition->execute($force); $to_sid = $transition->getToSid(); } else { // Entity is updated. To stay in sync with insert, we rely on // function/hook workflow_entity_update($entity) in file workflow.module. // $to_sid = $transition->execute($force); $to_sid = $transition->getToSid(); } } // Now the data is captured in the Transition, and before calling the // Execution, restore the default values for Workflow Field. // For instance, workflow_rules evaluates this. // // Set the transition back, to be used in hook_entity_update(). $item['workflow_transition'] = $transition; // // Set the value at the proper location. $item['value'] = $to_sid; } } return $values; }
/** * {@inheritdoc} */ public function buildEntity(array $form, FormStateInterface $form_state) { $entity = clone $this->entity; // N.B. Use a proprietary version of copyFormValuesToEntity, // where $entity is passed by reference. // $this->copyFormValuesToEntity($entity, $form, $form_state); $item = $form_state->getValues(); $entity = WorkflowTransitionElement::copyFormItemValuesToEntity($entity, $form, $item); // Mark the entity as NOT requiring validation. (Used in validateForm().) $entity->setValidationRequired(FALSE); return $entity; }