Simple Nodejs Web服务器总是发送文本/纯CSS和js文件
在Nodejs
中创建简单的Web服务器时,我遇到了一个奇怪的问题。 http服务器正常运行并接受像它应该的请求和响应。但是,由于某种原因,它总是希望发送content-type:
的text/plain
的一切。例如,.js
和.css
文件总是以text/plain
的形式出现,而它们通常应作为text/css
或application/javascript
发送。 Chrome浏览器,我使用的测试这个浏览器,总是抱怨MIME类型的资源:Simple Nodejs Web服务器总是发送文本/纯CSS和js文件
Resource interpreted as Stylesheet but transferred with MIME type text/plain: "http://localhost:3000/test.css".
Resource interpreted as Script but transferred with MIME type text/plain: "http://localhost:3000/test-client.js".
什么这最终意味着是css
永远不会应用到该页面。我添加了一些日志记录,看起来http响应正在发送正确的MIME类型。
我创建了一个我正在做的准系统版本。希望有人能指出我编写的缺陷:
test.js
var http = require('http'),
fs = require('fs'),
url = require('url'),
path = require('path');
var contentTypes = {
'.html': 'text/html',
'.css': "text/css",
'.js': 'application/javascript'
};
http.createServer(function(request, response) {
// get file based on pathname
var uri = url.parse(request.url).pathname,
filename = path.join(__dirname, uri);
fs.exists(filename, function(exists) {
// if root directory, append test.html
if (fs.statSync(filename).isDirectory()) {
filename += 'test.html';
}
// figure out MIME type by file ext
var contentType = contentTypes[path.extname(filename)];
fs.readFile(filename, function(err, file) {
// errors?
if (err) {
response.writeHead(404, {'Content-type:': 'text/plain'});
response.write(err + "\n");
response.end();
} else {
console.log('MIME TYPE for: ', filename , contentType);
response.setHeader('Content-Type:', contentType);
response.writeHead(200);
response.write(file);
response.end();
}
});
});
}).listen(3000, function(){
console.log("server started and listening on port 3000");
});
的test.html
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="test.css" type="text/css" />
</head>
<body>
<h1>Test</h1>
<div id="test"></div>
<script type="text/javascript" src="test-client.js"></script>
</body>
</html>
test.css
h1 {
color: red;
}
测试client.js
var div = document.getElementById('test');
div.innerHTML = 'test client ran successfully';
我认为这个问题是您正在设置头时,使用不必要的:
Content-Type
后。您应该做的response.setHeader('Content-Type',contentType);
或者,我认为这是更好的,这样做:response.writeHead(200,{'Content-Type':contentType});
w00t! **非常感谢!**这就是问题所在。 – xzela
而且你必须做出fs.readFile
通过封闭包裹,否则某些文件(特别是最后一个文件)将被读取一次以上,和其他人将不会被读取。并且contentType
将不会根据您的意愿进行设置。这是因为fs.readFile
使用的回调策略。当html文件只加载一个外部文件时,问题不会出现,但是当外部文件(css,js,png)加载多个文件时,它会按我上面指出的那样出现。 (我不能用我的Gmail登录,所以我张贴作为嘉宾)
所以,你的代码应该稍作改动如下:
;(function (filename, contentType) {
fs.readFile(filename, function(err, file) {
// do the left stuff here
});
}(filename, contentType));
设置标题时,你真的不这样做的权利。据我所知,你不应该使用'response.setHeader',而应该使用'response.writeHead(200,{'Content-Type':'contentType'});'并且在错误处理程序中为在'writeHead'上的选项你做了{Content-Type:','something-or/other'},但不应该在'Content-Type'后面加':'它应该是'Content-类型' – Markasoftware
感谢您想要将问题标记为已解决 - 但是,在堆栈溢出时,打勾很好':)'。 – halfer