在CodeIgniter中插入重复的数据



我只是在pastebin的codeigniter控制器部分插入数据http://pastebin.com/KBtqrAkZ

  public function add_product()
  {
    $this->lang->load('log_in', 'english');
        log_in_check($this->lang->line('log_in_authentication_error'), 'admin/log_in');
        $this->lang->load('common', 'english');
        $data['title'] = $this->lang->line('admin_index_title');
        $this->load->view('admin_template/header', $data);
        $this->load->view('admin_template/left_menu');
    $data['error_msg'] = '';
        if ($this->form_validation->run('add_product') === TRUE)
        {
      $this->admin_model->add_product($this->input->post());
            $this->session->set_flashdata('status_msg', $this->lang->line('add_product_success'));
            redirect(uri_string(), 'refresh');
      exit ;
          $data['error_msg'] = $this->lang->line('add_product_invalid_data');
        }
        $this->load->view('admin/add_product');
        //$this->load->view('admin_template/notification');
        $this->load->view('admin_template/footer');  
  }

比我的模型部分是简单的添加在pastebinhttp://pastebin.com/WiLHV2sr

  public function add_product($data = array())
  {
    $this->db->insert('ishop_product', $data);
    return $this->db->insert_id();
  }

我的问题是在重定向后,如果我按ctrl+F5或F5,数据就会插入。我是一个新的代码点火器。请帮帮我。任何帮助都将不胜感激。

这就是双重提交问题

有几种处理方法:

  1. 发布/重定向/获取模式:打断后退按钮,它不会阻止用户返回到足以再次提交的位置。不处理多次单击。

  2. 禁用提交按钮:有时会处理多次单击,但不会修复用户返回并再次提交的问题。

  3. 在会话中存储令牌:如果在浏览器中打开多个选项卡,则存储在会话中的令牌可能会混淆。(注意:可能可以使用javascript创建特定于浏览器选项卡的cookie,但我自己还没有尝试过。(

  4. 更改数据库以不允许重复:这是最好的解决方案,也是最努力的。如果检测到一组重复数据,则忽略第二个请求。

  5. 唯一事务id:在这个PHP黑客页面和这个答案中进行了描述。

  6. 会话中的多个令牌:选项3的变体。如果将所有生成的令牌存储在会话中,则不需要涉及数据库。考虑到令牌在会话中是唯一的,重复的概率要低得多。可能的问题包括令牌集的增长失控。也许可以用一个有限大小的堆栈来修复,在堆栈的顶部添加,然后额外的代币从底部掉下来。未测试。

--

我喜欢唯一事务id方法。它是这样工作的:

  1. 生成一个随机的transaction_id,并将其放在您的web表单中。当用户单击submit时,它就会出现。

  2. 当您收到添加产品的请求时,请检查事务表中的transaction_id

  3. 如果表中不存在id,则执行事务,并将transaction_id插入表中。

  4. 如果表中确实存在id,则事务已经完成。

您还应该在中搜索[双重提交预防],看看是否能找到更好的解决方案。

有一个简单的解决方案,您可以在添加产品后重定向到其他页面,如:

重定向(base_url((。"yourcontrollername/index"(;

这样做将删除发布数据,并且数据不会重新添加到数据库中。

最新更新