使用Microsoft Graph PHP获取今日日历事件:误拉取昨日全天事件
这个问题的核心原因是你传递给Graph的查询参数没有指定时区,导致Graph默认将日期解析为UTC时间,而你需要的是纽约时区的当日范围,两者的时间差导致查询范围包含了前一天纽约时区全天事件的后半段(UTC时间的当日凌晨)。
问题分析
你创建的纽约时区5月17日全天事件,在Graph中对应的UTC时间范围是2018-05-17T04:00:00Z到2018-05-18T04:00:00Z(纽约时区为UTC-4)。当你传递startdatetime=2018-05-18时,Graph会默认解析为UTC时间2018-05-18T00:00:00Z,你的查询范围就变成了UTC的5月18日00:00到19日00:00。这个范围和前一天全天事件的UTC范围(17日04:00到18日04:00)存在重叠(18日00:00到04:00),所以Graph会返回这个事件。
解决方案
你需要在startdatetime和enddatetime参数中明确包含纽约时区的信息,让Graph按照你需要的时区解析查询范围,而非默认使用UTC。具体步骤如下:
- 构造纽约时区的当日0点和次日0点的
DateTime对象; - 将日期格式化为带时区的ISO 8601字符串(比如
2018-05-18T00:00:00-04:00); - 对参数进行URL编码,避免时区符号(如
-)导致请求错误; - 发起Graph请求。
修改后的代码
// 构造纽约时区的当日0点和次日0点 $today = new DateTime('now', new DateTimeZone('America/New_York')); $today->setTime(0, 0, 0); // 重置为当日0点0分0秒 $tomorrow = clone $today; $tomorrow->add(new DateInterval('P1D')); // 增加一天得到次日0点 // 格式化为带时区的ISO 8601字符串,并URL编码 $start_date = urlencode($today->format('c')); $end_date = urlencode($tomorrow->format('c')); // 发起Graph请求 $events = ms_get_data_as_json( "calendarview?startdatetime={$start_date}&enddatetime={$end_date}&\$orderby=start/DateTime" );
为什么之前的尝试无效?
你之前尝试使用UTC时间戳startdatetime=2018-05-18T00:00:01Z&enddatetime=2018-05-18T23:59:59Z,这个范围对应的纽约时间是5月17日20:00到5月18日19:59,依然会包含前一天纽约时区全天事件的后半段(纽约时间17日20:00到24:00),所以还是会返回该事件。只有明确指定纽约时区的查询范围,才能精准拉取你需要的当日事件。
内容的提问来源于stack exchange,提问作者idealbrandon

