When an order is submitted and processed I need to be able to write values back to the related node to flag it as complete so I can create meaningful views of ordered products..

I followed this guide and it worked perfectly for passing the Order ID and Payment Status back to the node. I am having problems passing the value of the selected product attributes back to the node however. I have a textfield setup called Passed Attributes in my content type, but I think my call to the attributes is wrong.

Using conditional attributes, as documented above I am using this code to update the node on checkout:

if (isset($order)) {
foreach ($order->products as $product) {
if (isset($product->data['node_checkout_nid'])) {
$node = node_load($product->data['node_checkout_nid']);
$node->field_status['0']['value'] = 1;
$node->field_orderid['0']['value'] = $order->order_id;
node_save($node);
}
}
}

I i need to pass the attributes back too so am I looking for something like:

$node->field_orderid['0']['value'] = $order->attributes ?

Thanks,
Gary

Comments

garyh’s picture

Sorry I forgot to say what guide I followed for the above, it was this: http://drupaleasy.com/blogs/ultimike/2009/03/event-registration-ubercart

anni’s picture

I need this too!

Anyone an idea?

Train’s picture

If you were still wondering how to access the attributes (as I was), I figured it out...

Using the code above, you would access the attributes as such:

if (isset($order)) {
  foreach ($order->products as $product) {
    if (isset($product->data['node_checkout_nid'])) {
		
      $level = $product->data['attributes']['Level'][0];
			
      $node = node_load($product->data['node_checkout_nid']);
      $node->field_status['0']['value'] = 1;
      $node->field_orderid['0']['value'] = $order->order_id;
      node_save($node);
    }
  }
}

In this case I have an attribute I called "Level."

'attributes' is an array of arrays within the 'product' object that holds the data for your assigned attributes. You can write yourself a Conditional Action to print_r the 'orders' object after checkout (using the link in comment #1) to see how to access the attributes.

Hopefully somebody with the same issue will find this helpful.

epop’s picture

So how do I pass the ordered attribute to a node field? For example the status field becomes 1. Id like a field in my node to contain the the ordered attribute.

Train’s picture

This bit of code does it for me:

      $node = node_load($product->data['node_checkout_nid']);
      $node->field_status['0']['value'] = 1;
      $node->field_orderid['0']['value'] = $order->order_id;
      node_save($node);

Load the node via node_load(), set the value of your field to what you want, save the node via node_save().

paulwedge’s picture

For some strange reason the instructions provided in http://drupaleasy.com/blogs/ultimike/2009/03/event-registration-ubercart are not working for me.
I have followed the exact instructions - however when I include a dsm($node) or dsm($product) in the PHP code, they return blank.
Also when I go back to my product and click the 'Devel' tab, the 'data' string contains the following characters: a:1:{s:13:"form_build_id";s:37:"form-3ccc03345f4832c69666a89c560de940";}

Does anybody have a suggestion on what might be going wrong?

Thanks!

dallasw1983’s picture

For anyone still looking on how to pass the ordered attributes to the node, I was able to do it.
I'm new at PHP so there might be a better way of doing this, but it works. :D

Here are the steps I took in order to get the results.

1. Go to Home » Administer » Store administration » Conditional Actions
In your Actions tab for the 'Action: Execute custom PHP code' first use this code:

print t('<pre>');
print_r ($order);
print t('</pre>');

2. Make a node of the product that you want to get the attributes for and select all the attributes, you will get an output of $order with all the data related to $order, find the part that has the attributes. It will look something like this:

 [data] => Array
                        (
                            [nid] => 1
                            [node_checkout_nid] => 50
                            [attributes] => Array
                                (
                                    [Style] => Array
                                        (
                                            [0] => bold
                                            [1] => Border
                                            [2] => highlight
                                            [3] => Featured
                                        )

If some of the attributes are not selected, then the away will look something like this:

                                    [Style] => Array
                                        (
                                            [0] => highlight
                                            [1] => Featured
                                        )

3. Copy the PHP data from the array and put it into the code you need using the snippet from below. Next, go back to Home » Administer » Store administration » Conditional Actions > Actions tab
Put in the code after you've made changes to it.

if (isset($order)) {
  foreach ($order->products as $product) {
    if (isset($product->data['node_checkout_nid'])) {
    
      $style1 = $product->data['attributes']['Style'][0];
      $style2 = $product->data['attributes']['Style'][1];
      $style3 = $product->data['attributes']['Style'][2];
      $style4 = $product->data['attributes']['Style'][3];
      
      $node = node_load($product->data['node_checkout_nid']);
      $node->field_orderid['0']['value'] = $order->order_id;
      $node->field_style1['0']['value'] = $style1;
      $node->field_style2['0']['value'] = $style2;
      $node->field_style3['0']['value'] = $style3;
      $node->field_style4['0']['value'] = $style4;
      // $node->status = 1; Is used to publish the node if the node isn't marked as Publish in the workflow settings.
      $node->status = 1;
      node_save($node);
    }
  }
}

4. Order another node product and your attributes will be in the CCK fields on the node!

A note, in the array for the attributes in $order, the attributes won't always be in order from [0] to [3] if all the attributes are not selected.

Alright, hope this helps out any one that needed it! If you have any questions, I'll try to answer with my overwhelming PHP experience! lol

Dallas

aidanlis’s picture

Some sort of basic functionality should come with uc_node_checkout to achieve this, and also some documentation about extending this for other fields needs to be written.

aidanlis’s picture

Status: Active » Fixed

This is done, available in the latest -dev release.

bombjack’s picture

Version: 6.x-2.x-dev » 6.x-2.0-beta8
Category: support » bug
Status: Fixed » Active

Apologies for reopening this so soon after the beta8 release, but this fix appears to have changed the behaviour causing me an issue.

I too have been following the guide mentioned in post 1 & 6, with some minor additions to the php code called in the 'conditional actions' section, intending to save some additional fields, only I found the data wasn't being stored. I checked and confirmed that the node was being updated with drupal_set_message debug dumps showing the nodes' content after the call to the node_save function

After much searching, trial and lots of errors, I finally reverted to the beta7 version to find that the functionality worked as expected.

Having looked through the change log it made more sense to me why the Product ID, Order ID and Status where the only items to be saved, being as this was new functionality recently added. I think this might be the source of the problem blocking the saving of the node in my case.

I am still reasonably new to Drupal and have yet to get my head around tracing back through function calls sufficiently to understand exactly what is going on, but it appears to me that at the point at which the php code assigned to the conditional action is executed, node checkout may have a copy of the node, which it duly intends to update with the Product ID, Order ID and Status as per the recent update, only when it saves these details it overwrites the node, thereby deleting the additional data that I am attempting to store.

Whilst I appreciate the desire to make it easy to map data to fields through the GUI it would be nice to be able to maintain the ability and flexibility of storing other details too. I hope it might be possible to have the best of both worlds unless the behaviour I am reporting was intentional for reasons I am unaware of.

Being as this is my first ever bug report post, I hope reopening this issue is the most appropriate way to have gone about it. It does seem closely associated!

Craig.

stellrex’s picture

It seems as though I'm unable to update the status field, even after following the suggestions above and from the drupal easy article. I have a cck field called "field_status", and I've chosen it as the Status field in the node checkout settings. When an order completes, the status does not change from 0 .

I've also tried adding the conditional actions per the drupal easy article, and the status never changes from 0 to 1. Does anyone have any insight here? I've spent a couple hours trying to figure this out with no success. Below is the code I added per the article:

if (isset($order)) {
foreach ($order->products as $product) {
if (isset($product->data['node_checkout_nid'])) {
$node = node_load($product->data['node_checkout_nid']);
$node->field_status['0']['value'] = 1;
$node->field_orderid['0']['value'] = $order->order_id;
node_save($node);
}
}
}

aidanlis’s picture

Status: Active » Fixed

@stellrex stop trying to use an integer field to store a string?

@bombjack bummer, I will open a new bug for you.

aidanlis’s picture

Status: Fixed » Closed (fixed)

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

guntherdevisch’s picture

@stellrex & @aidanlis: Do have a solution to store the status?

If have the code below for my CA, but the status isn't saved for $node->status AND $node->field_status['0']['value']. Before this was no problem, but recently this doesn't work anymore. I think by updating the module 'uc_node_checkout' to 6.x-2.0-beta8.

if (isset($order)) {
  foreach ($order->products as $product) {
    if (isset($product->data['node_checkout_nid'])) {
      $node = node_load($product->data['node_checkout_nid']);
      $node->field_status['0']['value'] = 1;
      $node->field_orderid['0']['value'] = $order->order_id;
      $node->status = 1; // publish the node 
      node_save($node); 
    }
  }
}

Thanks in advance,
Gunther

lyy9981’s picture

Issue summary: View changes

I had the same problem as @bombjack and @guntherdevisch pointed out. @bombjack explained very well what caused the problem, I solved it by reverting to the beta7 version.