DataTables中category_name列排序功能失效问题排查
orderable: true Let's break down the issues with your configuration and fix them step by step:
1. Incorrect Property Name in Column Configuration
The first critical mistake is in your columns array for the category_name column (third column, index 2): you used ordering: true instead of the correct DataTables property name orderable: true.
DataTables doesn't recognize the ordering property, so this setting is ignored—even though you set orderable: true in columnDefs, fixing the root issue in the column's direct configuration will make your code clearer and more reliable.
2. Render Function Doesn't Return Raw Data for Sorting
Your render function returns HTML markup for all request types, including when DataTables needs the raw value for sorting (type='order'). When you sort, DataTables will try to sort based on the HTML string (e.g., <a href="...">Category Name</a>) instead of the actual name field value, which will lead to incorrect or non-functional sorting behavior.
You need to adjust the render function to return the raw data when the type is order or filter (for search functionality too), and only return the HTML for display purposes.
3. Redundant Configuration in columnDefs
You've set orderable: true for targets: 2 in both columns (with the wrong property name) and columnDefs. While columnDefs has higher priority, keeping duplicate configurations can lead to confusion. It's best to keep your sorting configuration in one place for maintainability.
Fixed Code Example
Here's the corrected columns configuration for the problematic column, plus adjusted render logic:
columns: [ { title: `<input type="checkbox" class="styled" onchange='toggleSelectAll(this);'>`, orderable: false, data: "category_id", width: "50px" }, { data: "image", render: function (data, type, row) { return `<img src="${row['image']}" height="50px">`; }, width: "100px" }, { data: "name", orderable: true, // Fixed property name here render: function (data, type, row) { // Return raw data for sorting/filtering if (type === 'order' || type === 'filter') { return data; } // Return HTML for display return `<a href="{{ link('catalog/category/update?category_id=') }}${row['category_id']}">${row['name']}</a>`; } }, { data: "cstatus", width: "30px" }, { width: "30px", data: "category_id" }, { width: "10px", data: "category_id" }, ], columnDefs: [ { targets: 1, orderable: true }, // Removed redundant targets:2 line since we set orderable in columns now { orderable: false, className: 'select-checkbox', targets: 0 }, { targets: 3, render: function (data, type, row) { var status = (data == "1" ? 'checked="checked"' : ''); return statusSwitch(row.category_id, status); } }, { targets: 4, orderable: false, selectable: false, visible: true, render: function (data, type, row) { return `<a data-popup="tooltip" title="${locales['text_preview']}" target="_blank" href="{{ linkfront('product/category', 'path=') }}${row['category_id']}" class='text-default'><i class='fa fa-eye fa-lg valign-middle'></i></a>`; } }, { targets: 5, orderable: false, render: function (data, type, row) { return `<ul class="icons-list pull-right"> <li class="dropdown"> <a href="#" class="dropdown-toggle" data-toggle="dropdown"> <i class="icon-menu9"></i> </a> <ul class="dropdown-menu dropdown-menu-right"> <li><a href='{{ link('catalog/category/update') }}?category_id=${row['category_id']}'><i class='icon-pencil7'></i> ${locales['button_edit']}</a></li> <li><a onclick="removeItem(${row['category_id']})"><i class='icon-trash'></i> ${locales['button_delete']}</a></li> </ul> </li> </ul> `; } } ]
Key Takeaways
- Always use the correct DataTables property names: it's
orderable, notordering. - When using
render, handle thetypeparameter to ensure sorting/filtering uses raw data instead of rendered HTML. - Keep your configurations consistent to avoid confusion and redundant code.
内容的提问来源于stack exchange,提问作者Muhammad Fayez

