我在使用jQuery的Twig模板中有一些Javascript代码。脚本似乎是在jQuery之前加载的,所以它会抛出一个$ is not defined
错误。我不明白为什么它要在包含jQuery (用webpack-encore
编译)的主包之前加载。
JQuery是加载的,因为我可以从控制台引用它,或者将脚本包装在setTimeout
中,以强制以后加载它。
我有一个基本模板:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>
{% block title %}Welcome!
{% endblock %}
</title>
{% block stylesheets %}
{{ encore_entry_link_tags('app') }}
{% endblock %}
{% block javascripts %}
{{ encore_entry_script_tags('app') }}
{% endblock %}
</head>
<body>
{% block body %}{% endblock %}
</body>
</html>
页面模板:
{% extends 'base.html.twig' %}
{% block body %}
/// ...
<script>
$.change(/*...*/); // $ is not defined
</script>
{% endblock %}
webpack.config.js
const path = require('path');
const Encore = require('@symfony/webpack-encore');
if (!Encore.isRuntimeEnvironmentConfigured()) {
Encore.configureRuntimeEnvironment(process.env.NODE_ENV || 'dev');
}
Encore
.setOutputPath('public/build/')
.setPublicPath('/build')
.enableSassLoader()
.addEntry('app', './assets/app.js')
.enableStimulusBridge('./assets/controllers.json')
.splitEntryChunks()
.enableSingleRuntimeChunk()
.cleanupOutputBeforeBuild()
.enableBuildNotifications()
.enableSourceMaps(!Encore.isProduction())
.enableVersioning(Encore.isProduction())
.configureBabel((config) => {
config.plugins.push('@babel/plugin-proposal-class-properties');
})
.configureBabelPresetEnv((config) => {
config.useBuiltIns = 'usage';
config.corejs = 3;
})
.autoProvidejQuery()
;
module.exports = Encore.getWebpackConfig();
app.js
require('./styles/app.scss');
import $ from 'jquery';
global.$ = global.jQuery = $;
这是生成的HTML:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<link rel="stylesheet" href="/build/app.css">
<script src="/build/runtime.js" defer></script>
<script src="/build/app.js" defer></script>
</head>
<body>
<main class="col p-4 content flex-grow-1">
<!-- page content -->
<script>
// $ is not defined here
</script>
</main>
</body>
</html>
发布于 2021-04-16 09:39:50
从生成的HTML中发现了这些行中的问题:
<script src="/build/runtime.js" defer></script>
<script src="/build/app.js" defer></script>
defer
属性强制在页面呈现后加载定义jQuery的Javascript文件。因为我要在页面中添加内联Javascript,所以它是在app.js
之前加载的。
由于无法在HTML中添加延迟的内联Javascript,因此有两种选择:
config/packages/webpack_encore.yaml
中的
script_attributes:
defer: false
这将禁用所描述的行为。这个解决方案并不理想,因为在我的情况下,使用defer
是可取的。
encore_entry_script_tags
).
将Javascript文件保存在assets/
中,如果您有与问题中类似的基本模板,请按如下方式将其导入页面模板:
{% block javascripts %}
{{ parent() }}
{{ encore_entry_script_tags('your_file') }}
{% endblock %}
在webpack.config.js
中
Encore
//...
.addEntry('your_file','./assets/your_file.js');
发布于 2021-04-16 05:26:25
注意:您必须注意,您不能在节点程序中同时使用required和import,更倾向于使用required而不是import,因为您需要使用实验性模块标志功能来运行导入程序。
--https://www.geeksforgeeks.org/difference-between-node-js-require-and-es6-import-and-export/
上面的文章还提到,使用require
“您可以直接运行代码”,在本例中,代码定义了$
函数,因此您想要运行它。
我的项目如下,没有问题:
app.js:
require('./styles/app.scss');
const $ = require('jquery');
window.$ = $;
在webpack.config.js中注释以下一行:
//.autoProvidejQuery()
https://stackoverflow.com/questions/67117036
复制相似问题