462 lines
10 KiB
Markdown
462 lines
10 KiB
Markdown
# 日期转换工具文档
|
||
|
||
## 概述
|
||
|
||
日期转换工具提供了丰富的日期时间处理功能,支持时区设定、格式转换、时间计算等常用操作。
|
||
|
||
## 功能特性
|
||
|
||
- 支持时区设定和转换
|
||
- 支持多种时间格式的解析和格式化
|
||
- 提供常用时间格式常量
|
||
- 支持Unix时间戳转换
|
||
- 提供时间计算功能(添加天数、月数、年数等)
|
||
- 提供时间范围获取功能(开始/结束时间)
|
||
- 支持将任意时区时间转换为UTC时间(用于数据库存储)
|
||
|
||
## 使用方法
|
||
|
||
### 1. 设置默认时区
|
||
|
||
```go
|
||
import "github.com/go-common/datetime"
|
||
|
||
// 设置默认时区为上海时区
|
||
err := datetime.SetDefaultTimeZone(datetime.AsiaShanghai)
|
||
if err != nil {
|
||
log.Fatal(err)
|
||
}
|
||
```
|
||
|
||
### 2. 获取当前时间
|
||
|
||
```go
|
||
// 使用默认时区
|
||
now := datetime.Now()
|
||
|
||
// 使用指定时区
|
||
now := datetime.Now(datetime.AsiaShanghai)
|
||
now := datetime.Now("America/New_York")
|
||
```
|
||
|
||
### 3. 解析时间字符串
|
||
|
||
```go
|
||
// 使用默认时区解析
|
||
t, err := datetime.Parse("2006-01-02 15:04:05", "2024-01-01 12:00:00")
|
||
if err != nil {
|
||
log.Fatal(err)
|
||
}
|
||
|
||
// 使用指定时区解析
|
||
t, err := datetime.Parse("2006-01-02 15:04:05", "2024-01-01 12:00:00", datetime.AsiaShanghai)
|
||
|
||
// 使用常用格式解析
|
||
t, err := datetime.ParseDateTime("2024-01-01 12:00:00")
|
||
t, err := datetime.ParseDate("2024-01-01")
|
||
```
|
||
|
||
### 4. 格式化时间
|
||
|
||
```go
|
||
t := time.Now()
|
||
|
||
// 使用默认时区格式化
|
||
str := datetime.Format(t, "2006-01-02 15:04:05")
|
||
|
||
// 使用指定时区格式化
|
||
str := datetime.Format(t, "2006-01-02 15:04:05", datetime.AsiaShanghai)
|
||
|
||
// 使用常用格式
|
||
str := datetime.FormatDateTime(t) // "2006-01-02 15:04:05"
|
||
str := datetime.FormatDate(t) // "2006-01-02"
|
||
str := datetime.FormatTime(t) // "15:04:05"
|
||
```
|
||
|
||
### 5. 时区转换
|
||
|
||
```go
|
||
t := time.Now()
|
||
|
||
// 转换到指定时区
|
||
t2, err := datetime.ToTimezone(t, datetime.AsiaShanghai)
|
||
if err != nil {
|
||
log.Fatal(err)
|
||
}
|
||
```
|
||
|
||
### 6. Unix时间戳转换
|
||
|
||
```go
|
||
t := time.Now()
|
||
|
||
// 转换为Unix时间戳(秒)
|
||
unix := datetime.ToUnix(t)
|
||
|
||
// 从Unix时间戳创建时间
|
||
t2 := datetime.FromUnix(unix)
|
||
|
||
// 转换为Unix毫秒时间戳
|
||
unixMilli := datetime.ToUnixMilli(t)
|
||
|
||
// 从Unix毫秒时间戳创建时间
|
||
t3 := datetime.FromUnixMilli(unixMilli)
|
||
```
|
||
|
||
### 7. 时间计算
|
||
|
||
```go
|
||
t := time.Now()
|
||
|
||
// 添加天数
|
||
t1 := datetime.AddDays(t, 7)
|
||
|
||
// 添加月数
|
||
t2 := datetime.AddMonths(t, 1)
|
||
|
||
// 添加年数
|
||
t3 := datetime.AddYears(t, 1)
|
||
```
|
||
|
||
### 8. 时间范围获取
|
||
|
||
```go
|
||
t := time.Now()
|
||
|
||
// 获取一天的开始时间(00:00:00)
|
||
start := datetime.StartOfDay(t)
|
||
|
||
// 获取一天的结束时间(23:59:59.999999999)
|
||
end := datetime.EndOfDay(t)
|
||
|
||
// 获取月份的开始时间
|
||
monthStart := datetime.StartOfMonth(t)
|
||
|
||
// 获取月份的结束时间
|
||
monthEnd := datetime.EndOfMonth(t)
|
||
|
||
// 获取年份的开始时间
|
||
yearStart := datetime.StartOfYear(t)
|
||
|
||
// 获取年份的结束时间
|
||
yearEnd := datetime.EndOfYear(t)
|
||
```
|
||
|
||
### 9. 时间差计算
|
||
|
||
```go
|
||
t1 := time.Now()
|
||
t2 := time.Now().Add(24 * time.Hour)
|
||
|
||
// 计算天数差
|
||
days := datetime.DiffDays(t1, t2)
|
||
|
||
// 计算小时差
|
||
hours := datetime.DiffHours(t1, t2)
|
||
|
||
// 计算分钟差
|
||
minutes := datetime.DiffMinutes(t1, t2)
|
||
|
||
// 计算秒数差
|
||
seconds := datetime.DiffSeconds(t1, t2)
|
||
```
|
||
|
||
### 10. 转换为UTC时间(用于数据库存储)
|
||
|
||
```go
|
||
// 将任意时区的时间转换为UTC
|
||
t := time.Now() // 当前时区的时间
|
||
utcTime := datetime.ToUTC(t)
|
||
|
||
// 从指定时区转换为UTC
|
||
t, _ := datetime.ParseDateTime("2024-01-01 12:00:00", datetime.AsiaShanghai)
|
||
utcTime, err := datetime.ToUTCFromTimezone(t, datetime.AsiaShanghai)
|
||
|
||
// 解析时间字符串并直接转换为UTC
|
||
utcTime, err := datetime.ParseDateTimeToUTC("2024-01-01 12:00:00", datetime.AsiaShanghai)
|
||
|
||
// 解析日期并转换为UTC(当天的00:00:00 UTC)
|
||
utcTime, err := datetime.ParseDateToUTC("2024-01-01", datetime.AsiaShanghai)
|
||
```
|
||
|
||
## API 参考
|
||
|
||
### 时区常量
|
||
|
||
```go
|
||
const (
|
||
UTC = "UTC"
|
||
AsiaShanghai = "Asia/Shanghai"
|
||
AmericaNewYork = "America/New_York"
|
||
EuropeLondon = "Europe/London"
|
||
AsiaTokyo = "Asia/Tokyo"
|
||
)
|
||
```
|
||
|
||
### 常用时间格式
|
||
|
||
```go
|
||
CommonLayouts.DateTime = "2006-01-02 15:04"
|
||
CommonLayouts.DateTimeSec = "2006-01-02 15:04:05"
|
||
CommonLayouts.Date = "2006-01-02"
|
||
CommonLayouts.Time = "15:04"
|
||
CommonLayouts.TimeSec = "15:04:05"
|
||
CommonLayouts.ISO8601 = "2006-01-02T15:04:05Z07:00"
|
||
CommonLayouts.RFC3339 = time.RFC3339
|
||
CommonLayouts.RFC3339Nano = time.RFC3339Nano
|
||
```
|
||
|
||
### 主要函数
|
||
|
||
#### SetDefaultTimeZone(timezone string) error
|
||
|
||
设置默认时区。
|
||
|
||
**参数:**
|
||
- `timezone`: 时区字符串,如 "Asia/Shanghai"
|
||
|
||
**返回:** 错误信息
|
||
|
||
#### Now(timezone ...string) time.Time
|
||
|
||
获取当前时间。
|
||
|
||
**参数:**
|
||
- `timezone`: 可选,时区字符串,不指定则使用默认时区
|
||
|
||
**返回:** 时间对象
|
||
|
||
#### Parse(layout, value string, timezone ...string) (time.Time, error)
|
||
|
||
解析时间字符串。
|
||
|
||
**参数:**
|
||
- `layout`: 时间格式,如 "2006-01-02 15:04:05"
|
||
- `value`: 时间字符串
|
||
- `timezone`: 可选,时区字符串
|
||
|
||
**返回:** 时间对象和错误信息
|
||
|
||
#### Format(t time.Time, layout string, timezone ...string) string
|
||
|
||
格式化时间。
|
||
|
||
**参数:**
|
||
- `t`: 时间对象
|
||
- `layout`: 时间格式
|
||
- `timezone`: 可选,时区字符串
|
||
|
||
**返回:** 格式化后的时间字符串
|
||
|
||
#### ToTimezone(t time.Time, timezone string) (time.Time, error)
|
||
|
||
转换时区。
|
||
|
||
**参数:**
|
||
- `t`: 时间对象
|
||
- `timezone`: 目标时区
|
||
|
||
**返回:** 转换后的时间对象和错误信息
|
||
|
||
#### ToUnix(t time.Time) int64
|
||
|
||
转换为Unix时间戳(秒)。
|
||
|
||
#### FromUnix(sec int64, timezone ...string) time.Time
|
||
|
||
从Unix时间戳创建时间。
|
||
|
||
#### ToUnixMilli(t time.Time) int64
|
||
|
||
转换为Unix毫秒时间戳。
|
||
|
||
#### FromUnixMilli(msec int64, timezone ...string) time.Time
|
||
|
||
从Unix毫秒时间戳创建时间。
|
||
|
||
#### AddDays(t time.Time, days int) time.Time
|
||
|
||
添加天数。
|
||
|
||
#### AddMonths(t time.Time, months int) time.Time
|
||
|
||
添加月数。
|
||
|
||
#### AddYears(t time.Time, years int) time.Time
|
||
|
||
添加年数。
|
||
|
||
#### StartOfDay(t time.Time, timezone ...string) time.Time
|
||
|
||
获取一天的开始时间。
|
||
|
||
#### EndOfDay(t time.Time, timezone ...string) time.Time
|
||
|
||
获取一天的结束时间。
|
||
|
||
#### StartOfMonth(t time.Time, timezone ...string) time.Time
|
||
|
||
获取月份的开始时间。
|
||
|
||
#### EndOfMonth(t time.Time, timezone ...string) time.Time
|
||
|
||
获取月份的结束时间。
|
||
|
||
#### StartOfYear(t time.Time, timezone ...string) time.Time
|
||
|
||
获取年份的开始时间。
|
||
|
||
#### EndOfYear(t time.Time, timezone ...string) time.Time
|
||
|
||
获取年份的结束时间。
|
||
|
||
#### DiffDays(t1, t2 time.Time) int
|
||
|
||
计算两个时间之间的天数差。
|
||
|
||
#### DiffHours(t1, t2 time.Time) int64
|
||
|
||
计算两个时间之间的小时差。
|
||
|
||
#### DiffMinutes(t1, t2 time.Time) int64
|
||
|
||
计算两个时间之间的分钟差。
|
||
|
||
#### DiffSeconds(t1, t2 time.Time) int64
|
||
|
||
计算两个时间之间的秒数差。
|
||
|
||
### UTC转换函数
|
||
|
||
#### ToUTC(t time.Time) time.Time
|
||
|
||
将时间转换为UTC时间。
|
||
|
||
**参数:**
|
||
- `t`: 时间对象(可以是任意时区)
|
||
|
||
**返回:** UTC时间
|
||
|
||
#### ToUTCFromTimezone(t time.Time, timezone string) (time.Time, error)
|
||
|
||
从指定时区转换为UTC时间。
|
||
|
||
**参数:**
|
||
- `t`: 时间对象(会被视为指定时区的时间)
|
||
- `timezone`: 源时区
|
||
|
||
**返回:** UTC时间和错误信息
|
||
|
||
#### ParseToUTC(layout, value string, timezone ...string) (time.Time, error)
|
||
|
||
解析时间字符串并转换为UTC时间。
|
||
|
||
**参数:**
|
||
- `layout`: 时间格式,如 "2006-01-02 15:04:05"
|
||
- `value`: 时间字符串
|
||
- `timezone`: 源时区,如果为空则使用默认时区
|
||
|
||
**返回:** UTC时间和错误信息
|
||
|
||
#### ParseDateTimeToUTC(value string, timezone ...string) (time.Time, error)
|
||
|
||
解析日期时间字符串并转换为UTC时间(便捷方法)。
|
||
|
||
**参数:**
|
||
- `value`: 时间字符串(格式: 2006-01-02 15:04:05)
|
||
- `timezone`: 源时区,如果为空则使用默认时区
|
||
|
||
**返回:** UTC时间和错误信息
|
||
|
||
#### ParseDateToUTC(value string, timezone ...string) (time.Time, error)
|
||
|
||
解析日期字符串并转换为UTC时间(便捷方法)。
|
||
|
||
**参数:**
|
||
- `value`: 日期字符串(格式: 2006-01-02)
|
||
- `timezone`: 源时区,如果为空则使用默认时区
|
||
|
||
**返回:** UTC时间(当天的00:00:00 UTC时间)和错误信息
|
||
|
||
## 注意事项
|
||
|
||
1. **时区字符串**:必须符合IANA时区数据库格式
|
||
2. **默认时区**:默认时区为UTC,建议在应用启动时设置合适的默认时区
|
||
3. **时间格式**:时间格式字符串必须使用Go的特定时间(2006-01-02 15:04:05)
|
||
4. **时间范围函数**:所有时间范围函数(StartOfDay、EndOfDay等)都会考虑时区
|
||
5. **数据库存储**:
|
||
- 数据库时间统一使用UTC时间存储
|
||
- 使用`ToUTC`、`ParseToUTC`等方法将时间转换为UTC后存储到数据库
|
||
- 从数据库读取UTC时间后,使用`ToTimezone`转换为用户时区显示
|
||
|
||
## 完整示例
|
||
|
||
### 示例1:基本使用
|
||
|
||
```go
|
||
package main
|
||
|
||
import (
|
||
"fmt"
|
||
"log"
|
||
"time"
|
||
|
||
"github.com/go-common/datetime"
|
||
)
|
||
|
||
func main() {
|
||
// 设置默认时区
|
||
datetime.SetDefaultTimeZone(datetime.AsiaShanghai)
|
||
|
||
// 获取当前时间
|
||
now := datetime.Now()
|
||
fmt.Printf("Current time: %s\n", datetime.FormatDateTime(now))
|
||
|
||
// 时区转换
|
||
t, _ := datetime.ParseDateTime("2024-01-01 12:00:00")
|
||
t2, _ := datetime.ToTimezone(t, datetime.AmericaNewYork)
|
||
fmt.Printf("Time in New York: %s\n", datetime.FormatDateTime(t2))
|
||
}
|
||
```
|
||
|
||
### 示例2:UTC转换(数据库存储场景)
|
||
|
||
```go
|
||
package main
|
||
|
||
import (
|
||
"fmt"
|
||
"log"
|
||
|
||
"github.com/go-common/datetime"
|
||
)
|
||
|
||
func main() {
|
||
// 从请求中获取时间(假设是上海时区)
|
||
requestTimeStr := "2024-01-01 12:00:00"
|
||
requestTimezone := datetime.AsiaShanghai
|
||
|
||
// 转换为UTC时间(用于数据库存储)
|
||
dbTime, err := datetime.ParseDateTimeToUTC(requestTimeStr, requestTimezone)
|
||
if err != nil {
|
||
log.Fatal(err)
|
||
}
|
||
|
||
fmt.Printf("Request time (Shanghai): %s\n", requestTimeStr)
|
||
fmt.Printf("Database time (UTC): %s\n", datetime.FormatDateTime(dbTime, datetime.UTC))
|
||
|
||
// 从数据库读取UTC时间,转换为用户时区显示
|
||
userTimezone := datetime.AsiaShanghai
|
||
displayTime, err := datetime.ToTimezone(dbTime, userTimezone)
|
||
if err != nil {
|
||
log.Fatal(err)
|
||
}
|
||
fmt.Printf("Display time (Shanghai): %s\n", datetime.FormatDateTime(displayTime, userTimezone))
|
||
}
|
||
```
|
||
|
||
完整示例请参考:
|
||
- `examples/datetime_example.go` - 基本使用示例
|
||
- `examples/datetime_utc_example.go` - UTC转换示例
|
||
|