如获取时区,获取当前或者时间范围内的日、周、月时间
package lib
import (
"fmt"
"log"
"reflect"
"time"
)
func ToMilliSeconds(v time.Time) int64 {
return v.UnixNano() / 1e6
}
func FromMilliSeconds(v int64) time.Time {
return time.Unix(0, v*1e6)
}
// GetCSTLocation 获取中国上海时区
func GetCSTLocation() *time.Location {
location, err := time.LoadLocation("Asia/Shanghai")
if err != nil {
return time.Local
}
return location
}
// GetDateStartTime 获取指定时间的开始时间
func GetDateStartTime(v interface{}) (time.Time, error) {
date, err := convertToTime(v)
if err != nil {
return date, err
}
// 获取指定时间的开始时间
startTime := time.Date(date.Year(), date.Month(), date.Day(), 0, 0, 0, 0, date.Location())
return startTime, nil
}
// GetWeekStartDateTime 获取指定时间所在周的开始时间
func GetWeekStartDateTime(v interface{}) (time.Time, error) {
date, err := convertToTime(v)
if err != nil {
return date, err
}
// 获取指定时间所在周的星期一
monday := date.AddDate(0, 0, -int(date.Weekday())+1)
return monday, nil
}
// GetMonthStartDateTime 获取指定时间所在月的开始时间
func GetMonthStartDateTime(v interface{}) (time.Time, error) {
date, err := convertToTime(v)
if err != nil {
return date, err
}
// 获取指定时间所在月的第一天
firstDay := time.Date(date.Year(), date.Month(), 1, 0, 0, 0, 0, date.Location())
return firstDay, nil
}
// convert interface{} to *time.Time
func convertToTime(v interface{}) (time.Time, error) {
var date time.Time
t := reflect.TypeOf(v)
switch t.Kind() {
case reflect.String:
// 如果 t 是 "2021-01-01" 这种字符串格式,需要先转换为 time.Time
dateString := v.(string)
parseDate, err := time.Parse("2006-01-02", dateString)
if err != nil {
return date, err
}
// 转换为北京时间
date = TimeToDate(parseDate, time.FixedZone("CST", 8*3600))
case reflect.Int64:
// 如果 t 是时间戳,直接转换为 time.Time
date = FromMilliSeconds(v.(int64))
case reflect.Struct:
// 如果 t 是 time.Time 结构体,直接使用
if t == reflect.TypeOf(time.Time{}) {
date = v.(time.Time)
} else {
return date, fmt.Errorf("unsupported type")
}
default:
return date, fmt.Errorf("unsupported type")
}
// 转换为上海时区
location, err := time.LoadLocation("Asia/Shanghai")
if err != nil {
return date, err
}
date = date.In(location)
return date, nil
}
// GetDateTimeByRange 获取指定时间范围内的每日开始时间
func GetDateTimeByRange(start, end int64, opt Opt) ([]time.Time, error) {
var days []time.Time
// 获取指定时间范围内的每日开始时间
for i := start; i <= end; i += 24 * 3600 * 1000 {
day, err := GetDateStartTime(i)
if err != nil {
return nil, err
}
if opt.FilterOutOfRange && (ToMilliSeconds(day) < start || ToMilliSeconds(day) > end) {
continue
}
days = append(days, day)
}
return days, nil
}
type Opt struct {
FilterOutOfRange bool
}
// GetWeekStartDateTimeByRange 获取指定时间范围内的周开始时间
func GetWeekStartDateTimeByRange(start, end int64, opt Opt) ([]time.Time, error) {
var weeks []time.Time
// 获取指定时间范围内的周开始时间
for i := start; i <= end; i += 7 * 24 * 3600 * 1000 {
week, err := GetWeekStartDateTime(i)
if err != nil {
return nil, err
}
if opt.FilterOutOfRange && (ToMilliSeconds(week) < start || ToMilliSeconds(week) > end) {
continue
}
weeks = append(weeks, week)
}
return weeks, nil
}
// GetMonthStartDateTimeByRange 获取指定时间范围内的月开始时间
func GetMonthStartDateTimeByRange(start, end int64, opt Opt) ([]time.Time, error) {
var months []time.Time
timestamp := start
// 获取指定时间范围内的月开始时间
for timestamp <= end {
month, err := GetMonthStartDateTime(timestamp)
if err != nil {
return nil, err
}
// month += 1
timestamp = ToMilliSeconds(month.AddDate(0, 1, 0))
if opt.FilterOutOfRange && (ToMilliSeconds(month) < start || ToMilliSeconds(month) > end) {
continue
}
months = append(months, month)
}
return months, nil
}