DataTable功能异常:$(...).DataTable is not a function问题求助
兄弟,我太懂这个坑了!SharePoint里的jQuery冲突简直是前端开发者的噩梦,尤其是母版页自带的jQuery和我们自己引入的版本打架,直接把DataTable搞罢工。你的问题核心就是重复加载jQuery导致命名空间冲突,DataTable绑定到了被覆盖/释放的jQuery对象上,所以才会出现功能失效的情况。下面给你几个针对性的解决方案:
一、先搞定jQuery的冲突问题
方案1:完全复用母版页的jQuery(推荐)
既然母版页已经包含jQuery,直接移除WebPart里的jQuery引用,避免重复加载。然后确保你的脚本加载顺序是:母版页jQuery → DataTable脚本 → 你的业务代码
修改后的引用部分:
<!-- 移除自己的jquery-3.4.0.min.js引用 --> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/popper.min.js"></script> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/bootstrap.min.js"></script> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/mdb-iefix.js"></script> <!-- DataTable必须在jQuery之后加载 --> <script type="text/javascript" src="/_catalogs/masterpage/V6/js/vendor/datatables.min.js"></script> <script type="text/javascript" src="/_catalogs/masterpage/V6/js/vendor/datatables-select.min.js"></script>
方案2:必须用自定义jQuery版本?用noConflict彻底隔离
如果你的MDB组件依赖特定版本的jQuery,那就得把自定义jQuery和母版页的jQuery彻底隔离开。关键是在自定义jQuery加载后立即调用noConflict,把自己的jQuery存为独立变量:
修改引用部分:
<!-- 先加载自定义jQuery --> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/jquery-3.4.0.min.js"></script> <script type="text/javascript"> // 接管jQuery命名空间,把母版页的jQuery存起来,自己的用$j(变量名随便取) var $j = $.noConflict(true); </script> <!-- 后续脚本会自动适配这个$j吗?MDB这类组件一般没问题,DataTable我们手动用$j初始化 --> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/popper.min.js"></script> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/bootstrap.min.js"></script> <script type="text/javascript" src="/Style%20Library/V7/js/vendor/mdb_update/js/mdb-iefix.js"></script> <script type="text/javascript" src="/_catalogs/masterpage/V6/js/vendor/datatables.min.js"></script> <script type="text/javascript" src="/_catalogs/masterpage/V6/js/vendor/datatables-select.min.js"></script>
然后把你的业务代码里所有的$替换成$j:
// 用$j代替$,彻底隔离母版页的jQuery var f1 = $j.ajax({ url: "/cyberSecurity/_api/web/lists/GetByTitle('cyberFeed')/items", method: 'GET', headers: { 'Accept': 'application/json; odata=verbose' }, success: function(data) { var items = data.d.results; console.log(items); var cyberFeed = $j('#cyberFeed'); var feedContent; for (var i = 0; i < items.length; i++) { feedContent = '<tr style="background-color: #003967; color: white;">' + '<th>' +'<h6 class="h6-responsive" style="padding-left: 5px; padding-top: 5px;margin-bottom: 4px; ">' +items[i].Title + '</h6>'+ '</th>' + '</tr>' + '<td style="background-color: white; padding-left: 19px; padding-top:10px;">' + items[i].Description + '</td>'; cyberFeed.append(feedContent); } // 表格渲染完成后立即初始化DataTable,不用等done initDataTable(); }, error: function(data) { console.log('Error: ' + data); } }); function initDataTable() { // 用$j初始化DataTable $j('#dtBasicExample').DataTable({ "pagingType": "numbers", "ordering": false, }); $j('.dataTables_length').addClass('bs-select'); }
二、额外的注意事项
确保表格DOM存在且渲染完成:
你代码里操作的是#cyberFeed,要确认这个是<table>标签的ID,而不是<tbody>。如果是tbody,初始化DataTable时要指向父级的<table>(比如$j('#cyberFeed').closest('table').DataTable(...))。用SharePoint的SOD确保脚本加载顺序:
如果母版页的脚本是延迟加载的,可以用SP.SOD.executeFunc来确保jQuery和DataTable都加载完成后再执行你的代码:// 确保母版页的jQuery加载完成 SP.SOD.executeFunc('jquery.js', 'jQuery', function() { // 确保DataTable脚本加载完成 SP.SOD.executeFunc('datatables.min.js', 'DataTable', function() { // 在这里执行你的ajax和DataTable初始化逻辑 var f1 = jQuery.ajax({...}); }); });检查DataTable脚本是否完整:
确认datatables.min.js包含了所有必要的模块(搜索、分页这些默认是包含的,但如果是自定义构建的版本可能会缺失)。
按上面的方法调整后,应该就能解决DataTable的功能失效问题了,祝你顺利!
内容的提问来源于stack exchange,提问作者DigiDev

