背景


做国外的项目经常会遇到时区转换的问题,这里简单针对遇到的时区问题做个记录,也希望对大家有所帮助,少走弯路。(本文设计开发语言为java)

时区的概念


先说下时区的概念 初中地理好的同学应该还记得,由于地球不停地自西向东旋转,使得昼夜半球和晨昏线也不断自东向西移动。

为了照顾到各地区的使用方便,又使其他地方的人容易将本地的时间换算到别的地方时间上去。有关国际会议决定将地球表面按经线从东到西,划成一个个区域(时区),全球一共分为24个时区(东12区+西12区),相邻时区时间相差1个小时。

规定英国(格林尼治天文台旧址)所在区域为零时区,往东分别为东1区、东2区……东11区、东12区,往西分别为西1区、西2区……西11区、西12区,东12区和西12区重合(所属同一个时区)。

我们国家由于地域广袤辽阔,横跨了5个时区(东5、东6、东7、东8、东9),但建国以后,全国统一采用首都北京所处的东8区的时间。

虽然全世界一共划分了24个时区,同一个时间点,每个时区钟表上显示的时间各不同,但是它们仅仅是同一时刻在不同地区展示的形式,它们代表的仍然是一个时刻/瞬间。

跑题结束,开始正文。

跨境电商下单场景涉及的时区转换


先以跨境电商系统中的下单场景举个栗子,如果该电商系统的【数据库服务器】部署在英国伦敦,【应用服务器】部署在德国柏林,北京时间2020-06-01 10:00:00 有位北京的用户在通过浏览器在该网站上买了一个儿童节礼物。

这个过程就涉及到了时区转换的问题,一般刚给电脑安装操作系统的时候,都会让选择电脑所在时区,系统就是以时区来显示时间的。上面下单的例子涉及到三个设备:客户端(电脑浏览器/手机App)、网站web服务器、网站数据库服务器,都配置了对应的时区,假设这三种设备配置的时区就是所在地区的时区。

在【客户端→web服务器】、【web服务器→数据库】、【数据库→web服务器】、【web服务器→客户端】这几个过程都涉及到了时区的转换。如果不考虑时区转换,北京的用户在2020-06-01 10:00:00下单,web服务器处理的时候认为订单时间是在2020-06-01 03:00:00,然后传给数据库的订单时间也是2020-06-01 03:00:00,数据库保存的时候会保存成2020-06-01 03:00:00。当北京的用户查询订单的时候,数据库返回给应用服务器的订单时间为2020-06-01 03:00:00,最后应用服务器返回给用户的订单时间(用户看到的时间)也就是2020-06-01 03:00:00,如下图:

但实际上对用户来说是在2020-06-01 10:00:00下的单,应该是这样:

要解决这个问题,可以通过在客户端和web服务器web服务器和数据库两两交互的时候添加”时区协议“来自动转换时区。

假如服务端应用是用SpringBoot实现的,可以在配置文件中配置
spring.jackson.time-zone = Asia/Shanghai(注意没有Asia/Beijing哈),这样应用服务器接收到客户端传来的时间后会把这个时间当成是东8区的时间转换成服务器所在时区的时间,也就是会把2020-06-01 10:00:00(UTC+8)转换成2020-06-01 03:00:00(UTC+1)。同样当客户端查询时,服务端会把当前时区的时间2020-06-01 03:00:00(UTC+1)转换成客户端所在时区的时间2020-06-01 10:00:00(UTC+8)。

假如服务端是用JDBC和MySQL交互,可以在MySQL连接中配置 serverTimezone=Europe/London,这样当应用服务器向Mysql发起持久化数据的请求时,会把服务器所在时区的时间2020-06-01 03:00:00(UTC+1)转换成数据库所在时区的时间2020-06-01 02:00:00(UTC)。同样当应用服务器查询数据的时候,会把数据库所在时区的时间2020-06-01 02:00:00(UTC)转换成服务器所在时区的时间2020-06-01 03:00:00(UTC+1)。

题外话


1、修改时区

一般浏览器的时区是默认获取的当前计算机系统的时区;应用服务器中获取的时区默认为当前计算机系统时区,可以在项目启动时设置(java -Duser.timezone=Asia/Shanghai -jar xxx.jar),也可以通过java.util.TimeZone动态设置;数据库时区默认也是取当前计算机系统时区,可以通过命令set global time_zone修改时区,可也以通过修改配置文件等其他方式。

2、Java中Date的时区无关性

Date类中有个fastTime变量,用来存储当前时刻的毫秒数。Date默认构造函数用System.currentTimeMillis()来为这个毫秒数赋值。

如果此刻在北京、柏林、伦敦同时执行如下语句:Date date = new Date();,那这三个date对象里存的毫秒数是相同的吗?答案是这3个Date里的毫秒数是完全一样的。

确切的说,Date对象里存的是自格林威治时间( GMT)1970年1月1日0点至Date对象所表示时刻所经过的毫秒数。所以,如果某一时刻遍布于世界各地的程序员同时执行new Date语句,这些Date对象所存的毫秒数是完全一样的。也就是说,Date里存放的毫秒数是与时区无关的。

客户端、服务器、数据库之间的时区转换相关推荐

  1. SQL不同服务器数据库之间的数据操作整理(完整版)(转)

    -- Blog   : http://blog.csdn.net/htl258(转载保留此信息) -- Subject: SQL不同服务器数据库之间数据操作整理 ------------------- ...

  2. 链接服务器,不同服务器数据库之间的数据操作。

    --********************************************************************************* -- 链接服务器,不同服务器数据 ...

  3. SQL不同服务器数据库之间的数据操作整理(完整版)

    --1. 创建链接服务器 --1.1 创建一个链接名 EXEC sp_addlinkedserver 'LinkName','','SQLOLEDB','远程服务器名或ip地址' --有自定义实例名还 ...

  4. mysql 不同服务器不同库之间的访问_不同服务器数据库之间的数据操作

    --创建链接服务器 exec sp_addlinkedserver 'ITSV ', ' ', 'SQLOLEDB ', '远程服务器名或ip地址 ' exec sp_addlinkedsrvlogi ...

  5. 不同服务器数据库之间的数据操作

    找到解决方法: 启用Ad Hoc Distributed Queries: exec sp_configure 'show advanced options',1 reconfigure exec s ...

  6. SQL对不同服务器数据库之间的数据操作

    创建链接服务器 exec sp_addlinkedserver 'ITSV' , ' ' , 'SQLOLEDB' , '192.168.0.237' --sql服务器ip地址exec sp_addl ...

  7. t3客户端连不上服务器数据库协议,t3客户端连接不到服务器6

    t3客户端连接不到服务器6 内容精选 换一换 介绍使用同一VPC内弹性云服务器ECS上的NodeJs Redis客户端连接Redis实例的方法.更多的客户端的使用方法请参考Redis客户端.本章节操作 ...

  8. 如何实现两个数据库之间的同步

    两台服务器分别架在两个不同的机房,要实现所有表中数据的同步,延时一两分钟没关系,数据库数据量很大,表大概有不到一百个吧,怎么实现同步?不同服务器数据库之间的数据操作--创建链接服务器 execsp_a ...

  9. 安卓系统怎么连接服务器数据库,安卓端如何与服务器端数据库连接

    安卓端如何与服务器端数据库连接 内容精选 换一换 本章节指导您使用MongoDB客户端,通过内网连接集群实例.通过MongoDB客户端连接实例的方式有普通连接和SSL连接两种,其中SSL连接通过了加密 ...

最新文章

  1. 激光雷达和毫米波雷达
  2. 吴恩达老师深度学习视频课笔记:序列模型和注意力机制
  3. 线上经验总结:一台 Java 服务器可以跑多少个线程?
  4. 测试Windows Live Writer对cnBlog的支持
  5. MySQL服务器意外关机-无法启动多实例
  6. pku2503 Babelfish(use bsearch)
  7. Linux下如何查看高CPU占用率线程 LINUX CPU利用率计算
  8. matlab中图例的字怎么改,matlab中legend函数在添加图例时的使用方法
  9. QQ第三方登陆-极简版
  10. 固态硬盘装win7系统怎么安装教程
  11. 2022年第十二届APMCM亚太地区数学建模竞赛1月加赛E题翻译以及思路
  12. jt808终端鉴权_JT/T808协议文档-道路运输车辆卫星定位系统北斗兼容车载终端通讯协议技术规范.pdf...
  13. cmake简洁教程 - 第五篇
  14. 为什么局域网IP通常以192.168开头而不是1.2或者193.169?
  15. 华为路由器isis配置实例_华为-ISIS路由协议(原理+配置实操)
  16. 数字平原CG场景搭建制作流程解析
  17. 【x与y的非线性关系】回归,自变量,自变量的平方项,自变量的二次项
  18. [译]网页移动端SEO权威指南
  19. Android学习笔记:Android基础知识点(不断更新中)
  20. 计算机专业英语简介模板,计算机专业英文简历模版

热门文章

  1. 用C++语言程序实现拉格朗日插值公式
  2. 財報中的HoH, YoY, MoM, QoQ是什麼意思?
  3. 商鼎云 | 你的数据管家
  4. 74ls161中rco是什么_74ls161引脚图与管脚功能表资料
  5. 基于java+jsp国外旅游网站设计与实现
  6. 支小蜜智慧食堂k12降低食堂成本,提升支付效率
  7. 工信部测算到2025年中国大数据产业规模将突破3万亿元
  8. 达内 盈深圳Java_深圳达内JAVA高级语言课程
  9. 江铖:乳腺癌识别By AI
  10. 【C语言 日历备忘录之彩蛋游戏】