[英]Including local JS and CSS files using Gatsbyjs
I am completely new to the gatsbyjs ecosystem, and at the same time I am learning a bit of reactjs .我是gatsbyjs生态系统的新手,同时我正在学习一些reactjs 。 I recently bought an html template and was trying to use it as a UI in a gatsbyjs application.
我最近买了一个 html 模板,并试图将其用作gatsbyjs应用程序中的 UI。 The template has many css and js, whether proprietary or costumized, which implies that there are no plugins in gatsbyjs to replace them.
模板有很多css和js,无论是私有的还是定制的,这意味着gatsbyjs中没有插件可以替代它们。 That said, the only option I have left is to add them directly as a link and scripts tags in the gatsbyjs application.
也就是说,我剩下的唯一选择是将它们直接添加为gatsbyjs应用程序中的链接和脚本标签。 Following some of the tutorials I saw that they suggest importing these files, the issue is that these files are not webpack friendly, resulting in multiple errors and the application does not compile.
按照我看到的一些教程,他们建议导入这些文件,问题是这些文件不是webpack友好的,导致多个错误并且应用程序无法编译。 Following this help page Gatsby Server Rendering APIs get to this code in the
gatsby-ssr.js
file:按照此帮助页面, Gatsby 服务器渲染 API会在
gatsby-ssr.js
文件中找到此代码:
const React = require("react")
exports.onRenderBody = ({ setBodyAttributes, setPostBodyComponents }) => {
setBodyAttributes({
"data-spy":"scroll",
"data-offset":"73",
"data-target":"#navbar-demos"
})
setPostBodyComponents([
<script
key="1"
type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.slim.js"
/>,
<script
key="2"
type="text/javascript"
src="./src/revolution/js/extensions/revolution.extension.actions.min.js"
/>,
])
}
the problem is this file revolution.extension.actions.min.js
is never exposed to the browser.问题是这个文件
revolution.extension.actions.min.js
永远不会暴露给浏览器。 when you open the Developer Tools appears to be there, but it definitely isn't:当您打开开发人员工具时,它似乎在那里,但它绝对不是:
What do I have to do to render those.js files correctly and the browser can see them?我需要做什么才能正确呈现 those.js 文件并且浏览器可以看到它们? That also applies for.css files
这也适用于 .css 文件
After a more extensive search, I found a couple of articles with a solution.经过更广泛的搜索,我找到了几篇提供解决方案的文章。 This was the first approach:
这是第一种方法:
import { withPrefix } from "gatsby"
import Helmet from "react-helmet"
const IndexPage = () => (
<div>
<Helmet>
<script src={withPrefix('revolution/js/extensions/revolution.extension.actions.min.js')} type="text/javascript" />
</Helmet>
</div>
)
export default IndexPage
This is the second approach using the gatsby-ssr.js
file:这是使用
gatsby-ssr.js
文件的第二种方法:
const React = require("react")
exports.onRenderBody = ({setPostBodyComponents}) => {
setPostBodyComponents([
<script key="1" src={'js/plugins/plugins.js'} type="text/javascript" />,
<script type="text/javascript" src={"js/beauty.custom.js"}/>
]);
};
this way the scripts tags will be added at the end of the body
instead of the head
这样脚本标签将被添加到
body
的末尾而不是head
I think the second one is the best one, but have to take in count that every time you change something in the gatsby-ssr.js
file have to stop the gatsby develop
and re-run it.我认为第二个是最好的,但必须考虑到每次更改
gatsby-ssr.js
文件中的gatsby-ssr.js
都必须停止gatsby develop
并重新运行它。
In the first case using react-helmet
will hot-reload.在第一种情况下,使用
react-helmet
会热重载。
NOTE : In both approaches, files have to be in the static
folder注意:在这两种方法中,文件都必须在
static
文件夹中
Here are the links to where I found this approach:以下是我找到此方法的链接:
How to include local javascript on a Gatsby page? 如何在 Gatsby 页面上包含本地 javascript?
How do you insert an external script using gatsby-browser?如何使用 gatsby-browser 插入外部脚本?
@ddieppa solution might not work if you demand your script must only be executed after the component/page is completely loaded , because:如果您要求脚本只能在组件/页面完全加载后执行, @ddieppa 解决方案可能不起作用,因为:
<head>
tag, no matter where you put it. <head>
标签内,无论你把它放在哪里。setPostBodyComponents
via ( gatsby-ssr.jsx/tsx
) will append your <script>
tag at the end of the body nicely, but watch out because your script file might actually executed before React completely finishes rendering your component. setPostBodyComponents
- 通过 ( gatsby-ssr.jsx/tsx
) setPostBodyComponents 将 append 你的<script>
标签很好地放在主体的末尾,但要小心,因为你的脚本文件可能会在 React 完全完成渲染你的组件之前实际执行。 If your js file is referring to any specific object in the component, you might end up seeing a bunch of null pointer exception, undefined exception. So if you want to make sure your script file get executed/loaded right after the component is completely rendered, you might need to use either React useEffect hook (if your React component is a functional component) orReact componentDidMount (if your component is a class component)因此,如果你想确保你的脚本文件在组件完全呈现后立即执行/加载,你可能需要使用React useEffect hook (如果你的 React 组件是功能组件)或React componentDidMount (如果你的组件是class 分量)
The idea will be simple, after the component is fully rendered, we will append a <script>
at the bottom of it.这个想法很简单,在组件完全渲染后,我们将 append 一个
<script>
放在它的底部。
(It's the same for componentDidMount) (对于 componentDidMount 也是一样的)
import React, { useEffect } from 'react'
const MyComponent = () => {
useEffect(() => {
const mainJsTag = document.createElement('script')
// given the js/main.js file is put in the static folder
mainJsTag.src = 'assets/js/main.js'
document.body.appendChild(mainJsTag)
console.log('Component Rendered!')
});
return (
<main>
<text>Pretty much the component's body here...</text>
</main>
)
}
export default MyComponent
(The snippet above assuming that you put your script file under the Gatsby static
folder, see Gatsby - Using the Static Folder in case you don't know about this concept in Gatsby) (上面的代码片段假设您将脚本文件放在 Gatsby
static
文件夹下,请参阅Gatsby - 使用 Static 文件夹以防您不知道 Gatsby 中的这个概念)
You can put a bunch of console.log
in both of your script file and in the useEffect/componentDidMount functions to confirm which one get executed first.您可以在脚本文件和 useEffect/componentDidMount 函数中放置一堆
console.log
以确认先执行哪个。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.