使用Express和Node.js连接SQL Server时遇到连接问题
我用Node.js结合Express框架连接SQL Server数据库,已经解决了IIS相关问题,但当前出现连接失败的情况。
代码示例
const express = require('express'); const app = express(); const mssql = require("mssql"); // Get request app.get('/', function (req, res) { // Config your database credential const config = { user: 'sa', password: '12345678', server: 'localhost', database: 'student' }; // Connect to your database mssql.connect(config, function (err) { // Create Request object to perform // query operation let request = new mssql.Request(); // Query to the database and get the records request.query('select * from dbo.student', function (err, records) { if (err) console.log(err) // Send records as a response // to browser res.send(records); }); }); }); let server = app.listen(5000, function () { console.log('Server is listening at port 5000...'); });
错误信息
RequestError: No connection is specified for that request.
at Request._query (C:\Users\canbe\OneDrive\Masaüstü\deneme123\node_modules\mssql\lib\base\request.js:493:37)
at Request._query (C:\Users\canbe\OneDrive\Masaüstü\deneme123\node_modules\mssql\lib\tedious\request.js:363:11)
at Request.query (C:\Users\canbe\OneDrive\Masaüstü\deneme123\node_modules\mssql\lib\base\request.js:429:12)
at C:\Users\canbe\OneDrive\Masaüstü\deneme123\index.js:24:17)
at Immediate. (C:\Users\canbe\OneDrive\Masaüstü\deneme123\node_modules\mssql\lib\global-connection.js:56:7)
at process.processImmediate (node:internal/timers:480:21) {
code: 'ENOCONN'
}
问题原因及解决办法
这个错误核心是创建Request时未绑定有效数据库连接,且原代码未处理连接失败场景,导致后续操作基于无效连接执行。
1. 修复回调写法代码
先捕获连接错误,再基于成功连接实例创建Request:
const express = require('express'); const app = express(); const mssql = require("mssql"); app.get('/', function (req, res) { const config = { user: 'sa', password: '12345678', server: 'localhost', database: 'student' }; mssql.connect(config, function (err) { // 优先处理连接错误 if (err) { console.error('数据库连接失败:', err); res.status(500).send('数据库连接失败'); return; } // 基于当前有效连接创建Request let request = new mssql.Request(mssql.getConnection()); request.query('select * from dbo.student', function (err, records) { if (err) { console.error('查询失败:', err); res.status(500).send('查询失败'); return; } res.send(records); // 可选:查询完成后关闭连接 mssql.close(); }); }); }); let server = app.listen(5000, function () { console.log('Server is listening at port 5000...'); });
2. 推荐使用Async-Await + 连接池(更稳定)
mssql官方推荐用连接池管理连接,结合async-await可避免回调地狱,代码更易维护:
const express = require('express'); const app = express(); const mssql = require("mssql"); app.get('/', async function (req, res) { const config = { user: 'sa', password: '12345678', server: 'localhost', database: 'student', options: { encrypt: false // 本地SQL Server需关闭加密,否则可能连接失败 } }; let pool; try { // 创建连接池(复用连接更高效) pool = await mssql.connect(config); // 基于连接池创建Request并执行查询 const result = await pool.request().query('select * from dbo.student'); // 返回查询结果的数据集 res.send(result.recordset); } catch (err) { console.error('数据库操作失败:', err); res.status(500).send('数据库操作失败'); } finally { // 确保连接池关闭,避免资源泄漏 if (pool) await pool.close(); } }); let server = app.listen(5000, function () { console.log('Server is listening at port 5000...'); });
3. 额外排查点
- 确认SQL Server服务已启动,用SSMS以相同账号密码登录验证连接有效性
- 检查SQL Server的TCP/IP协议是否启用(在SQL Server配置管理器的「SQL Server网络配置」中开启)
- 确保
sa账号已启用,且拥有student数据库的查询权限 - 若为远程SQL Server,需确认防火墙开放1433端口,且服务器允许远程连接
内容的提问来源于stack exchange,提问作者Canberk Ekinci

