如何在 NodeJS-App 中设置 Js 文件的内容类型

问题描述 投票:0回答:2

我在我的 NodeJS 服务器上打开 js 文件时遇到问题,因为它总是指定我的 .js 文件的 Content-Type 为“text/html”。

目标是将用户输入从 html 表单发送到 JavaScript 文件以进行一些计算,然后从中创建图形。

在我的 app.js(节点服务器)上我有:

const http = require('http');
const fs = require('fs');
const port = 3000;
const server = http.createServer(function(req, res) {
res.writeHead(200, { 'Content-Type': 'text/html' })
fs.readFile('index.html', function(error, data) {
        if (error) {
            res.writeHead(404)
            res.write('Error: File Not Found')
        } else {
            res.write(data)
        }
        res.end()
    })
})

这将正确打开我的 html 文件。这是一个如下的输入形式:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <script type="module" src="./js/index.js"></script> 
    <title>Node-App</title>
</head>
<body>
    Enter Name and Birthdate:<br><br>
    <form action="#" method="post" id="frm">
        <label for="Name">Name:</label><br>
        <input type="text" id="nam"><br>

        <label for="Date">Date:</label><br> 
        <input type="text" id="dat"><br>

        <input type="button" onclick="userInput()" value="Plot">
    </form>

但是现在我想通过单击一个按钮从这里打开一个 js 函数,这给了我错误“userInput is not defnied”。
不足为奇,因为加载页面已经抛出错误“从“www/js/index.js”加载模块被禁用的 MIME 类型(文本/html)阻止”

我的 JS 文件看起来像这样,但无论如何都没有正确加载:

function userInput() {
    console.log("Test The Function");
}

我可以在“网络分析”中看到,在 .js 文件的 http-header 中,它的 Content-Type 是“text/html”,所以我的问题是我该如何改变它?

我已经尝试了几种方法,例如通过键入

res.writeHead(200, { 'Content-Type': ['text/html', application/javascript] }) 
res.setHeader("Content-Type": "application/javascript");
在我的 app.js 中设置它,但它要么不再加载 html,要么什么都不做。

我还尝试将我的 index.html 中的 Content-Type 设置为像

<script type="application/javascript" src="./js/index.js"></script> 
这样的脚本标签,但它也没有任何改变。

感谢您的帮助!

javascript html node.js mime-types nodejs-server
2个回答
2
投票

默认情况下,当您向浏览器提供 html 页面时,它会分析您的文档,如果找到指向 css 或 javascript 的链接,它会向保存这些资产的服务器发出 HTTP 请求。

当你通过 devTools 打开浏览器控制台时,你可能会注意到你有一条错误消息告诉你无法获取请求的资源(你的 javascript 文件的名称),或者你的页面无限加载而不返回回应。

由此我们可以理解一个非常简单的事情,那就是您必须管理存储在服务器中的资源的路由。

例如,浏览器将使用 GET 方法和 url http://localhost:3000/script.js 查询您的服务器,之后您的服务器必须为其提供此资产。

这里有一个例子来说明这一点:

想象一个文件结构包含:

  • 一个公共文件夹,它本身包含一个“assets”文件夹和一个“html”文件夹。

  • 包含服务器逻辑的 server.js 文件。

此 html 文件夹将包含要提供的 html 文件。

资产文件夹将包含“script.js”和“styles.css”文件。

"use strict";

const http = require("http");
const fs = require("fs");
const os = require("os");
const path = require("path");

const host = "localhost";
const port = 3000;

const server = http.createServer((req, res) => {
    if (req.method === "GET") {
        if (req.url === "/") {
            const readStream = fs.createReadStream(path.join(process.cwd(), "public", "html", "index.html"));
            res.writeHead(200, {
                "Content-Type": "text/html",
            });
            readStream.pipe(res);
        }
        if (req.url === "/styles.css") {
            const readStream = fs.createReadStream(path.join(process.cwd(), "public", "assets", "styles.css"));
            res.writeHead(200, {
                "Content-Type": "text/css",
            });
            readStream.pipe(res);
        }
        if (req.url === "/script.js") {
            const readStream = fs.createReadStream(path.join(process.cwd(), "public", "assets", "script.js"));
            res.writeHead(200, {
                "Content-Type": "text/html",
            });
            readStream.pipe(res);
        }
    }

});

server.on("listening", () => {
    console.log(`Server running on http://${host}:${port}`);
})

server.listen(port);

process.on("SIGINT", () => {
    console.log(`${os.EOL}Server interrupted by 'SIGINT'`);
    process.exit(1);
});
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Node-App</title>
    <link rel="stylesheet" href="styles.css">
</head>
<body>
    Enter Name and Birthdate:<br><br>
    <form action="#" method="post" id="frm">
        <label for="Name">Name:</label><br>
        <input type="text" id="nam"><br>

        <label for="Date">Date:</label><br> 
        <input type="text" id="dat"><br>

        <input type="button" onclick="userInput()" value="Plot">
    </form>
    <script src="script.js"></script>
</body>

在此示例中,我使用“fs”模块中的 createReadStream() 来提高性能,我强烈建议您在提供静态文件时使用它。

现在,当浏览器向您的服务器发出一个或多个请求时,涉及我示例中的“script.js”或“styles.css”等资产,您的服务器将为它提供请求的文件。

希望这有帮助,祝你好运!


0
投票

所以有了 express 模块就可以这样解决,app.js:

const path = require("path");
const express = require("express");
const app = express();

app.get("/", function(req, res){    
    res.sendFile(path.join(__dirname, 'html', 'index.html'));
});
app.get("/assets/main.js", function(req, res){
    res.setHeader('Content-Type', 'text/javascript');
    res.sendFile(path.join(__dirname, 'assets', 'main.js'));
});
app.post("/data", function(req, res) {
    res.sendFile(path.join(__dirname, 'html', 'file.html'));    
});
const port = 8080;
app.listen(port, function(){
    console.log("Server is running");
});

index.html:

<form action="/data" method="POST" id="frm">
    some input fields
    <button type="submit" id="btn">Send data to backend</button>
</form>
© www.soinside.com 2019 - 2024. All rights reserved.