Проблема с загрузкой, работающей как плагин jQuery

#javascript #jquery #twitter-bootstrap #es6-modules #laravel-mix

Вопрос:

Поэтому я работаю с приложением, которое интенсивно использует модалы. Недавно я сделал большое обновление на переднем конце; переход к скомпилированным ресурсам с помощью Laravel Mix, а также обновление начальной загрузки до версии 5. По большей части мы полагаемся на data-bs-* атрибуты, но есть несколько мест, где модальность запускается событием, и именно здесь у нас возникают проблемы.

В документации по начальной загрузке говорится:

Bootstrap 5 предназначен для использования без jQuery, но все еще возможно использовать наши компоненты с jQuery. Если Bootstrap обнаружит jQuery в window объекте, он добавит все наши компоненты в систему плагинов jQuery; это означает, что вы сможете $('[data-bs-toggle="tooltip"]').tooltip() включить всплывающие подсказки. То же самое касается и других наших компонентов.

Я подтвердил, что это работает должным образом в традиционной среде со сценариями, загруженными браузером:

 $("#foo").on("click", ()=>$("#exampleModal").modal("toggle")); 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/5.0.1/js/bootstrap.min.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/5.0.1/css/bootstrap.min.css"/>

<!-- Button trigger modal -->
<div class="container">
  <div class="row">
    <div class="col-6">
      <button id="foo" type="button" class="btn btn-primary">
        Launch demo modal
      </button>    
    </div>
  </div>
</div>

<!-- Modal -->
<div class="modal fade" id="exampleModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
  <div class="modal-dialog">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title" id="exampleModalLabel">Modal title</h5>
        <button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
      </div>
      <div class="modal-body">
        ...
      </div>
      <div class="modal-footer">
        <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
      </div>
    </div>
  </div>
</div> 

Тем не менее, я получаю старое доброе Uncaught TypeError: edit.first().modal is not a function из следующего кода. Я мог бы переписать, чтобы использовать новые статические методы, которые поставляются с JS начальной загрузки, но переписывание не требуется. Я уверен, что основная причина-глупая ошибка из-за моей неопытности во всем этом новом модуле ES6/импорте.

 window.$ = window.jQuery = require("jquery");
require("datatables.net");
require("datatables.net-bs4");
const pdfMake = require('pdfmake/build/pdfmake.js');
const pdfFonts = require('pdfmake/build/vfs_fonts.js');
pdfMake.vfs = pdfFonts.pdfMake.vfs;
window.sprintf = require("sprintf-js").sprintf;
window.echarts = require("echarts");
import moment from "moment";
window.moment = moment;
import * as bootstrap from "bootstrap";

$(function () {
    // does not work
    $("table.datatable tbody").on("dblclick", "tr", function() {
        const edit = $(".editModal");
        edit.first().modal("show");
    });
    // works, as documented
    $("table.datatable tbody").on("dblclick", "tr", function() {
        const edit = $(".editModal");
        const modal = new bootstrap.Modal(edit.get(0));
        modal.show();
    });

});
 

Ответ №1:

Я разобрался с этим, изменив свой JS, чтобы он выглядел так:

 window.$ = window.jQuery = require("jquery");
// get rid of this
// import * as bootstrap from "bootstrap";
// and do this instead
require("bootstrap");
require("datatables.net");
require("datatables.net-bs4");
require("bootstrap-3-typeahead");
const pdfMake = require('pdfmake/build/pdfmake.js');
const pdfFonts = require('pdfmake/build/vfs_fonts.js');
pdfMake.vfs = pdfFonts.pdfMake.vfs;
window.sprintf = require("sprintf-js").sprintf;
window.echarts = require("echarts");
import moment from "moment";
window.moment = moment;
 

Я не совсем понимаю разницу между import и require , но это исправило проблему, и единственным недостатком является то, что PhpStorm не хочет распознавать popover() метод в элементах jQuery.