gpt4 book ai didi

javascript - res.writehead 实际上是写到我的 html 页面的头部吗?

转载 作者:行者123 更新时间:2023-11-30 17:47:41 25 4
gpt4 key购买 nike

在我的 node.js 网页中,我正在制作类似于 Facebook 链接预览的页面预览。我正在调用以获取页面的 html,并使用它来创建预览。

$.ajax({
type: 'GET',
data: { "html": url },
url: "/htmlTest",
success: function (data) {
imgArray = [];
$('img', data).each(function () {
imgArray.push(this.src);
});
...

这是处理请求的服务器端代码。

app.get('/htmlTest', function (req, res) {
res.writeHead(200, { 'content-type': 'text/html' });
request(req.query.html, function (error, response, body) {
if (error) {
res.write(error.toString());
res.end('\n');
}
else if (response.statusCode == 200) {
res.write(body);
res.end('\n');
}
})
});

现在我注意到的是,它只会将其他页面使用的任何 css 插入到我的页面中,这真的会搞砸一切。为什么会这样?

此外,当我在做的时候,有没有人对 facebook 风格的页面预览有更好的想法?

最佳答案

没有。 writeHead 将 HTTP header 写入底层 TCP 流。它与 HTML 完全无关。

您遇到了问题,因为您的服务器返回所请求 URL 的批发 HTML 内容。然后将此字符串传递给 jQuery,这显然是将包含的 CSS 样式添加到您的文档中。

通常,从用户提供的 URL 中获取随机代码并在您的页面上下文中运行是一个糟糕的主意。它向您打开了巨大的安全漏洞 - 您看到的 CSS 工件就是一个例子。

坦率地说,您的代码有很多问题,请耐心等待我指出一些问题。

app.get('/htmlTest', function (req, res) {
res.writeHead(200, { 'content-type': 'text/html' });

在这里,您向浏览器响应成功状态 (200) beore 您的服务器实际上执行任何操作。这是不正确的:只有在知道请求成功或失败后,您才应该使用成功或错误代码进行响应。

        request(req.query.html, function (error, response, body) {
if (error) {
res.write(error.toString());
res.end('\n');
}

这里是用错误代码响应的好地方,因为我们知道请求确实失败了。 res.send(500, error) 就可以了。

            else if (response.statusCode == 200) {
res.write(body);
res.end('\n');
}

这里是我们可以使用成功代码进行响应的地方。不要使用 writeHead,而是使用 Express 的 setsend 方法——诸如 Content-Length 之类的东西将被正确设置:

res.set('Content-Type', 'text/html');
res.send(body);

现在如果 response.statusCode != 200 会发生什么?你不处理那个案子。 error 仅在网络错误的情况下设置(例如无法连接到目标服务器)。目标服务器仍然可以以非 200 状态响应,并且您的 Node 服务器永远不会响应浏览器。事实上,连接会挂起,直到用户终止它。这可以通过一个简单的 else res.end() 来解决。


即使解决了这些问题,我们仍然没有解决这样一个事实,即尝试在浏览器中解析任意 HTML 并不是一个好主意。

如果我是你,我会在服务器上使用将 HTML 解析为 DOM 的工具,然后只将必要的信息作为 JSON 返回给浏览器。 cheerio是您可能想要使用的模块——它看起来就像 jQuery,只是它在服务器上运行。

我会这样做:

var cheerio = require('cheerio'), url = require('url'), request = require('request');

app.get('/htmlTest', function(req, res) {
request(req.query.url, function(err, response, body) {
if (err) res.send(500, err); // network error, send a 500
else if (response.status != 200) res.send(500, { httpStatus: response.status }); // server returned a non-200, send a 500
else {
// WARNING! We should probably check that the response content-type is html
var $ = cheerio.load(body); // load the returned HTML into cheerio
var images = [];
$('img').each(function() {
// Image srcs can be relative.
// You probably need the absolute URL of the image, so we should resolve the src.
images.push(url.resolve(req.query.url, this.src));
});

res.send({ title: $('title').text(), images: images }); // send back JSON with the image URLs
}
});
});

然后从浏览器:

$.ajax({
url: '/htmlTest',
data: { url: url },
dataType: 'json',
success: function(data) {
// data.images has your image URLs
},
error: function() {
// something went wrong
}
});

关于javascript - res.writehead 实际上是写到我的 html 页面的头部吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19778791/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com