I was in search of an easy way to send a tracking number to a customer who purchased something from a Drupal Commerce store. After unsuccessfully searching around for a module to accomplish this task I turned to the rules module. In the flow I detail below, we are going to build a rule that fires when a commerce order status is updated to completed. Before we can send a tracking # we need to have a number associated with an order.
To do this we need to add a new field to the order. In the Order settings configuration page (admin/commerce/config/order) click on manage fields. In my case I'm adding a USPS tracking #, so I'm going to add a new field called USPS Tracking Number.
I want the field to be visible when viewing and order so I'm going to leave the display settings alone. If you want to hide the field you would edit the display fields now.
Now that the field exists, we can setup a rule that will fire after a order has been saved. This rule will then check to see if the order status has been set to completed and if there is a value in the USPS Tracking Number field. To do this we want to add a new rule called 'Send USPS tracking number'. The action is going to be: 'After saving and existing commerce order'.
For the conditions we are going to add a data comparison that checks the commerce-order:type equals Order
Now that the order is in context we can check that the tracking number field is not empty by adding a condition: "Data value is empty", using commerce-order:field-tracking-number as the data selector and checking the 'negate' box.
Now we need to check that the commerce order status has been set to completed. Add a new 'Data comparison" and set the 'data to compare' to: commerce-order:status, operator should be set to 'equals' and Data Value to compare is 'Completed'.
We want to make sure that the tracking number only gets sent when the order status gets set to 'completed' from any other status. To do this we want to check that the unchanged order status does not equal 'completed'. Add a new 'Data Comparison' condition and set the 'Data to compare' to commerce-order:status, the operator should be 'equals' and the 'data value' should be commerce-order-unchanged:status. Make sure to check the 'Negate' check box.
Now let's add an action to send an email with the tracking number.
Click on 'add action' and under system choose 'Send mail'. The TO address should be set to commerce-order:owner:mail so that the person who placed the order gets the email. The Subject can be anything you'd like. I went with 'Your order has been shipped!' Same goes for the message. I went with 'Your order has been shipped via USPS. Your tracking number is: [commerce-order:field-tracking-number].' Click save after adding a from address in the appropriate box.
We now have a rule that will send an email to the order owner when a tracking number is added and the order status is set to completed. The rule will also send an email anytime the order is changed from completed to another status and then back to completed. If you want to prevent that from happening you can add another field to the order. This field will be a simple boolean field with a widget of 'Single on/off checkbox'. Make sure to check the checkbox that says 'Use field lable instead of the "On value" as label'. Also set the On value to 1 and the Off value to 0. You'll want to set the display settings to hidden for this field.
Now that we have this new field we need to modify our rule again. Add another condition to check the value of this field. We want to add a new 'Data comparison' and set the selector to commerce-order:field-tracking-email-sent (this depends on how you name your boolean field). The operator should be 'equals' and the Data Value checkbox should be checked. We also want to make sure Negate is checked. Now our rule will fire when the value does not equal 1. The final step is to set the value of the checkbox to 1 so it does not fire the next time the order is saved from another status.
Add a new 'Set a data value' action. The data to set is commerce-order:field-tracking-email-sent and the value is checked.
That's it, we now have a way to track whether or not the email has been sent and prevent it from sending again. Unless of course you want to send it again by un-checking the sent checkbox.