case 'delete_options_values_of_option_name':
     $options_id_from = $_POST['options_id_from'];
     $options_values_values_id_from = $_POST['options_values_values_id_from'];
     // one category of products or all products
     if ($_POST['copy_to_categories_id'] != '') {
         $products_only = $db->Execute("select ptc.products_id from " . TABLE_PRODUCTS_TO_CATEGORIES . " ptc left join " . TABLE_PRODUCTS_ATTRIBUTES . " pa on pa.products_id=ptc.products_id where ptc.categories_id='" . $_POST['copy_to_categories_id'] . "' and (pa.options_id='" . $options_id_from . "' and pa.options_values_id='" . $options_values_values_id_from . "')");
     } else {
         $products_only = $db->Execute("select pa.products_id from " . TABLE_PRODUCTS_ATTRIBUTES . " pa where pa.options_id='" . $options_id_from . "' and pa.options_values_id='" . $options_values_values_id_from . "'");
     }
     if ($_POST['copy_to_categories_id'] == '') {
         $zc_categories = ' All Products ';
     } else {
         $zc_categories = ' Category: ' . $_POST['copy_to_categories_id'];
     }
     $new_attribute = 0;
     if (!zen_validate_options_to_options_value($options_id_from, $options_values_values_id_from)) {
         $messageStack->add(ERROR_OPTION_VALUES_DELETE_MISMATCH . TEXT_INFO_FROM . zen_options_name($options_id_from) . ' ' . zen_values_name($options_values_values_id_from), 'warning');
     } else {
         // check for existing combination
         if ($products_only->RecordCount() > 0) {
             // check existing matching products and add new attributes
             while (!$products_only->EOF) {
                 $current_products_id = $products_only->fields['products_id'];
                 // check for associated downloads
                 $downloads_remove_query = "select products_attributes_id from " . TABLE_PRODUCTS_ATTRIBUTES . " where products_id='" . $current_products_id . "' and options_id='" . $options_id_from . "' and options_values_id='" . $options_values_values_id_from . "'";
                 $downloads_remove = $db->Execute($downloads_remove_query);
                 $sql = "delete from " . TABLE_PRODUCTS_ATTRIBUTES . " where products_id='" . $current_products_id . "' and options_id='" . $options_id_from . "' and options_values_id='" . $options_values_values_id_from . "'";
                 $delete_selected = $db->Execute($sql);
                 // delete associated downloads
                 while (!$downloads_remove->EOF) {
                     $db->Execute("delete from " . TABLE_PRODUCTS_ATTRIBUTES_DOWNLOAD . "\n                            where products_attributes_id='" . $downloads_remove->fields['products_attributes_id'] . "'");
                 }
             }
         }
     }
     // reset products_price_sorter for searches etc.
     zen_update_products_price_sorter($_POST['products_id']);
     zen_redirect(zen_href_link(FILENAME_ATTRIBUTES_CONTROLLER, $_SESSION['page_info'] . '&products_filter=' . $_POST['products_id'] . '&current_category_id=' . $_POST['current_category_id']));
     break;
 case 'update_product_attribute':
     $check_duplicate = $db->Execute("select * from " . TABLE_PRODUCTS_ATTRIBUTES . "\n                                         where products_id ='" . (int) $_POST['products_id'] . "'\n                                         and options_id = '" . (int) $_POST['options_id'] . "'\n                                         and options_values_id = '" . (int) $_POST['values_id'] . "'\n                                         and products_attributes_id != '" . (int) $_POST['attribute_id'] . "'");
     if ($check_duplicate->RecordCount() > 0) {
         // do not add duplicates give a warning
         $messageStack->add_session(ATTRIBUTE_WARNING_DUPLICATE_UPDATE . ' - ' . zen_options_name($_POST['options_id']) . ' : ' . zen_values_name($_POST['values_id']), 'error');
     } else {
         // Validate options_id and options_value_id
         if (!zen_validate_options_to_options_value($_POST['options_id'], $_POST['values_id'])) {
             // do not add invalid match
             $messageStack->add_session(ATTRIBUTE_WARNING_INVALID_MATCH_UPDATE . ' - ' . zen_options_name($_POST['options_id']) . ' : ' . zen_values_name($_POST['values_id']), 'error');
         } else {
             // add the new attribute
             // iii 030811 added:  Enforce rule that TEXT and FILE Options use value PRODUCTS_OPTIONS_VALUES_TEXT_ID
             $products_options_query = $db->Execute("select products_options_type from " . TABLE_PRODUCTS_OPTIONS . " where products_options_id = '" . (int) $_POST['options_id'] . "'");
             switch ($products_options_array->fields['products_options_type']) {
                 case PRODUCTS_OPTIONS_TYPE_TEXT:
                 case PRODUCTS_OPTIONS_TYPE_FILE:
                     $values_id = PRODUCTS_OPTIONS_VALUES_TEXT_ID;
                     break;
                 default:
                     $values_id = zen_db_prepare_input($_POST['values_id']);
             }
             // iii 030811 added END
 function validate_save($post)
 {
     global $db;
     $errors = array();
     // check for duplicate and block them
     $query = "select * from " . TABLE_PRODUCTS_ATTRIBUTES . "\n                where products_id ='" . $post['products_id'] . "'\n                  and options_id = '" . $post['options_id'] . "'\n                  and options_values_id = '" . $post['options_values_id'] . "'";
     if ($post['attributes_id']) {
         $query .= " and products_attributes_id != '" . $post['attributes_id'] . "'";
     }
     $check_duplicate = $db->Execute($query);
     if ($check_duplicate->RecordCount() > 0) {
         $errors[] = ATTRIBUTE_WARNING_DUPLICATE . ' - ' . zen_options_name($post['options_id']) . ' : ' . zen_values_name($post['options_values_id']);
     } else {
         // Validate options_id and options_value_id
         if (!zen_validate_options_to_options_value($post['options_id'], $post['options_values_id'])) {
             // do not add invalid match
             $errors[] = ATTRIBUTE_WARNING_INVALID_MATCH . ' - ' . zen_options_name($post['options_id']) . ' : ' . zen_values_name($post['options_values_id']);
         }
     }
     return $errors;
 }