许多新手开发人员在处理时区时感到困惑。

  • 如何将它们存储在数据库中
  • 如何在Go中解析它们

当将时区存储在数据库中时,请始终遵循一个标准时区,理想的做法是保存UTC时间,并在显示时区时根据需要将其转化为各种时区。

以MYSQL作为存储时间的示例

以下解决方案与DB无关。根据MySQL文档,有两种可以在MySQL存储时间的方法。

  • DATETIME--DATETIME类型用于包含日期和时间部分的值。MYSQL检索DATETIME并以'YYYY-MM-DD hh:mm:ss'格式显示值。支持的范围是'1000-01-01 00:00:00''9999-12-31 23:59:59'
  • TIMESTAMP-TIMESTAMP数据类型用于同时包含日期和时间部分的值。UTC TIMESTAMP的范围是UTC。'1970-01-01 00:00:01''2038-01-19 03:14:07'。

在本文中,我将使用DATETIME为例。

现在,另一个也是最重要的事情是读取并将其转化为其他时区。

Go时间时区的转换

下面的代码是展示我们如何在Go语言中做时区的转换. 首先让我们来定义地区和时区的的字典. 时区列表IANA时区标识可以从这里得到Time Zones,

package main

import (
"fmt"
"errors"
"time"
) type Country string const (
Germany Country = "Germany"
UnitedStates Country = "United States"
China Country = "China" ) // timeZoneID 是国家=>IANA 标准时区标识符 的键值对字典
var timeZoneID = map[Country]string{
Germany: "Europe/Berlin",
UnitedStates: "America/Los_Angeles",
China: "Asia/Shanghai",
} //获取 IANA 时区标识符
func (c Country) TimeZoneID() (string, error) {
if id, ok := timeZoneID[c]; ok {
return id, nil
}
return "", errors.New("timezone id not found for country")
} // 获取tz时区标识符的格式化时间字符
func TimeIn(t time.Time, tz, format string) string { // https:/golang.org/pkg/time/#LoadLocation loads location on
// 加载时区
loc, err := time.LoadLocation(tz)
if err != nil {
//handle error
}
// 获取指定时区的格式化时间字符串
return t.In(loc).Format(format)
} func main() {
// 获取美国的时区结构体
tz, err := UnitedStates.TimeZoneID()
if err != nil {
//handle error
}
//格式化成美国的时区
usTime := TimeIn(time.Now(), tz, time.RFC3339) fmt.Printf("Time in %s: %s",
UnitedStates,
usTime,
)
}

Go语言time.LoadLocation可能的坑

正如标准库文档中所说的:

The time zone database needed by LoadLocation may not be present on all systems, especially non-Unix systems. LoadLocation looks in the directory or uncompressed zip file named by the ZONEINFO environment variable, if any, then looks in known installation locations on Unix systems, and finally looks in $GOROOT/lib/time/zoneinfo.zip.

LoadLocation所需的时区数据库可能并不存在于所有系统上,尤其是非unix系统. 如果有的话,LoadLocation查找由ZONEINFO环境变量命名的目录或未压缩的 ZONEINFO 环境变量命名的zip文件, 然后查找Unix系统上已知的安装位置,最后查找 $GOROOT/lib/time/ ZONEINFO .zip.

Docker Go语言使用时区

默认的情况下时区信息文件时在Go安装的时候已经存在. 但是万一你部署和编译docker使用的时 multi-stage-docker Alpine 镜像.你可以手动的使用一下命令来添加时区的数据.

RUN apk add tzdata

这将把时区信息添加到 alpine 镜像的 /usr/share/timezone. 但是也不要忘记设置环境变量 ZONEINFO 的值为 /usr/share/timezone

ZONEINFO=/usr/share/timezone

这里有一个参考的示例 Dockerfile

FROM golang:1.12-alpine as build_base
RUN apk add --update bash make git
WORKDIR /go/src/github.com/your_repo/your_app/
ENv GO111MODULE on
COPY go.mod .
COPY go.sum .
RUN go mod download FROM build_bash AS server_builder
COPY . ./
RUN GOOS=linux GOARCH=amd64 go build -ldflags="-w -s" -o /go/bin/your_app FROM alpine
RUN apk add tzdata # 自定义运行阶段的命令

示例

您可以在Go playground https://play.golang.org/p/UCKSpIWmiX7中查看完整示例

[golang]在Go中处理时区的更多相关文章

  1. C# 中获取时区列表

    c#中获取时区列表 下面方法获得的仅仅用来显示和使用,无法用来进行时间转换. public static List<DisplayTimeZone> GetSystemTimeZones( ...

  2. golang 结构体中的匿名接口

    golang 结构体中的匿名接口 代码示例 golang 中,可以给结构体增加匿名field,可参考 unknwon 大神的书. 匿名字段和内嵌结构体 但,golang同时也可以给结构体定义一个匿名i ...

  3. golang在gitlab中的工作流

    在敏捷开发的时代, 快速的编码, code review, 测试, 部署, 是提升程序员效率的关键. 同时在基础工具完备的如今, 我们甚至无需过多的操作就可以轻松实现上述步骤, 本文就以gitlab为 ...

  4. 彻底解决Odoo8.0单时区应用中的时区问题

    原文地址:http://shine-it.net/index.php/topic,17001.0.html 由于数据库中存储的是UTC时区,默认情况下数据导出和group by都存在时区问题.彻底解决 ...

  5. Windows中的时区信息

    时区 Windows API 没有提供直接得到特定时区信息的功能,Windows 系统中的时区信息存储在注册表中下面的位置: HKEY_LOCAL_MACHINE     SOFTWARE      ...

  6. java中的时区转换

    目录 java中的时区转换 一.时区的说明 二.时间的表示 三.时间戳 四.Date类和时间戳 五.java中的时区转换 java中的时区转换 一.时区的说明 地球表面按经线从东到西,被划成一个个区域 ...

  7. kvm虚拟化环境中的时区设置

    guest OS时间保持 kvm技术是全虚拟化,guest OS并不需要做修改就可以直接运行,然而在计时方面却存在问题,guest OS计时的一种方式是通过时钟中断计数,进而换算得到,但host产生的 ...

  8. [转帖]Docker中的时区问题处理

    Docker中的时区问题处理 这两天在打docker的时候,发现自己的容器启动之后,里面date -R的输出时区是UTC,总是和北京时间差了8个小时. 作者:云平台运维开发来源:今日头条|2019-0 ...

  9. Django 中的时区

    Django 中的时区 在现实环境中,存在有多个时区.用户之间很有可能存在于不同的时区,并且许多国家都拥有自己的一套夏令时系统.所以如果网站面向的是多个时区用户,只以当前时间为标准开发,便会在时间计算 ...

随机推荐

  1. 在本地库不连接远远程库的情况下操作远程库-----sql server

    --创建链接服务器 --前面都是固定不变的------q:自己随便起-----38.107.111.185:远程服务器的ip exec sp_addlinkedserver 'q', ' ', 'SQ ...

  2. ADO.NET 三(Command)

    操作数据库需则要用到 Command 类中提供的属性和方法.下面来介绍一下如何使用 Command 类来操作数据表中的数据. Command 类概述 在 System.Data.SqlClient 命 ...

  3. Mongodb 学习笔记(二) :索引

    Mongodb 是基于集合建立索引 (Index),索引的作用类似于传统关系型数据库,目的是为了提高查询速度 . 如果没有建立索引, Mongodb  在读取数据时必须扫描集合中的 所有文档记录. 这 ...

  4. Cookie 和 Session 总结

    Cookie 和 Session 区别 cookie数据存放在客户的浏览器上,session数据放在服务器上 cookie不是很安全,别人可以分析存放在本地的cookie并进行cookie欺骗,考虑* ...

  5. js编写日历的思路

    首先写出一个日历我们需要考虑以下2个问题: 每个月的总天数 每个月的第一天周几 这里提供了一个判断平年闰年2月份天数的方法: function leapYear(year) { return (yea ...

  6. ts介绍

    typescript是微软开发的一门编程语言,它是javascrip的一个超集,它遵循最新的es6脚本语言规范,typescript扩展了javascript的语法,任何已经存在的javascipt程 ...

  7. 剑指offer:二维数组的查找

    题目描述 在一个二维数组中(每个一维数组的长度相同),每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序.请完成一个函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数 ...

  8. 非正常卸载Chrome浏览器导致无法重新安装

    昨晚在使用selenium的时候,Chrome浏览器和Chromedriver.exe不兼容,前几天使用的时候都没问题,查看浏览器版本后发现浏览器已经自动升级为67版本(我之前安装的是61版本). 于 ...

  9. 团队作业第六次—团队Github实战训练(追光的人)

    所属课程 软件工程1916 作业要求 团队作业第六次-团队Github实战训练 团队名称 追光的人 作业目标 搭建一个相对公平公正的抽奖系统,根据QQ聊天记录,完成从统计参与抽奖人员颁布抽奖结果的基本 ...

  10. 【Java】《Java程序设计基础教程》第五章学习

    5.1 抽象类 Java语言中,父类的某些方法不包括任何逻辑,并且需要由子类重写.在这种情况下,用abstract关键字来修饰一个类时,这个类叫做抽象类,用abstract关键字来修饰一个方法时,这个 ...