http 服务器响应异步函数的输出
http server respnd with an output from an async function
我希望我的 HTTP 响应脚本响应来自我的 SQL 服务器的数据。因此,我可以使用 AJAX 使用来自我的 SQL 服务器的数据更新 HTML。我找不到办法做到这一点。我只是在学习异步,我有一种感觉,如果我可以将我的异步函数的输出保存到一个全局变量中,那么它就可以工作了。任何帮助都会减轻我的头痛。
我的简单监听脚本是:
var test = "hello!"
var http = require('http');
http.createServer(function (req, res) {
res.writeHead(200, {'Content-Type': 'text/plain'});
res.write(test);
res.end();
}).listen(8080);
我的 sql 代码是:
const util = require('util');
var mysql = require('mysql');
var con = mysql.createConnection({
host: "XXXXX",
user: "XXXXX",
password: "XXXXX",
database: "XXX"
});
var DBresult=null;
function getdb(){
const query = util.promisify(con.query).bind(con);
(async () => {
try {
const rows = await query('SELECT * FROM mylist');
DBresult=rows;
} finally {
con.end();
}
})()
}
不要对服务器中的异步结果使用任何全局变量或共享的、更高范围的变量。永远不要那样做。这是一种有充分理由的反模式,因为这会产生间歇性的并发问题,因为在您的服务器上可以同时处理多个请求,因此这些会导致对这些变量的访问冲突,从而产生间歇性的、非常难以处理的问题-调试问题。我再说一遍,从不。
您没有描述您正在尝试为其编写代码的确切情况,但这里有一个示例。
相反,您在异步调用到达的上下文中使用结果。如果可以使用 await
,通常会使编码更清晰。
这是一个简单的例子:
const con = mysql.createConnection({
host: "XXXXX",
user: "XXXXX",
password: "XXXXX",
database: "XXX"
});
const query = util.promisify(con.query).bind(con);
http.createServer(async function(req, res) {
if (req.path === "/query" && req.method === "GET") {
try {
const rows = await query('SELECT * FROM mylist');
res.writeHead(200, { 'Content-Type': 'application/json' });
res.end(JSON.stringify(rows));
} catch(e) {
console.log(e);
res.statusCode = 500;
res.end();
}
} else {
// some other respone
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.write("hello");
res.end();
}
}).listen(8080);
这里需要注意的事项:
- 在处理请求之前检查路径和方法。
- 制作回调函数
async
以便它可以使用await
。
- 确保
await
的任何 promise 拒绝都被 try/catch
捕获,并在出现错误时发送错误响应。
- 将结果发送为 JSON 并设置适当的内容类型。
- 您可能会将普通的
http
模块用作学习经验,但您很快就会发现使用简单的 Express framework 会节省您大量的编程时间并使事情变得容易得多。
我希望我的 HTTP 响应脚本响应来自我的 SQL 服务器的数据。因此,我可以使用 AJAX 使用来自我的 SQL 服务器的数据更新 HTML。我找不到办法做到这一点。我只是在学习异步,我有一种感觉,如果我可以将我的异步函数的输出保存到一个全局变量中,那么它就可以工作了。任何帮助都会减轻我的头痛。
我的简单监听脚本是:
var test = "hello!"
var http = require('http');
http.createServer(function (req, res) {
res.writeHead(200, {'Content-Type': 'text/plain'});
res.write(test);
res.end();
}).listen(8080);
我的 sql 代码是:
const util = require('util');
var mysql = require('mysql');
var con = mysql.createConnection({
host: "XXXXX",
user: "XXXXX",
password: "XXXXX",
database: "XXX"
});
var DBresult=null;
function getdb(){
const query = util.promisify(con.query).bind(con);
(async () => {
try {
const rows = await query('SELECT * FROM mylist');
DBresult=rows;
} finally {
con.end();
}
})()
}
不要对服务器中的异步结果使用任何全局变量或共享的、更高范围的变量。永远不要那样做。这是一种有充分理由的反模式,因为这会产生间歇性的并发问题,因为在您的服务器上可以同时处理多个请求,因此这些会导致对这些变量的访问冲突,从而产生间歇性的、非常难以处理的问题-调试问题。我再说一遍,从不。
您没有描述您正在尝试为其编写代码的确切情况,但这里有一个示例。
相反,您在异步调用到达的上下文中使用结果。如果可以使用 await
,通常会使编码更清晰。
这是一个简单的例子:
const con = mysql.createConnection({
host: "XXXXX",
user: "XXXXX",
password: "XXXXX",
database: "XXX"
});
const query = util.promisify(con.query).bind(con);
http.createServer(async function(req, res) {
if (req.path === "/query" && req.method === "GET") {
try {
const rows = await query('SELECT * FROM mylist');
res.writeHead(200, { 'Content-Type': 'application/json' });
res.end(JSON.stringify(rows));
} catch(e) {
console.log(e);
res.statusCode = 500;
res.end();
}
} else {
// some other respone
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.write("hello");
res.end();
}
}).listen(8080);
这里需要注意的事项:
- 在处理请求之前检查路径和方法。
- 制作回调函数
async
以便它可以使用await
。 - 确保
await
的任何 promise 拒绝都被try/catch
捕获,并在出现错误时发送错误响应。 - 将结果发送为 JSON 并设置适当的内容类型。
- 您可能会将普通的
http
模块用作学习经验,但您很快就会发现使用简单的 Express framework 会节省您大量的编程时间并使事情变得容易得多。