Tau*_*ren 5 java timezone datetime hibernate jodatime
我的Java应用程序需要每天向所有用户发送一次电子邮件.我想在大约凌晨2点根据每个用户的当地时间提供.因此,纽约的用户将在2AM America/New_York时间收到消息.洛杉矶的用户将在2AM America/Los_Angeles时间收到消息.我的邮件流程每天都会运行一次.
我计划使用HTML5地理位置功能或IP地址定位来在注册期间自动确定每个用户的时区.当然,如果这些值不正确,用户可以手动修改时区.我打算将选定的时区存储在User对象中作为时区ID字符串,例如"America/New_York".这将作为字符串持久保存到数据库,但如有必要,可以更改.
需要考虑的事项:
我正在使用Spring Scheduling cron功能(通过Quartz)在当天每小时2分钟运行一个方法.现在我的大多数用户都在America/Los_Angeles,所以我手动强制所有邮件都在太平洋时间凌晨2:02发送.以下方法每小时运行一次:02小时,但它会手动检查时间,并且仅在洛杉矶当前时间为2:00小时时才会进行.这意味着其他地方的用户将在凌晨2点以外的时间收到电子邮件.
@Scheduled(cron="0 2 * * * *")
public void sendDailyReportEmail()  {
    DateTime now = new DateTime(DateTimeZone.forID("America/Los_Angeles"));
    if (now.getHourOfDay() != 2) {
        log.info("Not 2AM pacific, so skipping email reports");
        return;
    }
    // send email reports
}
因此,我需要的是执行一个数据库查询,该查询将根据用户对象中的时区为我提供在凌晨2:00时有本地时间的所有用户.有关如何实现这一点的任何想法?
我对此进行了更多思考并找到了可能的解决方案。我还没有实现它,但我认为它应该有效。基本上,它涉及执行以下查询(注意:这是 MySQL 特定的):
select * from members where hour(convert_tz(now(),'UTC',timezone)) = 3;
此查询通过执行以下操作来选择当前当地时间在凌晨 3 点到凌晨 3:59 之间的所有成员:
now(),这是 UTC 时间,因为数据库服务器配置为 UTC 时间。convert_tz()中指定的成员时区。timezone请注意,Member 类包含格式为“America/Los_Angeles”的时区字段。hour(),看看它是否为3, 3AM。我有点担心每小时为系统中的每个成员进行时区转换和计算。我必须进行一些测试,看看它会给数据库带来什么样的负载,但它可能会因为数百万甚至上万的用户而窒息。
另一种可以显着减轻负载但不太优雅的方法是执行以下操作(注意此代码未经测试!):
@Scheduled(cron="0 2 * * * *")
public void sendDailyReportEmail()  {
    Query query = session.createQuery(
        "select distinct m.timezone from Member m");
    List<String> timezones = query.list();
    for (String timezone : timezones) {
        DateTime now = new DateTime(DateTimeZone.forID(timezone));
        if (now.getHourOfDay() == 3) {
            Query query2 = session.createQuery(
                "from Member where timezone = :zone");
            query2.setParameter("zone", timezone);
            List<Member> members = query2.list();
            // send email reports
        }
    }
}
这段代码执行以下操作:
这会在每小时开始时增加一点额外的开销,但不需要每个用户的时区处理。系统实际使用的唯一时区很可能只有几十个。我不太可能在所有 500 多个时区都拥有会员。
最后一件事。我没有在凌晨 2 点发送电子邮件,而是将其移至凌晨 3 点。这是因为当春季夏令时发生变化时,时间会从凌晨 2 点变为凌晨 3 点。因此,不存在“凌晨 2:02”这样的事情,这意味着当天不会发送电子邮件。此外,在秋季,系统可以向每个用户发送 2 封电子邮件,因为一小时会重复。我需要查明非美国时区是否在不同时间更改时间,因为凌晨 3 点可能在其他地方出现问题。
| 归档时间: | 
 | 
| 查看次数: | 2166 次 | 
| 最近记录: |