Sequelize返回时区与服务器不一致的原因咨询
Sequelize查询时区与PostgreSQL不一致问题
我花费一整天排查Sequelize查询时间计算错误的原因后,在本地及服务器环境执行了如下代码:
const time = await db.Bar.sequelize.query("Select CURRENT_TIME") console.log("CURRENT_TIME: ", time); const time3 = await db.Bar.sequelize.query("Select now()") console.log("Time now: ", time3)
执行结果为:
CURRENT_TIME: [ [ { current_time: '15:00:45.709239+02' } ], .....
Time now: [ [ { now: 2023-12-06T13:00:45.711Z } ],...
而在本地及服务器的PostgreSQL pgAdmin4中执行select CURRENT_TIME和select now(),返回的是正确的GMT+1时区时间:
14:00:30.633552+01:00
服务器与本地均已设置为GMT+1时区,请问为何Sequelize会出现此类时区差异?
问题原因
- Sequelize连接时区配置缺失:尽管系统和数据库服务器时区设为GMT+1,但Sequelize不会自动继承系统时区,默认使用UTC时区,若连接时未指定与数据库匹配的时区参数,会导致数据库返回的时间被转换为错误的时区偏移。
now()返回值的类型转换:Sequelize处理PostgreSQL的now()结果时,会将其转为JavaScript的Date对象,而Date对象默认以UTC格式输出(带Z后缀),你看到的13:00是UTC时间,对应GMT+1的14:00,时间值本身正确,但显示格式为UTC。- pg驱动时区设置偏差:PostgreSQL的pg驱动若未指定时区,可能使用默认UTC或非系统时区的设置,导致
CURRENT_TIME返回的时区偏移错误。
解决方案
- 在Sequelize连接配置中指定时区:
初始化Sequelize实例时添加timezone配置,设置为与数据库一致的GMT+1时区:const sequelize = new Sequelize('database', 'username', 'password', { host: 'localhost', dialect: 'postgres', timezone: '+01:00', // 也可使用具体时区名如'Europe/Amsterdam' }); - 验证数据库时区设置:
在pgAdmin中执行SHOW TIMEZONE;,确认数据库时区为GMT+1对应的时区(如Europe/Paris),确保Sequelize配置的时区与数据库完全匹配。 - 手动格式化时间输出(可选):
若需要将now()结果转为GMT+1本地时间格式,可手动处理Date对象:const nowResult = await db.Bar.sequelize.query("Select now()"); const localTime = new Date(nowResult[0][0].now).toLocaleString('en-GB', { timeZone: 'Europe/Paris' }); console.log('Local time:', localTime);
内容的提问来源于stack exchange,提问作者BenoHiT
相关产品推荐
相关产品推荐

