【问题标题】:forbidden in ajax call error function in codeigniter csrf在codeigniter csrf中的ajax调用错误函数中被禁止
【发布时间】:2017-01-25 17:28:22
【问题描述】:

我刚刚开始使用 codeigniter 我想通过 ajax 将一些数据插入数据库,但是我的 ajax 调用有问题; 我一直在寻找两个小时,但我无法解决问题。 我的问题是当我点击提交按钮时,它说禁止。
我的 csrf 保护也设置为 TRUE!请帮忙,谢谢

JS

$(document).ready(function() {

$(".addbtn").click(function (e) {
        e.preventDefault();
        if($("#mname").val()==='' || 
           $('#sname').val() === '' || 
           $('#genre').val()==='' || 
           $('#album').val()==='' ||
           $('#publishyear').val() ==='' ||
           $('#artist').val()==='')
        {
            alert("Please fill all the fields!");
            return false;
        }

        $("#FormSubmit").hide(); 
        $("#LoadingImage").show(); 

        var baseurl = "<?php echo base_url(); ?>";
        var data = {
                'mname': $("#mname").val(),
                'sname': $('#sname').val(),
                'genre': $('#genre').val(),
                'album': $('#album').val(),
                'publishyear': $('#publishyear').val(),
                'artist': $('#artist').val(),
                '<?php echo $this->security->get_csrf_token_name(); ?>':
                '<?php echo $this->security->get_csrf_hash(); ?>'
                };

        $.ajax({
        type: "POST", 
        url:  baseurl+"index.php/admin_page/send_ajax", 
        data: data, 
        success:function(){
            alert("success");

        },
        error:function (xhr, ajaxOptions, thrownError){
            $("#FormSubmit").show(); 
            $("#LoadingImage").hide(); 
            alert(thrownError);
        }
        });
  });});

配置文件

$config['csrf_protection'] = TRUE;
$config['csrf_token_name'] = 'csrf_test_name';
$config['csrf_cookie_name'] = 'csrf_cookie_name';
$config['csrf_expire'] = 7200;
$config['csrf_regenerate'] = TRUE;
$config['csrf_exclude_uris'] = array();

控制器

public function send_ajax(){


    $data = array(
                'name_of_music'=>$this->input->post("mname", TRUE),
                'artist'=>$this->input->post("artist", TRUE),
                'name_of_singer'=>$this->input->post("sname", TRUE),
                'genre'=>$this->input->post("genre", TRUE),
                'album'=>$this->input->post("album", TRUE),
                'publishyear'=>$this->input->post("publishyear", TRUE)
            );
    $json_data['lyrics_info_data'] = json_decode($data);
    $this->user_model->insert_json_in_db($json_data);
  }

型号

public function insert_json_in_db($json_data){
    $this->db->insert('lyrics', $json_data);
  }

【问题讨论】:

  • 你应该json_encode($data),而不是json_decode
  • Zeeshan 我修好了,但还是不行!说禁止
  • 你能通过输入echo 'In controller;exit;来确定你的控制器的函数是否被ajax调用
  • 是的,我确定。一切都设置正确!我不知道为什么还要说禁止
  • 我觉得问题是csrf配置我不知道在哪里!

标签: ajax codeigniter csrf


【解决方案1】:

你能确认$json_data['lyrics_info_data'] = json_decode($data);这行有什么用吗?我认为这条线是错误的。

您可以使用$json_data['lyrics_info_data'] = $data; 代替$json_data['lyrics_info_data'] = json_decode($data);

模型功能也需要更新。

public function insert_json_in_db($json_data){
    $this->db->insert('lyrics', $json_data['lyrics_info_data']);
}

脚本更新

Codeigniter 将在每次请求时重新生成其 crcf 令牌,并且此信息将存储在 cookie 中。因此,您需要从 cookie 中获取令牌值并与您传递的 ajax 数据一起发送。我对以下 javascript 所做的是,使用一个通用函数将 crcf 值与所有 ajax 请求一起附加。

在 jquery 中有一个选项可以添加自定义数据以及 ajax 请求。 详情请参阅 jquery 文档http://api.jquery.com/jquery.ajaxprefilter/

<script>
   $(document).ready(function(){ 

function getCookie(c_name) { // A javascript function to get the cookie value 
    if(document.cookie.length > 0) {
        c_start = document.cookie.indexOf(c_name + "=");
        if(c_start != -1) {
            c_start = c_start + c_name.length + 1;
            c_end = document.cookie.indexOf(";", c_start);
            if(c_end == -1) c_end = document.cookie.length;
            return unescape(document.cookie.substring(c_start,c_end));
        }
    }
    return "";
}

$.ajaxPrefilter(function(options, originalOptions, jqXHR){ // This function will attach "csrf_test_name" with all the request you are sending. 
    if (options.type.toLowerCase() === "post") { // Required only if its a post method 
        var csrf_token = getCookie("csrf_test_name");
        // initialize `data` to empty string if it does not exist
        options.data = options.data || "";

        // add leading ampersand if `data` is non-empty
        options.data += options.data?"&":"";

        // add _token entry
        options.data += "csrf_test_name=" + csrf_token;
    }
});
 });
   </script>

您可以从var data 中删除'&lt;?php echo $this-&gt;security-&gt;get_csrf_token_name(); ?&gt;': '&lt;?php echo $this-&gt;security-&gt;get_csrf_hash(); ?&gt;'

重要提示:如果您在 config.php 中更改 $config['csrf_token_name'] = 'csrf_test_name';,那么您也需要更新此脚本。

请在更新您的代码后尝试,如果问题仍然存在,请告诉我。

【讨论】:

  • 还是说禁止。
  • 你能确保你已经加载了你的模型文件吗?
  • 我 100% 确定,因为我的控制器中的其他方法工作正常
  • 是的,我试过你的代码。问题是 ajax 根本无法将请求发送到我的控制器中的方法这里是我的网址:url: "http://localhost/CodeIgniter/admin_dashboard/send_ajax",
  • 在浏览器中直接调用“localhost/CodeIgniter/admin_dashboard/send_ajax”会发生什么?控制器名称为“admin_dashboard”,文件名为“Admin_dashboard”(注意,如果您使用 CI 版本 3,则控制器的第一个字母应为大写)?
【解决方案2】:

确保base_url() 正确,并且在 javascript 中,您应该在某处全局定义 base_url(),以便您可以在任何脚本中访问它,如下所示

var baseurl = <?php echo base_url() ?>;

`

【讨论】:

    【解决方案3】:

    您正在竭尽全力使这变得困难。 csrf 不是你的问题。试试这样的

    $(function () {
     "use strict";
     $("#form2").submit(function () {
     var data = $("#form2").serialize();
     //alert(data); return false;
     $.ajax({
      url: "/log/login",
      data: data,
      type: "POST",
      success: function (msg) {
        $("#display").text(msg);
      },
      error: function (msg) {
        $("#display").text("its all bad");
      }
      });
      return false;
     });
     });
    

    (当然你需要将自己的表单ID放入等)

    您的控制器应如下所示:

      $data = array(
    'borncity'  => htmlspecialchars(trim($this->input->post('borncity'))),
    'state'     => htmlspecialchars(trim($this->input->post('state'))),
    'country'   => htmlspecialchars(trim($this->input->post('country'))),
    'family'    => htmlspecialchars(trim($this->input->post('family'))),
    'year'      => htmlspecialchars(trim($this->input->post('year'))),
    'state1'    => htmlspecialchars(trim($this->input->post('state1'))),
    'deathcity' => htmlspecialchars(trim($this->input->post('deathcity')))
    );
    
    $this->form_validation->set_rules('borncity', 'city of birth', 'required|trim');
    $this->form_validation->set_rules('state', 'state', 'required|trim');
    $this->form_validation->set_rules('country', 'country', 'required|trim');
    $this->form_validation->set_rules('family', 'family', 'required|trim');
    $this->form_validation->set_rules('year', 'year', 'required|trim');
    $this->form_validation->set_rules('state1', 'Born State', 'required|trim');
    $this->form_validation->set_rules('deathcity', 'Death City', 'trim');
    
    if( $this->form_validation->run() == FALSE) {
      echo validation_errors();
    }else
    {
      $this->db->insert('cities', $data);
      echo "Success"; //this will show up in your ajax success line
    }
    }
    

    在您的控制器中使用 Codeigniter 的表单验证。您不需要使用 json 解码。请注意这些是示例

    【讨论】:

    • 我像上面一样更新了我的代码,但没有工作,仍然说禁止! ajax 无法将请求发送到方法我不知道为什么但似乎根本找不到方法。
    • 不使用ajax还能用吗?记住ajax url和方法url是一样的
    • 是的,我可以使用 codeigniter 表单并将我的数据发送到控制器。这种方式会很好用。我尝试了您上面的代码,但 ajax 再次拒绝了该请求。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-03-23
    • 2023-03-05
    • 2015-10-06
    • 2013-05-25
    • 2023-03-08
    • 1970-01-01
    相关资源
    最近更新 更多