"Set order status" action doesn't work correctly

Created on 9 September 2024, 5 months ago

Problem/Motivation

The "Set order status" action has a problem - it sets the status correctly, but then after the data is updated it's reverted to the previous value when VBO finishes cleaning up.

Steps to reproduce

Set up a view that lists orders and has a VBO bulk operations row.
Display the view.
Select an order.
Use the "Set order status" action.
Set "Order status" to a different status than the order currently has.
Complete the operation.

Should see this:
* The order has the new status.

What actually happens:
* The order still has the old status.

Proposed resolution

Fix the bug.

Remaining tasks

Work out how to fix the bug.
Provide a patch.
Add test coverage.

User interface changes

The "Set order status" operation works correctly.

API changes

n/a

Data model changes

n/a

πŸ› Bug report
Status

Needs review

Version

3.0

Component

Orders

Created by

πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Comments & Activities

  • Issue created by @DamienMcKenna
  • πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA
  • πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA

    The problem comes from VBO that runs entity_save() on the *old* order object after it runs the action.

      public function execute($data, array $context) {
        $context['entity_type'] = $this->entityType;
        $context['settings'] = $this->getAdminOption('settings', array());
        $context += $this->formOptions;
        $context += $this->operationInfo['parameters'];
        // Actions provided by the Drupal system module require the entity to be
        // present in $context, keyed by entity type.
        if (is_object($data)) {
          $context[$this->entityType] = $data;
        }
    
        actions_do($this->operationInfo['callback'], $data, $context);
    
        // The action might need to have its entities saved after execution.
        if (in_array('changes_property', $this->operationInfo['behavior'])) {
          $data = is_array($data) ? $data : array($data);
          foreach ($data as $entity) {
            entity_save($this->entityType, $entity);
          }
        }
      }
    
  • πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA

    Having dug through the code I'm not sure it's possible to fix in Ubercart as VBO just uses actions_do() to run the operation, which doesn't pass the object by reference, meaning that the changed object can't be pushed back up to the original process.

    Dangit.

  • πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA

    The issue is that VBO assumes that if the action's "behavior" value (see hook_action_info()) should be "changes_property" if it isn't defined.

  • Status changed to Needs review 5 months ago
  • πŸ‡ΊπŸ‡ΈUnited States DamienMcKenna NH, USA

    The solution seems to be to set "behavior" to a value that doesn't do anything.

Production build 0.71.5 2024