dptpn06684 2016-11-13 12:49
浏览 53

PHP / MYSQL事务生成两个相同的主键

I have a function which used as a web services. code is like below.

public function create_order() {
       try{
            $this->db->trans_begin();
            $this->form_validation->set_rules($this->form_validation_array->get_app_rules('authenticate'));
            $this->form_validation->set_rules("table_id","Table_id","required");
           // $this->form_validation->set_rules("item[]","Items","required");
            if ($this->form_validation->run() == true) {
                $credential = array(
                    "restaurant_id" => $this->input->post("restaurant_id"),
                    "app_user_id" => $this->input->post("app_user_id"),
                    "app_id" => $this->input->post("app_id"),
                    "app_secret_id" => $this->input->post("app_secret")
                );
                $check = $this->authenticate_app_user($credential);
                if($check){
                   $order_data = array(
                        "user_id" => $credential['restaurant_id'],
                        "table_id" => $this->input->post("table_id"),
                        "created_by" => $credential['app_user_id'],
                        "created_date" => current_timestamp(),
                        'comments'=> ($this->input->post('comment')) ? $this->input->post('comment') : NULL, 
                        'status'=>1,
                    );
                    $order_id = $this->ws_details_model->current_order_id($order_data);
                    log_message('error','order_id_while_inserting '.print_r($order_id,true));
                    if(!$order_id) {
                       $order_data['unique_order_id'] = $this->common_function->unique_no('order');
                       $this->common_details_model->complete_existing_order($order_data);
                       $order = $this->ws_details_model->create_order($order_data);
                    } else {
                       $order_data['unique_order_id'] = $order_id->unique_order_id;
                       $order = $order_id->id;
                    }

                    if($order){
                       //$item_data = json_decode($this->input->post("item"),true);
                       $item_data = $this->input->post("item");
                       log_message('error','===============order id : '.$order.' is started====================
');
                       log_message('error',cook_log_message('order_array_without_process',$item_data));
                        if(is_array($item_data)) {
                            $order_item_data = array();
                            $j=0;
                            foreach ($item_data as $i){
                                $item_details = $this->ws_details_model->get_item_details($i['item_id']);
                                $toppings = $toppings_price = $varient = $varient_price = $topping_text = $varient_text = '';
                                 $topping_price = 0.00;
                                if(isset($i['item_topping'])) {
                                   $topping_details = $this->ws_details_model->get_toppings_details(explode(',',$i['item_topping']));
                                   if(!empty($topping_details)) {
                                      foreach($topping_details as $topping) {
                                         if($topping->is_t_v == 1) {
                                            $price = !empty($topping->price) ? $topping->price : '0';
                                            $toppings.= $topping->id.'|'.$topping->title.'|'.$price.',';
                                            $topping_text.= $topping->title.',';
                                            //$toppings_price.= (!empty($topping->price) ? $topping->price : '0').',';
                                         } else {
                                            $price = !empty($topping->price) ? $topping->price : '0';
                                            $varient.= $topping->id.'|'.$topping->title.'|'.$price.',';
                                            $varient_text.= $topping->title.',';
                                            //$varient_price.= (!empty($topping->price) ? $topping->price : '0').',';
                                         }
                                         $topping_price = $topping_price + $topping->price;
                                      }
                                   }
                                }
                                if($i['item_id']){
                                    $order_item_data[$j] = array(
                                        "order_id" => $order,
                                        "item_id" => $i['item_id'],
                                        "item_name" => $item_details['title'],
                                        "category_name" => $item_details['category_name'],
                                        "item_size" => $i['item_size'],
                                        "item_quantity" => $i['item_quantity'],
                                        "created_by" => $credential['app_user_id'],
                                        "created_date" => current_timestamp(),
                                        'comments'=> ($this->input->post('comment')) ? $this->input->post('comment') : NULL, 
                                        'status'=>1,
                                        "toppings"=>(!empty($toppings)) ? trim($toppings,',') : NULL,
                                        "toppings_text"=>(!empty($topping_text)) ? trim($topping_text,',') : NULL,
                                        "toppings_price"=>NULL,
                                        "varient"=>(!empty($varient)) ? trim($varient,',') : NULL,
                                        "varient_text"=>(!empty($varient_text)) ? trim($varient_text,',') : NULL,
                                        "varient_price"=>NULL,
                                    );
                                    if($i['item_size'] == 1) {
                                       $order_item_data[$j]['item_price'] = $item_details['small_price'];
                                    } elseif($i['item_size'] == 2) {
                                       $order_item_data[$j]['item_price'] = $item_details['medium_price'];
                                    } elseif($i['item_size'] == 3) {
                                       $order_item_data[$j]['item_price'] = $item_details['large_price'];
                                    } else {
                                       $order_item_data[$j]['item_price'] = $item_details['price'];
                                    }
                                    $order_item_data[$j]['final_price'] = ($order_item_data[$j]['item_quantity'] * $order_item_data[$j]['item_price']) + ($order_item_data[$j]['item_quantity'] * $topping_price);
                                    $j++;
                                }
                            }
                            log_message('error',cook_log_message('process_order_array_before_insert',$order_item_data));
                            $order_item = $this->ws_details_model->insert_order_item($order_item_data);
                            $table_data = array(
                               'status'=>3,
                               'updated_by'=>$credential['app_user_id'],
                               'updated_date'=>  current_timestamp()
                            );
                            $this->ws_details_model->change_table_status($order_data['table_id'],$table_data);
                            if ($this->db->trans_status() === FALSE)
                            {
                                $this->db->trans_rollback();
                                $data = array('result' => 'error', 'msg' => "Something went wrong!!! Please try again.");
                            }
                            else
                            {
                                $this->db->trans_commit();
                                log_message('error','===============order id : '.$order.' is end====================
');
                                $this->publish($credential['restaurant_id'],'inhouse',array('order_id'=>$order,'order_type'=>'inhouse'));
                                $data = array('result' => 'success', 'msg' => 'Order has been placed successfully','order_id'=>$order,'unique_order_id'=>$order_data['unique_order_id']);
                            }
                        } else {
                           $data = array('result' =>'error', 'msg' => "Item data is not in proper format");
                           $this->db->trans_rollback();
                        }
                    } else {
                        $data = array('result' => 'error', 'msg' => "Something went wrong!!! Please try again.");
                         $this->db->trans_rollback();
                    }
                } else {
                    $data = array('result' => 'error', 'msg' => "You are not authenticated user");
                    $this->db->trans_rollback();
                }
            }
            else {
               $data = array('result' => 'error', 'msg' => preg_replace("/[
]/", "", strip_tags(validation_errors())));
               $this->db->trans_rollback();
            }
            echo json_encode($data);
       } catch (Exception $e) {
          $this->db->trans_rollback();
          log_message('error',cook_log_message('app_create_order_error',$e->getMessage()));
       }
    }

Now the here is the problem.

  1. When this function called sometimes its insert some row automatically which are not in order_item_data array. I know its little bit weird but if you can check out the below screenshot you will understand what I am saying. enter image description here

To trace out this issue I have put log system with my function. When I have checked log I found out that The same primary key has generated two times. below is the log

ERROR - 2016-11-12 21:49:07 --> ===============order id : 5091 is started====================

ERROR - 2016-11-12 21:49:07 --> 2016-11-12 21:49:07 :  : Order array without process  : order_array_without_process : Array
(
    [0] => Array
        (
            [item_id] => 40
            [item_size] => 0
            [item_quantity] => 1
            [item_topping] => 79
        )

)
ERROR - 2016-11-12 21:49:07 --> ===============order id : 5091 is end====================


ERROR - 2016-11-12 22:15:08 --> ===============order id : 5091 is started====================

ERROR - 2016-11-12 22:15:08 --> 2016-11-12 22:15:08 :  : Order array without process  : order_array_without_process : Array
(
    [0] => Array
        (
            [item_id] => 65
            [item_size] => 0
            [item_quantity] => 1
        )

    [1] => Array
        (
            [item_id] => 64
            [item_size] => 0
            [item_quantity] => 1
        )

)
ERROR - 2016-11-12 22:15:08 --> ===============order id : 5091 is end====================

In above log you can see that order_id 5091 which is primary is key its generated two times and if you can check ERROR - Time of log than both have different time than how it would be possible ?

Below are the table structure.

1. order table

CREATE TABLE `m_order` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `user_id` int(11) NOT NULL COMMENT 'belongs to m_users table',
 `table_id` int(11) DEFAULT NULL COMMENT 'belongs to m_table',
 `unique_order_id` varchar(100) DEFAULT NULL,
 `order_type` int(1) NOT NULL DEFAULT '1' COMMENT '1=table_order,2=take_away',
 `payment_by` int(11) NOT NULL DEFAULT '0' COMMENT '1=cash,2=card',
 `order_from` int(11) DEFAULT '1' COMMENT '1=web,2=app',
 `device_id` text COMMENT 'device id from where order placed',
 `device_name` varchar(254) DEFAULT NULL,
 `delivery_taken_by` int(11) DEFAULT NULL COMMENT 'belongs to m_staff tables ',
 `comments` text,
 `ip_address` varchar(40) DEFAULT NULL,
 `created_by` int(11) NOT NULL,
 `updated_by` int(11) DEFAULT NULL,
 `created_date` int(20) NOT NULL,
 `updated_date` int(20) DEFAULT NULL,
 `status` int(1) NOT NULL DEFAULT '1' COMMENT '1=current order,2=completed,3=order cancelled,4=out for delivery',
 PRIMARY KEY (`id`),
 KEY `user_id` (`user_id`),
 KEY `table_id` (`table_id`)
) ENGINE=InnoDB AUTO_INCREMENT=180 DEFAULT CHARSET=utf8

2. Order Item table structure

CREATE TABLE `m_order_items` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `order_id` int(11) NOT NULL,
 `item_id` int(11) NOT NULL,
 `category_name` varchar(200) DEFAULT NULL,
 `item_name` varchar(100) NOT NULL,
 `item_size` varchar(100) NOT NULL COMMENT 'small,medium,large',
 `item_price` float(12,2) NOT NULL,
 `item_quantity` float NOT NULL DEFAULT '1',
 `item_unit` varchar(255) DEFAULT NULL,
 `toppings` varchar(250) DEFAULT NULL,
 `toppings_text` varchar(255) DEFAULT NULL,
 `toppings_price` varchar(250) DEFAULT NULL,
 `varient` varchar(250) DEFAULT NULL,
 `varient_text` varchar(255) DEFAULT NULL,
 `varient_price` varchar(250) DEFAULT NULL,
 `final_price` float(12,2) DEFAULT NULL,
 `comments` text,
 `ip_address` varchar(40) DEFAULT NULL,
 `created_by` int(11) NOT NULL,
 `updated_by` int(11) DEFAULT NULL,
 `created_date` int(20) NOT NULL,
 `updated_date` int(20) DEFAULT NULL,
 `is_printed` int(1) NOT NULL DEFAULT '0' COMMENT '1=printed,0=not yet printed',
 `status` int(1) NOT NULL DEFAULT '1' COMMENT '1=active,2=completed,3=cancelled,4=after serve return,5=deleted',
 PRIMARY KEY (`id`),
 KEY `order_id` (`order_id`),
 CONSTRAINT `m_order_items_ibfk_1` FOREIGN KEY (`order_id`) REFERENCES `m_order` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=430 DEFAULT CHARSET=utf8

So If anyone can understand this issue than please help to resolve this issue.What should I change in my code so it would not extra item with my array with same primary as its not in posted array value.

Thanks in advance.

  • 写回答

0条回答 默认 最新

    报告相同问题?

    悬赏问题

    • ¥20 求各位懂行的人,注册表能不能看到usb使用得具体信息,干了什么,传输了什么数据
    • ¥15 Vue3 大型图片数据拖动排序
    • ¥15 划分vlan后不通了
    • ¥15 GDI处理通道视频时总是带有白色锯齿
    • ¥20 用雷电模拟器安装百达屋apk一直闪退
    • ¥15 算能科技20240506咨询(拒绝大模型回答)
    • ¥15 自适应 AR 模型 参数估计Matlab程序
    • ¥100 角动量包络面如何用MATLAB绘制
    • ¥15 merge函数占用内存过大
    • ¥15 使用EMD去噪处理RML2016数据集时候的原理