phparraysfor-looposcommerce

loop through array not returning correct values


I've been staring at this for some time, but can't figure out what's wrong. First of all my code:

//Show the products information line by line
$item_count = 0 ;
for ($i = 0, $n = sizeof($order->products); $i < $n; $i++) {
    $data2[$i][0] = $order->products[$i]['qty'];

    if (strlen($order->products[$i]['name']) > 40 && strlen($order->products[$i]['name']) < 50){
        $data2[$i][1] = $order->products[$i]['name'];
    } else if (strlen($order->products[$i]['name']) > 50) {
        $data2[$i][1] = substr($order->products[$i]['name'],0,50);
    } else {
        $data2[$i][1] = $order->products[$i]['name'];
    }

    $data2[$i][2] = $order->products[$i]['model'];

    $data2[$i][3] = str_replace('&nbsp;', ' ',$currencies->format($order->products[$i]['final_price'], true, $order->info['currency'], $order->info['currency_value']));

    // Add to $data2 if needed (adjust/renumber subsequent array keys!):

    // For VAT purposes:
    // Check if product is an 'electronic service'. If so, determine the customer's country.

    // NOTE (Debug): the comparison of " pov.products_options_values_name = $order->products[$i]['attributes'][$j]['value'] " only holds if the option description is not changed/replaced/deleted.

    if (isset($order->products[$i]['attributes']) && (($k = sizeof($order->products[$i]['attributes'])) > 0)) {
        for ($j = 0; $j < $k; $j++) {
            $virtual_check_query = tep_db_query("select count(*) as total from " . TABLE_PRODUCTS_ATTRIBUTES . " pa, " . TABLE_PRODUCTS_ATTRIBUTES_DOWNLOAD . " pad, " . TABLE_PRODUCTS_OPTIONS_VALUES . " pov where pa.products_id = '" . $order->products[$i]['id'] . "' and pov.products_options_values_name = '" . $order->products[$i]['attributes'][$j]['value'] . "' and pa.products_attributes_id = pad.products_attributes_id");
            $virtual_check = tep_db_fetch_array($virtual_check_query);
            if ($virtual_check['total'] > 0) {
                $product_type_check = 'virtual';
                $order_type_check = 'virtual or mixed';
                break;
            }
        }
    }

    if ($product_type_check == 'virtual') {
        if ($customer_country == 'home country') {
            $data2[$i][4] = str_replace('&nbsp;', ' ',tep_display_tax_value($order->products[$i]['tax']) . '%');
        } elseif ($customer_country == 'eu country') {
            $data2[$i][4] = '***';
        } else {
            $data2[$i][4] = str_replace('&nbsp;', ' ',tep_display_tax_value($order->products[$i]['tax']) . '%');
        }
    } else {
        $data2[$i][4] = str_replace('&nbsp;', ' ',tep_display_tax_value($order->products[$i]['tax']) . '%');
    }

    unset($product_type_check);

    //      $data2[$i][3] = str_replace('&nbsp;', ' ',$currencies->format($order->products[$i]['final_price'], true, $order->info['currency'], $order->info['currency_value']));

    // Add to $data2 if needed (adjust/renumber subsequent array keys!):
    //      $data2[$i][5] = str_replace('&nbsp;', ' ',$currencies->format(tep_add_tax($order->products[$i]['final_price'], $order->products[$i]['tax']), true, $order->info['currency'], $order->info['currency_value']));

    $data2[$i][5] = str_replace('&nbsp;', ' ',$currencies->format($order->products[$i]['final_price'] * $order->products[$i]['qty'], true, $order->info['currency'], $order->info['currency_value'])) ;

    // Add to $data2 if needed (adjust/renumber subsequent array keys!):
    //      $data2[$i][5] = str_replace('&nbsp;', ' ',$currencies->format(tep_add_tax($order->products[$i]['final_price'], $order->products[$i]['tax']) * $order->products[$i]['qty'], true, $order->info['currency'], $order->info['currency_value']));


    // Show the products attributes
    $data3 = array();

    //get attribs
    if (isset($order->products[$i]['attributes']) && (($z = sizeof($order->products[$i]['attributes'])) > 0)) {
        $attribute_line = 'true';
        for ($m = 0; $m < $z; $m++) {
            if ($order->products[$i]['attributes'][$m]['price'] != '0') {
                if (strlen('- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value'] . ' (' . $order->products[$i]['attributes'][$m]['prefix'] . $currencies->format($order->products[$i]['attributes'][$m]['price'] * $order->products[$i]['qty'], true, $order->info['currency'], $order->info['currency_value']) . ')') > 50) {
                    $data3[$i][$m][1] = substr('- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value'],0,40) . ' (' . $order->products[$i]['attributes'][$m]['prefix'] . $currencies->format($order->products[$i]['attributes'][$m]['price'] * $order->products[$i]['qty'], true, $order->info['currency'], $order->info['currency_value']) . ')';
                } else {
                    $data3[$i][$m][1] = '- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value'] . ' (' . $order->products[$i]['attributes'][$m]['prefix'] . $currencies->format($order->products[$i]['attributes'][$m]['price'] * $order->products[$i]['qty'], true, $order->info['currency'], $order->info['currency_value']) . ')' ;
                }
            } else {
                if (strlen('- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value']) > 50) {
                    $data3[$i][$m][1] = substr('- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value'],0,50);
                } else {
                    //        $data3[$i][$m][1] = '- ' . $order->products[$i]['attributes'][$m]['option'] . ': ' . $order->products[$i]['attributes'][$m]['value'];
                    $data3[$i][$m][1] = '- ' . $order->products[$i]['attributes'][$m]['value'];
                }
            }
        }
    }
}

The code above is supposed to:

The array $order->products contains the following data:

Array (

[0] => Array ( 
[qty] => 1 
[id] => 4 
[name] => Product A
[model] => 
[tax] => 21.0000 
[price] => 19.9900 
[final_price] => 19.9900 
[attributes] => Array ( 
[0] => Array ( 
[option] => Type 
[value] => X 
[prefix] => + 
[price] => 0.0000 
) 
) 
) 

[1] => Array ( 
[qty] => 1 
[id] => 4 
[name] => Product A
[model] => 
[tax] => 21.0000 
[price] => 19.9900 
[final_price] => 19.9900 
[attributes] => Array ( 
[0] => Array ( 
[option] => Type 
[value] => Y
[prefix] => 
[price] => 0.0000 
) 
) 
) 
)

The code enters the following data in the array $data3:

Array ( 
[1] => Array (
[0] => Array (
[1] => - Y
) 
) 
) 

This means that the attributes of the first product (Product A with key 0 in the $order->products array is missing!

My gut feeling tells me that the code has moved already moved through the $order->products array before executing the 'Show the products attributes' section of the code.

The code is based on this snippet taken from checkout_confirmation.php (osCommerce):

for ($i=0, $n=sizeof($order->products); $i<$n; $i++) {
echo '          <tr>' . "\n" .
 '            <td class="infoBoxMargin">' . tep_draw_separator('pixel_trans.gif', '10', '1') . '</td>' . "\n" .
     '            <td class="main" align="left" valign="top" width="10%">' . $order->products[$i]['qty'] . '&nbsp;x</td>' . "\n" .
     '            <td class="main" align="left" valign="top" width="60%">' . $order->products[$i]['name'];

if (STOCK_CHECK == 'true') {
  echo tep_check_stock($order->products[$i]['id'], $order->products[$i]['qty']);
}

if ( (isset($order->products[$i]['attributes'])) && (sizeof($order->products[$i]['attributes']) > 0) ) {
  for ($j=0, $n2=sizeof($order->products[$i]['attributes']); $j<$n2; $j++) {
echo '<br /><nobr><small>&nbsp;<i> - ' . $order->products[$i]['attributes'][$j]['option'] . ': ' . $order->products[$i]['attributes'][$j]['value'] . '</i></small></nobr>';
  }
}

Can anyone explain to me where things go wrong?

Kind regards,

Dennis


Solution

  • Dealing with osCommerce code for many years I have to say, that there are lots of wierd code and if you are not for long with it, you better migrate to something new, thay doesn't use register_globals al least. Another reason to migrate is that there's no MVC model - you always see mixed php code, html layout and sql queries, especially in admin section. Another important reason for migration is tables structure, or more precisely, lack or wrong indexes.

    As for me, I've completely rewritten lots of code, including totally new product class and products attributes. Now, for example, I use product object everywhere, including products list in category, shoping cart, wishlist, etc. Believe me, I don't have a headache with separate sql queries that get different products' data.

    Now to you question. I suppose that problem is here:

    $data3 = array();
    

    Each time you loop $order->products your variable is set to empty array. Thus try to define it before you start iterating $order->products. For example:

    $data3 = array();
    for ($i = 0, $n = sizeof($order->products); $i < $n; $i++) {
    // your code
    }
    

    and don't forget to remove $data3 = array(); from the loop.

    Hope this helps.

    Good luck.