You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

酒店预订网站new Date()跨时区日期显示错误问题排查

解决跨时区酒店预订日期显示错误问题

问题背景

运营印度酒店预订网站时,IST时区用户选择日期后显示正常,但非IST时区(如美国东部夏令时EST)用户从日历选择日期后,new Date(props.checkin)会将正确日期自动转为前一天。例如选择2024年9月7日,转成Date对象后变成2024年9月6日,仅在非IST时区出现该问题。

问题原因

props.checkin是带IST时区的字符串(示例:Sat Sep 07 2024 00:00:00 GMT+0530 (India Standard Time)),当在非IST时区环境下用new Date()解析时,会自动将其转换为本地时区时间。由于EST比IST晚10.5小时,IST的9月7日00:00对应EST的9月6日13:30,此时仅取日期部分就会显示为前一天,导致错误。

解决方案

核心思路是剥离时区影响,确保日期值在任意时区解析后都保持正确的年月日,以下是具体实现方案:

方案1:构造UTC日期对象

提取原日期的年、月、日信息,创建UTC时区的0点日期,避免本地时区偏移:

// 辅助函数:将带时区的日期字符串转为UTC日期
const getUTCDate = (dateString) => {
  const rawDate = new Date(dateString);
  // 提取原日期的年、月、日,构造UTC 0点时间
  return new Date(Date.UTC(rawDate.getFullYear(), rawDate.getMonth(), rawDate.getDate()));
};

方案2:直接解析日期字符串(无时区依赖)

从原日期字符串中提取年、月、日,直接构造本地日期:

// 辅助函数:从日期字符串中提取年月日,忽略时区
const parseDate = (dateString) => {
  // 匹配格式中的月、日、年
  const matchResult = dateString.match(/(\w{3}) (\d{2}) (\d{4})/);
  if (!matchResult) return new Date();
  
  const [, monthStr, day, year] = matchResult;
  const monthIndex = ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"].indexOf(monthStr);
  // 构造本地时区的0点日期
  return new Date(year, monthIndex, day);
};

修改后的代码示例

将上述辅助函数应用到你的useEffect中:

useEffect(() => {
  console.log("props.checkin>>>>", new Date(props.checkin));
  
  // 使用方案1的UTC日期处理
  const checkInDate = getUTCDate(props.checkin);
  const checkOutDate = getUTCDate(props.checkout);

  dispatch(
    updateBookingDateRange({
      checkInDate,
      checkOutDate,
      searchedRoomCount: Number(props.num_rooms),
      searchAdultCount: Number(props.num_adults),
      searchedChildrenCount: Number(props.num_children),
      searchGuestCount: Number(props.num_guests),
    }),
  );

  if (
    totalRoomCount === 0 &&
    props.planStatus &&
    router.query.roomId &&
    router.query.planId
  ) {
    dispatch(
      addFirstRoom({
        roomInfo: props.roomDetails,
        planInfo: props.planDetails,
        roomCount: props.num_rooms,
        guestCount: Number(props.num_guests),
        adultCount: Number(props.num_adults),
        childCount: Number(props.num_children),
      }),
    );
  }
}, [
  router.query.hotelInfo,
  router.query.checkin,
  router.query.checkout,
  router.query.num_guests,
  router.query.num_children,
  router.query.num_rooms,
]);

额外注意:日期显示时的时区处理

如果前端需要展示日期,建议指定IST时区格式化,确保所有用户看到一致的日期:

// 以印度时区格式显示日期
checkInDate.toLocaleDateString('en-IN', { timeZone: 'Asia/Kolkata' });

内容的提问来源于stack exchange,提问作者Rishabh Sharma

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 15:07:27