Recently I've been coding new payment methods for Ubercart (Polish gateway) and I've hit a serious design flaw.
Consider this scenario:
- Customer submits an order.
- Payment method has been selected and customer went through payment process.
- Payment verification takes some time - eg. two days for standard money transfers during weekends.
- Before payment arrives admin is able to edit order which is fine if he changes only billing or delivery address. But what if he'll add or remove order items? Or change their price?
- Order total price changes! But customer has already paid!
There is no way for payment module to prevent from changing order price when order awaits payment.
But! There is more!
Even if payment module would like to cancel old and create new transaction with accurate price after order price changes - it can not! Why? Because when Ubercart invokes payment callback (defined in hook_payment_method) it passes order object with old total price (that is the price that was BEFORE admin changed it).
Current design that does not allow payment modules to react on order price change is wired and counter intuitive. Especially if you look at hook_order which allows anyone to refuse order status change or order deletion, BUT NOT saving order changes. This may lead to serious data inconsistency.
Allow blocking of order editing by payment modules through callback defined in hook_payment_method. Modules can block order submission ($op = 'order-submit') so I don't see why it couldn't be done for order editing ($op = 'edit-process').
Allow blocking of order saving by modules through hook_order function the same way it is done for $op = 'can_update' and $op = 'can_delete'.