数据表 - 将列作为HTML元素返回

时间:2017-07-21 17:52:09

标签: php jquery ajax laravel datatables

我在将某些客户端数据表逻辑迁移到服务器端时遇到了一些困难。

我当前的问题是,对于Datatables,如果要分页大量数据(20,000多行),我首先需要加载Controller中的所有行,然后将它们传递给视图:

$records = \App\Records::get();

return view("example.datatables")->with(["records" => $records]);

接下来,在加载所有内容之前需要大约2分钟的等待时间,Datatables将记录分页为500页:

$("#table").DataTable({
  paging: true,
  pageLength: 500,
  ...
});

我已经通过ajax更改了Datatables声明以处理服务器端处理,如下所示:

$("#table").DataTable({
  processing: true,
  serverSide: true,
  ajax: {
    url: "...",
    type: "GET"
  }, paging: true,
  pageLength: 500,
  ...
});

让我的工作变得非常顺利,但问题是Datatables正在压倒或忽略我从ajax请求发回的内容:

$columnData = [];
foreach($recordsFromDatabase AS $record){
  $columnDataObject = [];

  $columnDataObject[0] = '<td class="myClass" data-property="myProperty"><input type="text" name="customInput[]"/></td>'

  ...

  $columnData[] = $columnDataObject;
}

return response()->json([
  "draw" => (int)$request->input("draw"),
  "recordsTotal" => $totalRecords,
  "recordsFiltered" => $totalFilteredRecords,
  "data" => $columnData,
  "error" => null
]);

基本上,我发回的是json响应,其中包含data,这是一个列数组,它们是<td>个元素,而不仅仅是一个普通值。所以<td>Value</td> vs Value

数据表给出了这种方法正常工作的错觉,但我最终得到了

<tr role="row" class="even">
  <td class="sorting_1"><input type="text" name="customInput[]"/></td>
  ...
</tr>
<tr role="row" class="odd">
  <td class="sorting_1"><input type="text" name="customInput[]"/></td>
  ...
</tr>

它正确地呈现<input>内的<td>,但class="myClass" data-property="myProperty"丢失了,这会破坏我的表格的扩展功能。

有没有办法告诉Datatables我发回的内容是有效的<td>元素,而且它需要做的就是添加oddeven类? (即便如此,我认为这只是为了造型)。

2 个答案:

答案 0 :(得分:2)

您正在错误地使用jQuery DataTable。

您不应将<td>元素作为数据发送。使用columns.render选项为您的单元格生成内容和/或columns.createdCell选项,以便将属性添加到<td>元素。

例如:

$('#example').DataTable( {
  "columnDefs": [ {
    "targets": 3,
    "createdCell": function (td, cellData, rowData, row, col) {
      $(td)
        .attr('data-property', rowData['myCustomProperty'])
        .addClass(rowData['myClass']);
    }
  } ]
} );

对于Laravel,使用优秀的Laravel DataTables包在服务器端处理模式下正确显示表。

答案 1 :(得分:0)

所以我最后仍然通过我的响应发送HTML,并使用datatable的createdRow回调,我能够将HTML解析为本地DOM元素,检查它们的类和属性,并将它们分配给行/列根据要求:

createdRow: function(row, data, rowIndex) {
  $.each($("td", row), function (colIndex) {
    var elementFromData = $.parseHTML(data[colIndex]);
    var element = elementFromData[0];

    var elementClass = $(element).attr("class");
    if(typeof elementClass !== undefined){
      $(this).addClass(elementClass);
    }

    var attributes = [
      {
        label: "data-id",
        value: $(element).attr("data-id")
      }, ...
    ];

    for(var i = 0; i < attributes.length; i++){
      var attribute = attributes[i];

      if(typeof attribute.value !== undefined){
        $(this).attr(attribute.label, attribute.value);
      }
    }
  });
}, ...

它可能不是最漂亮的解决方案,我理解从我的AJAX请求返回HTML效率很低,但由于时间限制,这是我能想到的最佳解决方案。