【问题标题】:Why there exist error Uncaught ReferenceError: $ is not defined if add async?为什么存在错误 Uncaught ReferenceError: $ is not defined if add async?
【发布时间】:2020-01-17 19:29:56
【问题描述】:

我的索引是这样的:

...
<html >

<head>
    ...
    <script src="/scripts/myapp.min.js"></script>
    <script src="/scripts/myapp-themming.min.js"></script>

</head>

<body class="header-static">
    <div class="page-container">
        <!-- this is call header, navigaton, content, footer -->
    </div>

    <script type="text/javascript" src="https://code.jquery.com/jquery-3.2.1.min.js"></script>
    <script type="text/javascript" src="/Content/assets/script/jquery-ui.min.js"></script>
    ...

    <script type="text/javascript">
        ...
    </script>
    <script>
        $(document).ready(function () {
            ...
        });
    </script>
</body>

</html>

如果我使用 gtmetrix 测试页面速度。和 gtmetrix 推荐延迟解析 JavaScript。所以我尝试像这样添加async

<script src="/scripts/myapp.min.js" async></script>
<script src="/scripts/myapp-themming.min.js" async></script>

它显示以下错误,

未捕获的引用错误:$ 未定义

如果我使用 defer,它会产生 3 个这样的错误:Uncaught ReferenceError: $ is not definedUncaught TypeError: $(...).material_select is not a functionUncaught TypeError: $(...).select2 is not a function

我该如何解决这个错误?

【问题讨论】:

  • 看起来你在加载 jQuery 之前加载了你的 javascript - 如果你在 javascript 中使用 jQuery,你需要在加载 jquery 之后加载你的 javascript - 这就像在你上车之前尝试开车跨度>
  • @Jaromanda X 当我添加异步或延迟时会发生此错误。如果我不使用它,没有错误
  • @Jaromanda X 如果我在 jquery 脚本下移动标签脚本,它是一样的。还是有错误
  • 如果包含依赖脚本B的脚本A,则需要确保脚本A运行时脚本B已满载。 async 与此相反。 javascript.info/script-async-defer
  • 问题是 $() 在 jquery 准备好之前运行。这就是 async 的用途,以防止脚本在并行下载时阻塞页面。这是您可以load and use jquery asynchronously的方法。

标签: javascript jquery asynchronous optimization pagespeed


【解决方案1】:

首先将&lt;body&gt; 中的两个脚本移动到顶部的&lt;head&gt; 部分(在您添加的3 个点上方)。这就是@Nijin Koderi 的意思。

重要的是要确保 jQuery 高于一切,所以它首先被加载。

其次 - 你不能像the other answer I gave 中提到的那样只使用async,因为你最终会遇到竞争条件。

async 错误较少的原因纯粹是资源的加载速度,您会发现加载足够多的情况下,您会收到不同的错误,具体取决于哪些脚本下载速度最快。

在你学习这个时使用defer 会容易得多(事实上我几乎总是使用 defer,除非你正在加载兆字节的 JS 或者你的网站需要在几毫秒内运行 JS)

引用我给出的答案

[延迟解析 JavaScript] 最简单的方法是添加 defer 每个 JavaScript 请求的属性。

为了获得更好的性能(困难),我建议使用异步 而是因为这将更快开始下载并激活每个脚本 只要它可用。

但是,这通常会导致脚本出现“竞争条件”问题 可能会乱序加载(即,如果您使用 jQuery 和另一个脚本 在需要 jQuery 之前加载,你会得到一个错误)。

先试试 defer,如果性能好就使用它。

【讨论】:

    【解决方案2】:

    如上所述,您有两个错误,Uncaught ReferenceError: $ is not defined, Uncaught TypeError: $(...).material_select is not a function, and Uncaught TypeError: $(...).select2 is not a function

    第一个问题可以通过在任何其他js之前添加以下js文件来解决,如下所示

    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js">
    ...
    <script src="/scripts/myapp.min.js"></script>
    <script src="/scripts/myapp-themming.min.js"></script>
    

    下一个错误是针对select2。为了解决这个问题,在jquery.min.js之后添加如下样式表和js文件

    <link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.10/css/select2.min.css" rel="stylesheet" />
    
    <script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.10/js/select2.min.js">
    

    【讨论】:

    • 请不要在你的答案中使用“text-speak”。而不是你有两个错误...,应该是你有两个错误...
    猜你喜欢
    • 1970-01-01
    • 2015-12-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-08
    • 1970-01-01
    • 2017-10-25
    • 2019-01-22
    相关资源
    最近更新 更多