When you delete an order, associated packages are not deleted.

I think that the shipments are also not deleted, although I haven't confirmed this.

One could argue that the package records should stay, since perhaps there should be a record that something has shipped, even if the order is gone. However, the the packages get their addresses from the shipment record, and their contents from the ordered product record. Also, there's no way in the UI to get to orphaned packages or shipments. So the package records are pretty useless without the order, and should probably just be deleted.

This should probably be done by implementing hook_uc_order(). It should look up records in {uc_packages}, and call uc_shipping_package_delete(). Likewise with the {uc_shipments} table and uc_shipping_shipment_delete().

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

DanZ’s picture

A decision needs to be made here: Should the shipments and packages really be deleted if the order is deleted? My opinion is "yes", but that's not the only possibility.

If the orphaned shipment and packages get to stay, then they need to be self-sufficient without their corresponding orders. Their order_id fields need to be set to NULL on delete. They need UI support to get to them. They need to be tied to the users who placed the orders to get things like the e-mail address.

longwave’s picture

I think there is a reasonable expectation that if you delete an order, all associated data with that order should be deleted; this is what happens when you delete a node, for example. As you say, the remaining data is currently useless as it is incomplete and there is no UI (which may change when the Views shipping patch gets in, but the partially deleted data is still not much use).

SilviuChingaru’s picture

I think also package should be deleted on order delete. But we also have to make a hook_update_N function that looks for orphaned packages and shipments until update and delete them.
If the user decide to delete a order then all related data should be deleted. If user wants to keep that data, can do like I do, make a status "Deleted" and hide orders with that status and their related data from any view.

DanZ’s picture

Assigned: Unassigned » DanZ

But we also have to make a hook_update_N function that looks for orphaned packages and shipments until update and delete them.

Yep. I realized this last night. It will clean up any mess already there.

I'll take this one.

Question: Do we want to make a "clean up" button that will do this, or just count on the hook_update_N and the improved code to keep it clean?

SilviuChingaru’s picture

I think this is not a user option. The packages won't display with the current code so I don't think the user agreement is required because they cannot access any package or shipping if the order is deleted right now (at least not in usual way: the packages and shipping are tabs of order and if the order is not displayed the packages or shipping aren't displayed also).

longwave’s picture

Keep it simple. hook_update_N is enough - the docblock comment will be displayed when running update.php, which should be enough warning in the unlikely event anyone actually wants to keep this data.

longwave’s picture

Category: bug » task

Also, not sure this is really a bug; nothing bad actually happens if we don't delete this data.

DanZ’s picture

Status: Active » Needs review
FileSize
2.22 KB

Here's a first pass, with just the hook_uc_order(), but not the hook_update_N().

This also prevents backend users from deleting orders with a shipment or package that has a tracking number, unless the user has administrative privileges or the "Unconditionally delete orders" permission.

If I'm reading the hook_update_N() docs correctly, it looks like the cleanup is going to have to be some fairly raw database operations, without using the schemas or calling any functions that have hooks in them. It will just have to drop the records from the tables, without any other niceties. That means that any other modules that would want to know about shipments or packages being deleted won't be informed here, and will have to do their own cleanup, if they are interested in that sort of thing. Does that sound correct?

Also, I'm figuring on calling it uc_shipping_update_7301(), to avoid a naming conflict with #1911278: Expose shipping data to views. Does that sound right? Will that cause problems if it is committed before uc_shipping_update_7300()?

Also, not sure this is really a bug; nothing bad actually happens if we don't delete this data.

Not from Ubercart's current perspective, but any modules that work back from packages to orders blow up if the packages are there and the orders aren't (guess how I learned that?).

DanZ’s picture

Here it is with the cleanup hook uc_shipping_update_7301().

I'm not sure how efficient this sort of db_delete() is, but it works. I tried a bunch of stuff with subqueries and ->notExists(), but they didn't work at all.

I'm not sure if this requires using the batch sandbox and showing progress, etc. These could be some pretty big database operations if there are a lot of package and shipment records around.

longwave’s picture

I am not very bothered about the performance of db_delete() in hook_update_N(), it will only ever be called once during upgrades of sites that use uc_shipping.

However, in hook_uc_order('can_delete') surely it is more efficient to use a count query with a condition that checks for tracking numbers, rather than loop through all the results? We should also short circuit if the first query returns FALSE, as there is little point running the second query in this case.

DanZ’s picture

I am not very bothered about the performance of db_delete() in hook_update_N(), it will only ever be called once during upgrades of sites that use uc_shipping.

I'm worried about Web timeouts during the update if the tables are big. I don't know if I should be worried or not. It's three separate queries, so there's a pretty obvious way to divide it up. I didn't do it because I haven't figured out the batch/sandbox thing.

However, in hook_uc_order('can_delete') surely it is more efficient to use a count query with a condition that checks for tracking numbers, rather than loop through all the results?

It's not terrible as-is, because it only loops through the shipments on that one order. However, it's probably worth improving, since this gets called once for every order displayed on the orders view.

We should also short circuit if the first query returns FALSE, as there is little point running the second query in this case.

Definitely.

I'll take a shot at all this in a couple days.

longwave’s picture

Status: Needs review » Needs work
DanZ’s picture

Status: Needs work » Needs review
FileSize
3.37 KB

This patch incorporates the changes suggested in #10. It seems to work for my tests.

The uc_shipping_update_7301() here will have to be renamed uc_shipping_update_7300() if this is committed before #1911278: Expose shipping data to views.

longwave’s picture

@fiftyz: Are you able to test the patch in #13?

SilviuChingaru’s picture

Yes, but I'm not at test pc untill monday. Monday I'll test it and post back the results.

DanZ’s picture

@fiftyz, any luck yet?

On another note, this seems like something that should probably go into an auto-test, but I'm not sure if the hook_update_N() stuff can work that way. I guess I'll have to learn about auto-tests sooner or later.

longwave’s picture

Status: Needs review » Fixed

Finally had time to test and review this. I committed #13 with some minor changes to the update hook, as I don't really see any use in telling the user how many packages and shipments were deleted.

SilviuChingaru’s picture

Uhhh... I didn't have so much time those 2 and half months. Sorry DanZ. I hope I'll have more time from now on.

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.

Anonymous’s picture

Issue summary: View changes

A little clarification about orphaned packages and shipments.