| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923 |
- /*
- * Copyright (c) 2000-2018, 达梦数据库有限公司.
- * All rights reserved.
- */
- package dm
- import (
- "math"
- "strconv"
- "strings"
- "time"
- "unicode"
- )
- func encodeByString(x string, column column, conn DmConnection) ([]byte, error) {
- dt := make([]int, DT_LEN)
- if _, err := toDTFromString(x, dt); err != nil {
- return nil, err
- }
- return encode(dt, column, int(conn.dmConnector.localTimezone), int(conn.DbTimezone))
- }
- func encodeByTime(x time.Time, column column, conn DmConnection) ([]byte, error) {
- dt := toDTFromTime(x)
- return encode(dt, column, int(conn.dmConnector.localTimezone), int(conn.DbTimezone))
- }
- func toTimeFromString(str string, ltz int) time.Time {
- dt := make([]int, DT_LEN)
- toDTFromString(str, dt)
- return toTimeFromDT(dt, ltz)
- }
- func toTimeFromDT(dt []int, ltz int) time.Time {
- var year, month, day, hour, minute, second, nsec, tz int
- year = dt[OFFSET_YEAR]
- if dt[OFFSET_MONTH] > 0 {
- month = dt[OFFSET_MONTH]
- } else {
- month = 1
- }
- if dt[OFFSET_DAY] > 0 {
- day = dt[OFFSET_DAY]
- } else {
- day = 1
- }
- hour = dt[OFFSET_HOUR]
- minute = dt[OFFSET_MINUTE]
- second = dt[OFFSET_SECOND]
- nsec = dt[OFFSET_NANOSECOND]
- if dt[OFFSET_TIMEZONE] == INVALID_VALUE {
- tz = ltz * 60
- } else {
- tz = dt[OFFSET_TIMEZONE] * 60
- }
- return time.Date(year, time.Month(month), day, hour, minute, second, nsec, time.FixedZone("", tz))
- }
- func decode(value []byte, isBdta bool, column column, ltz int, dtz int) []int {
- var dt []int
- if isBdta {
- dt = dmdtDecodeBdta(value)
- } else {
- dt = dmdtDecodeFast(value)
- }
- if column.mask == MASK_LOCAL_DATETIME {
- transformTZ(dt, dtz, ltz)
- }
- return dt
- }
- func dmdtDecodeFast(value []byte) []int {
- dt := make([]int, DT_LEN)
- dt[OFFSET_TIMEZONE] = INVALID_VALUE
- dtype := 0
- if len(value) == DATE_PREC {
- dtype = DATE
- } else if len(value) == TIME_PREC {
- dtype = TIME
- } else if len(value) == TIME_TZ_PREC {
- dtype = TIME_TZ
- } else if len(value) == DATETIME_PREC {
- dtype = DATETIME
- } else if len(value) == DATETIME2_PREC {
- dtype = DATETIME2
- } else if len(value) == DATETIME_TZ_PREC {
- dtype = DATETIME_TZ
- } else if len(value) == DATETIME2_TZ_PREC {
- dtype = DATETIME2_TZ
- }
- if dtype == DATE {
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0)) & 0x7FFF
- if dt[OFFSET_YEAR] > 9999 {
- dt[OFFSET_YEAR] = int(int16(dt[OFFSET_YEAR] | 0x8000))
- }
- dt[OFFSET_MONTH] = ((int(value[1]) >> 7) & 0x1) + ((int(value[2]) & 0x07) << 1)
- dt[OFFSET_DAY] = ((int(value[2]) & 0xF8) >> 3) & 0x1f
- } else if dtype == TIME {
- dt[OFFSET_HOUR] = int(value[0]) & 0x1F
- dt[OFFSET_MINUTE] = ((int(value[0]) >> 5) & 0x07) + ((int(value[1]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[1]) >> 3) & 0x1f) + ((int(value[2]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[2]) >> 1) & 0x7f) + ((int(value[3]) & 0x00ff) << 7) + ((int(value[4]) & 0x1F) << 15)
- dt[OFFSET_NANOSECOND] *= 1000
- } else if dtype == TIME_TZ {
- dt[OFFSET_HOUR] = int(value[0]) & 0x1F
- dt[OFFSET_MINUTE] = ((int(value[0]) >> 5) & 0x07) + ((int(value[1]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[1]) >> 3) & 0x1f) + ((int(value[2]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[2]) >> 1) & 0x7f) + ((int(value[3]) & 0x00ff) << 7) + ((int(value[4]) & 0x1F) << 15)
- dt[OFFSET_NANOSECOND] *= 1000
- dt[OFFSET_TIMEZONE] = int(Dm_build_1.Dm_build_98(value, 5))
- } else if dtype == DATETIME {
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0)) & 0x7FFF
- if dt[OFFSET_YEAR] > 9999 {
- dt[OFFSET_YEAR] = int(int16(dt[OFFSET_YEAR] | 0x8000))
- }
- dt[OFFSET_MONTH] = ((int(value[1]) >> 7) & 0x1) + ((int(value[2]) & 0x07) << 1)
- dt[OFFSET_DAY] = ((int(value[2]) & 0xF8) >> 3) & 0x1f
- dt[OFFSET_HOUR] = (int(value[3]) & 0x1F)
- dt[OFFSET_MINUTE] = ((int(value[3]) >> 5) & 0x07) + ((int(value[4]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[4]) >> 3) & 0x1f) + ((int(value[5]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[5]) >> 1) & 0x7f) + ((int(value[6]) & 0x00ff) << 7) + ((int(value[7]) & 0x1F) << 15)
- dt[OFFSET_NANOSECOND] *= 1000
- } else if dtype == DATETIME_TZ {
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0)) & 0x7FFF
- if dt[OFFSET_YEAR] > 9999 {
- dt[OFFSET_YEAR] = int(int16(dt[OFFSET_YEAR] | 0x8000))
- }
- dt[OFFSET_MONTH] = ((int(value[1]) >> 7) & 0x1) + ((int(value[2]) & 0x07) << 1)
- dt[OFFSET_DAY] = ((int(value[2]) & 0xF8) >> 3) & 0x1f
- dt[OFFSET_HOUR] = (int(value[3]) & 0x1F)
- dt[OFFSET_MINUTE] = ((int(value[3]) >> 5) & 0x07) + ((int(value[4]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[4]) >> 3) & 0x1f) + ((int(value[5]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[5]) >> 1) & 0x7f) + ((int(value[6]) & 0x00ff) << 7) + ((int(value[7]) & 0x1F) << 15)
- dt[OFFSET_NANOSECOND] *= 1000
- dt[OFFSET_TIMEZONE] = int(Dm_build_1.Dm_build_98(value, len(value)-2))
- } else if dtype == DATETIME2 {
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0)) & 0x7FFF
- if dt[OFFSET_YEAR] > 9999 {
- dt[OFFSET_YEAR] = int(int16(dt[OFFSET_YEAR] | 0x8000))
- }
- dt[OFFSET_MONTH] = ((int(value[1]) >> 7) & 0x1) + ((int(value[2]) & 0x07) << 1)
- dt[OFFSET_DAY] = ((int(value[2]) & 0xF8) >> 3) & 0x1f
- dt[OFFSET_HOUR] = (int(value[3]) & 0x1F)
- dt[OFFSET_MINUTE] = ((int(value[3]) >> 5) & 0x07) + ((int(value[4]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[4]) >> 3) & 0x1f) + ((int(value[5]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[5]) >> 1) & 0x7f) + ((int(value[6]) & 0x00ff) << 7) + ((int(value[7]) & 0x00ff) << 15) + ((int(value[8]) & 0x7F) << 23)
- } else if dtype == DATETIME2_TZ {
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0)) & 0x7FFF
- if dt[OFFSET_YEAR] > 9999 {
- dt[OFFSET_YEAR] = int(int16(dt[OFFSET_YEAR] | 0x8000))
- }
- dt[OFFSET_MONTH] = ((int(value[1]) >> 7) & 0x1) + ((int(value[2]) & 0x07) << 1)
- dt[OFFSET_DAY] = ((int(value[2]) & 0xF8) >> 3) & 0x1f
- dt[OFFSET_HOUR] = (int(value[3]) & 0x1F)
- dt[OFFSET_MINUTE] = ((int(value[3]) >> 5) & 0x07) + ((int(value[4]) & 0x07) << 3)
- dt[OFFSET_SECOND] = ((int(value[4]) >> 3) & 0x1f) + ((int(value[5]) & 0x01) << 5)
- dt[OFFSET_NANOSECOND] = ((int(value[5]) >> 1) & 0x7f) + ((int(value[6]) & 0x00ff) << 7) + ((int(value[7]) & 0x00ff) << 15) + ((int(value[8]) & 0x7F) << 23)
- dt[OFFSET_TIMEZONE] = int(Dm_build_1.Dm_build_98(value, len(value)-2))
- }
- return dt
- }
- func dmdtDecodeBdta(value []byte) []int {
- dt := make([]int, DT_LEN)
- dt[OFFSET_YEAR] = int(Dm_build_1.Dm_build_98(value, 0))
- dt[OFFSET_MONTH] = int(value[2] & 0xFF)
- dt[OFFSET_DAY] = int(value[3] & 0xFF)
- dt[OFFSET_HOUR] = int(value[4] & 0xFF)
- dt[OFFSET_MINUTE] = int(value[5] & 0xFF)
- dt[OFFSET_SECOND] = int(value[6] & 0xFF)
- dt[OFFSET_NANOSECOND] = int((value[7] & 0xFF) + (value[8] << 8) + (value[9] << 16))
- dt[OFFSET_TIMEZONE] = int(Dm_build_1.Dm_build_98(value, 10))
- if len(value) > 12 {
- dt[OFFSET_NANOSECOND] += int(value[12] << 24)
- }
- return dt
- }
- func dtToStringByOracleFormat(dt []int, oracleFormatPattern string, scale int32, language int) string {
- return format(dt, oracleFormatPattern, scale, language)
- }
- func dtToString(dt []int, dtype int, scale int) string {
- switch dtype {
- case DATE:
- return formatYear(dt[OFFSET_YEAR]) + "-" + format2(dt[OFFSET_MONTH]) + "-" + format2(dt[OFFSET_DAY])
- case TIME:
- if scale > 0 {
- return format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + "." + formatMilliSecond(dt[OFFSET_NANOSECOND], scale)
- } else {
- return format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND])
- }
- case TIME_TZ:
- if scale > 0 {
- return format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + "." + formatMilliSecond(dt[OFFSET_NANOSECOND], scale) + " " + formatTZ(dt[OFFSET_TIMEZONE])
- } else {
- return format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + " " + formatTZ(dt[OFFSET_TIMEZONE])
- }
- case DATETIME, DATETIME2:
- if scale > 0 {
- return formatYear(dt[OFFSET_YEAR]) + "-" + format2(dt[OFFSET_MONTH]) + "-" + format2(dt[OFFSET_DAY]) + " " + format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + "." + formatMilliSecond(dt[OFFSET_NANOSECOND], scale)
- } else {
- return formatYear(dt[OFFSET_YEAR]) + "-" + format2(dt[OFFSET_MONTH]) + "-" + format2(dt[OFFSET_DAY]) + " " + format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND])
- }
- case DATETIME_TZ, DATETIME2_TZ:
- if scale > 0 {
- return formatYear(dt[OFFSET_YEAR]) + "-" + format2(dt[OFFSET_MONTH]) + "-" + format2(dt[OFFSET_DAY]) + " " + format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + "." + formatMilliSecond(dt[OFFSET_NANOSECOND], scale) + " " + formatTZ(dt[OFFSET_TIMEZONE])
- } else {
- return formatYear(dt[OFFSET_YEAR]) + "-" + format2(dt[OFFSET_MONTH]) + "-" + format2(dt[OFFSET_DAY]) + " " + format2(dt[OFFSET_HOUR]) + ":" + format2(dt[OFFSET_MINUTE]) + ":" + format2(dt[OFFSET_SECOND]) + " " + formatTZ(dt[OFFSET_TIMEZONE])
- }
- }
- return ""
- }
- func formatYear(value int) string {
- if value >= 0 {
- if value < 10 {
- return "000" + strconv.FormatInt(int64(value), 10)
- } else if value < 100 {
- return "00" + strconv.FormatInt(int64(value), 10)
- } else if value < 1000 {
- return "0" + strconv.FormatInt(int64(value), 10)
- } else {
- return strconv.FormatInt(int64(value), 10)
- }
- } else {
- if value > -10 {
- return "-000" + strconv.FormatInt(int64(-value), 10)
- } else if value > -100 {
- return "-00" + strconv.FormatInt(int64(-value), 10)
- } else if value > -1000 {
- return "-0" + strconv.FormatInt(int64(-value), 10)
- } else {
- return strconv.FormatInt(int64(value), 10)
- }
- }
- }
- func format2(value int) string {
- if value < 10 {
- return "0" + strconv.FormatInt(int64(value), 10)
- } else {
- return strconv.FormatInt(int64(value), 10)
- }
- }
- func formatMilliSecond(ms int, prec int) string {
- var ret string
- if ms < 10 {
- ret = "00000000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 100 {
- ret = "0000000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 1000 {
- ret = "000000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 10000 {
- ret = "00000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 100000 {
- ret = "0000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 1000000 {
- ret = "000" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 10000000 {
- ret = "00" + strconv.FormatInt(int64(ms), 10)
- } else if ms < 100000000 {
- ret = "0" + strconv.FormatInt(int64(ms), 10)
- } else {
- ret = strconv.FormatInt(int64(ms), 10)
- }
- if prec < NANOSECOND_DIGITS {
- ret = ret[:prec]
- }
- return ret
- }
- func formatTZ(tz int) string {
- tz_hour := int(math.Abs(float64(tz / 60)))
- tz_min := int(math.Abs(float64(tz % 60)))
- if tz >= 0 {
- return "+" + format2(tz_hour) + ":" + format2(tz_min)
- } else {
- return "-" + format2(tz_hour) + ":" + format2(tz_min)
- }
- }
- func toDTFromTime(x time.Time) []int {
- hour, min, sec := x.Clock()
- ts := make([]int, DT_LEN)
- ts[OFFSET_YEAR] = x.Year()
- ts[OFFSET_MONTH] = int(x.Month())
- ts[OFFSET_DAY] = x.Day()
- ts[OFFSET_HOUR] = hour
- ts[OFFSET_MINUTE] = min
- ts[OFFSET_SECOND] = sec
- ts[OFFSET_NANOSECOND] = (int)(x.Nanosecond())
- _, tz := x.Zone()
- ts[OFFSET_TIMEZONE] = tz / 60
- return ts
- }
- func toDTFromUnix(sec int64, nsec int64) []int {
- return toDTFromTime(time.Unix(sec, nsec))
- }
- func toDTFromString(s string, dt []int) (dtype int, err error) {
- defer func() {
- if p := recover(); p != nil {
- err = ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- }()
- date_s := ""
- time_s := ""
- nanos_s := ""
- tz_s := ""
- year := 0
- month := 0
- day := 0
- hour := 0
- minute := 0
- second := 0
- a_nanos := 0
- firstDash := -1
- secondDash := -1
- firstColon := -1
- secondColon := -1
- period := -1
- sign := 0
- ownTz := INVALID_VALUE
- dtype = -1
- zeros := "000000000"
- if s != "" && strings.TrimSpace(s) == "" {
- return 0, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- s = strings.TrimSpace(s)
- if strings.Index(s, "-") == 0 {
- s = strings.TrimSpace(s[1:])
- sign = 1
- }
- comps := strings.Split(s, " ")
- switch len(comps) {
- case 3:
- date_s = comps[0]
- time_s = comps[1]
- tz_s = comps[2]
- dtype = DATETIME_TZ
- case 2:
- if strings.Index(comps[0], ":") > 0 {
- time_s = comps[0]
- tz_s = comps[1]
- dtype = TIME_TZ
- } else {
- date_s = comps[0]
- time_s = comps[1]
- dtype = DATETIME
- }
- case 1:
- if strings.Index(comps[0], ":") > 0 {
- time_s = comps[0]
- dtype = TIME
- } else {
- date_s = comps[0]
- dtype = DATE
- }
- default:
- return 0, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- if date_s != "" {
- firstDash = strings.Index(date_s, "-")
- secondDash = strings.Index(date_s[firstDash+1:], "-")
- if firstDash < 0 || secondDash < 0 {
- firstDash = strings.Index(s, ".")
- secondDash = strings.Index(date_s[firstDash+1:], ".")
- }
- if firstDash < 0 || secondDash < 0 {
- firstDash = strings.Index(s, "/")
- secondDash = strings.Index(date_s[firstDash+1:], "/")
- }
- if secondDash > 0 {
- secondDash += firstDash + 1
- }
- if (firstDash > 0) && (secondDash > 0) && (secondDash < len(date_s)-1) {
- if sign == 1 {
- i, err := strconv.ParseInt(date_s[:firstDash], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- year = 0 - int(i) - 1900
- } else {
- i, err := strconv.ParseInt(date_s[:firstDash], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- year = int(i) - 1900
- }
- i, err := strconv.ParseInt(date_s[firstDash+1:secondDash], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- month = int(i) - 1
- i, err = strconv.ParseInt(date_s[secondDash+1:], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- day = int(i)
- if !checkDate(year+1900, month+1, day) {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- } else {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- }
- if time_s != "" {
- firstColon = strings.Index(time_s, ":")
- secondColon = strings.Index(time_s[firstColon+1:], ":")
- if secondColon > 0 {
- secondColon += firstColon + 1
- }
- period = strings.Index(time_s[secondColon+1:], ".")
- if period > 0 {
- period += secondColon + 1
- }
- if (firstColon > 0) && (secondColon > 0) && (secondColon < len(time_s)-1) {
- i, err := strconv.ParseInt(time_s[:firstColon], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- hour = int(i)
- i, err = strconv.ParseInt(time_s[firstColon+1:secondColon], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- minute = int(i)
- if period > 0 && period < len(time_s)-1 {
- i, err = strconv.ParseInt(time_s[secondColon+1:period], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- second = int(i)
- nanos_s = time_s[period+1:]
- if len(nanos_s) > NANOSECOND_DIGITS {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- if !unicode.IsDigit(rune(nanos_s[0])) {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- nanos_s = nanos_s + zeros[0:NANOSECOND_DIGITS-len(nanos_s)]
- i, err = strconv.ParseInt(nanos_s, 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- a_nanos = int(i)
- } else if period > 0 {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- } else {
- i, err = strconv.ParseInt(time_s[secondColon+1:], 10, 32)
- if err != nil {
- return 0, ECGO_INVALID_DATETIME_FORMAT.addDetailln(err.Error()).throw()
- }
- second = int(i)
- }
- if hour >= 24 || hour < 0 || minute >= 60 || minute < 0 || second >= 60 || second < 0 {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- } else {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- }
- if tz_s != "" {
- neg := false
- if strings.Index(tz_s, "-") == 0 {
- neg = true
- }
- if strings.Index(tz_s, "-") == 0 || strings.Index(tz_s, "+") == 0 {
- tz_s = strings.TrimSpace(tz_s[1:])
- }
- hm := strings.Split(tz_s, ":")
- var tzh, tzm int16 = 0, 0
- switch len(hm) {
- case 2:
- s, err := strconv.ParseInt(strings.TrimSpace(hm[0]), 10, 16)
- if err != nil {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- tzh = int16(s)
- s, err = strconv.ParseInt(strings.TrimSpace(hm[1]), 10, 16)
- if err != nil {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- tzm = int16(s)
- case 1:
- s, err := strconv.ParseInt(strings.TrimSpace(hm[0]), 10, 16)
- if err != nil {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- tzh = int16(s)
- default:
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- ownTz = int(tzh*60 + tzm)
- if ownTz < 0 {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- if neg {
- ownTz *= -1
- }
- if ownTz <= -13*60 || ownTz > 14*60 {
- return -1, ECGO_INVALID_DATETIME_FORMAT.throw()
- }
- }
- dt[OFFSET_YEAR] = year + 1900
- dt[OFFSET_MONTH] = month + 1
- if day == 0 {
- dt[OFFSET_DAY] = 1
- } else {
- dt[OFFSET_DAY] = day
- }
- dt[OFFSET_HOUR] = hour
- dt[OFFSET_MINUTE] = minute
- dt[OFFSET_SECOND] = second
- dt[OFFSET_NANOSECOND] = a_nanos
- dt[OFFSET_TIMEZONE] = int(ownTz)
- return dtype, nil
- }
- func transformTZ(dt []int, defaultSrcTz int, destTz int) {
- srcTz := defaultSrcTz
- if srcTz != INVALID_VALUE && destTz != INVALID_VALUE && destTz != srcTz {
- dt = addMinute(dt, destTz-srcTz)
- dt[OFFSET_TIMEZONE] = destTz
- }
- }
- func encode(dt []int, column column, lTz int, dTz int) ([]byte, error) {
- if dt[OFFSET_TIMEZONE] != INVALID_VALUE {
- transformTZ(dt, dt[OFFSET_TIMEZONE], lTz)
- }
- if column.mask == MASK_LOCAL_DATETIME {
- transformTZ(dt, dt[OFFSET_TIMEZONE], dTz)
- }
- if dt[OFFSET_YEAR] < -4712 || dt[OFFSET_YEAR] > 9999 {
- return nil, ECGO_DATETIME_OVERFLOW.throw()
- }
- year := dt[OFFSET_YEAR]
- month := dt[OFFSET_MONTH]
- day := dt[OFFSET_DAY]
- hour := dt[OFFSET_HOUR]
- min := dt[OFFSET_MINUTE]
- sec := dt[OFFSET_SECOND]
- msec := dt[OFFSET_NANOSECOND]
- var tz int
- if dt[OFFSET_TIMEZONE] == INVALID_VALUE {
- tz = dTz
- } else {
- tz = dt[OFFSET_TIMEZONE]
- }
- var ret []byte
- if column.colType == DATE {
- ret = make([]byte, 3)
- ret[0] = (byte)(year & 0xFF)
- if year >= 0 {
- ret[1] = (byte)((year >> 8) | ((month & 0x01) << 7))
- } else {
- ret[1] = (byte)((year >> 8) & (((month & 0x01) << 7) | 0x7f))
- }
- ret[2] = (byte)(((month & 0x0E) >> 1) | (day << 3))
- } else if column.colType == DATETIME {
- msec /= 1000
- ret = make([]byte, 8)
- ret[0] = (byte)(year & 0xFF)
- if year >= 0 {
- ret[1] = (byte)((year >> 8) | ((month & 0x01) << 7))
- } else {
- ret[1] = (byte)((year >> 8) & (((month & 0x01) << 7) | 0x7f))
- }
- ret[2] = (byte)(((month & 0x0E) >> 1) | (day << 3))
- ret[3] = (byte)(hour | ((min & 0x07) << 5))
- ret[4] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[5] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[6] = (byte)((msec >> 7) & 0xFF)
- ret[7] = (byte)((msec >> 15) & 0xFF)
- } else if column.colType == DATETIME2 {
- ret = make([]byte, 9)
- ret[0] = (byte)(year & 0xFF)
- if year >= 0 {
- ret[1] = (byte)((year >> 8) | ((month & 0x01) << 7))
- } else {
- ret[1] = (byte)((year >> 8) & (((month & 0x01) << 7) | 0x7f))
- }
- ret[2] = (byte)(((month & 0x0E) >> 1) | (day << 3))
- ret[3] = (byte)(hour | ((min & 0x07) << 5))
- ret[4] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[5] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[6] = (byte)((msec >> 7) & 0xFF)
- ret[7] = (byte)((msec >> 15) & 0xFF)
- ret[8] = (byte)((msec >> 23) & 0xFF)
- } else if column.colType == DATETIME_TZ {
- msec /= 1000
- ret = make([]byte, 10)
- ret[0] = (byte)(year & 0xFF)
- if year >= 0 {
- ret[1] = (byte)((year >> 8) | ((month & 0x01) << 7))
- } else {
- ret[1] = (byte)((year >> 8) & (((month & 0x01) << 7) | 0x7f))
- }
- ret[2] = (byte)(((month & 0x0E) >> 1) | (day << 3))
- ret[3] = (byte)(hour | ((min & 0x07) << 5))
- ret[4] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[5] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[6] = (byte)((msec >> 7) & 0xFF)
- ret[7] = (byte)((msec >> 15) & 0xFF)
- Dm_build_1.Dm_build_12(ret, 8, int16(tz))
- } else if column.colType == DATETIME2_TZ {
- ret = make([]byte, 11)
- ret[0] = (byte)(year & 0xFF)
- if year >= 0 {
- ret[1] = (byte)((year >> 8) | ((month & 0x01) << 7))
- } else {
- ret[1] = (byte)((year >> 8) & (((month & 0x01) << 7) | 0x7f))
- }
- ret[2] = (byte)(((month & 0x0E) >> 1) | (day << 3))
- ret[3] = (byte)(hour | ((min & 0x07) << 5))
- ret[4] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[5] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[6] = (byte)((msec >> 7) & 0xFF)
- ret[7] = (byte)((msec >> 15) & 0xFF)
- ret[8] = (byte)((msec >> 23) & 0xFF)
- Dm_build_1.Dm_build_12(ret, 8, int16(tz))
- } else if column.colType == TIME {
- msec /= 1000
- ret = make([]byte, 5)
- ret[0] = (byte)(hour | ((min & 0x07) << 5))
- ret[1] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[2] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[3] = (byte)((msec >> 7) & 0xFF)
- ret[4] = (byte)((msec >> 15) & 0xFF)
- } else if column.colType == TIME_TZ {
- msec /= 1000
- ret = make([]byte, 7)
- ret[0] = (byte)(hour | ((min & 0x07) << 5))
- ret[1] = (byte)(((min & 0x38) >> 3) | ((sec & 0x1F) << 3))
- ret[2] = (byte)(((sec & 0x20) >> 5) | ((msec & 0x7F) << 1))
- ret[3] = (byte)((msec >> 7) & 0xFF)
- ret[4] = (byte)((msec >> 15) & 0xFF)
- Dm_build_1.Dm_build_12(ret, 5, int16(tz))
- }
- return ret, nil
- }
- func toDate(x int64, column column, conn DmConnection) ([]byte, error) {
- switch column.colType {
- case DATETIME, DATETIME2:
- if x > 2958463*24*60*60 {
- return nil, ECGO_DATETIME_OVERFLOW.throw()
- }
- dt := toDTFromUnix(x-Seconds_1900_1970, 0)
- return encode(dt, column, int(conn.dmConnector.localTimezone), int(conn.DbTimezone))
- case TIME:
- dt := toDTFromUnix(x, 0)
- return encode(dt, column, int(conn.dmConnector.localTimezone), int(conn.DbTimezone))
- case DATE:
- if x > 2958463 {
- return nil, ECGO_DATETIME_OVERFLOW.throw()
- }
- dt := toDTFromUnix(x*24*60*60-Seconds_1900_1970, 0)
- if dt[OFFSET_YEAR] < -4712 || dt[OFFSET_YEAR] > 9999 {
- return nil, ECGO_DATETIME_OVERFLOW.throw()
- }
- return encode(dt, column, int(conn.dmConnector.localTimezone), int(conn.DbTimezone))
- default:
- return nil, ECGO_DATA_CONVERTION_ERROR.throw()
- }
- }
- func checkDate(year int, month int, day int) bool {
- if year > 9999 || year < -4712 || month > 12 || month < 1 {
- return false
- }
- monthDays := getDaysOfMonth(year, month)
- if day > monthDays || day < 1 {
- return false
- }
- return true
- }
- func getDaysOfMonth(year int, month int) int {
- switch month {
- case 1, 3, 5, 7, 8, 10, 12:
- return 31
- case 4, 6, 9, 11:
- return 30
- case 2:
- if isLeapYear(year) {
- return 29
- }
- return 28
- default:
- return 0
- }
- }
- func isLeapYear(year int) bool {
- return (year%4 == 0 && year%100 != 0) || year%400 == 0
- }
- func addYear(dt []int, n int) []int {
- dt[OFFSET_YEAR] += n
- return dt
- }
- func addMonth(dt []int, n int) []int {
- month := dt[OFFSET_MONTH] + n
- addYearValue := month / 12
- if month %= 12; month < 1 {
- month += 12
- addYearValue--
- }
- daysOfMonth := getDaysOfMonth(dt[OFFSET_YEAR], month)
- if dt[OFFSET_DAY] > daysOfMonth {
- dt[OFFSET_DAY] = daysOfMonth
- }
- dt[OFFSET_MONTH] = month
- addYear(dt, addYearValue)
- return dt
- }
- func addDay(dt []int, n int) []int {
- tmp := dt[OFFSET_DAY] + n
- monthDays := 0
- monthDays = getDaysOfMonth(dt[OFFSET_YEAR], dt[OFFSET_MONTH])
- for tmp > monthDays || tmp <= 0 {
- if tmp > monthDays {
- addMonth(dt, 1)
- tmp -= monthDays
- } else {
- addMonth(dt, -1)
- tmp += monthDays
- }
- }
- dt[OFFSET_DAY] = tmp
- return dt
- }
- func addHour(dt []int, n int) []int {
- hour := dt[OFFSET_HOUR] + n
- addDayValue := hour / 24
- if hour %= 24; hour < 0 {
- hour += 24
- addDayValue--
- }
- dt[OFFSET_HOUR] = hour
- addDay(dt, addDayValue)
- return dt
- }
- func addMinute(dt []int, n int) []int {
- minute := dt[OFFSET_MINUTE] + n
- addHourValue := minute / 60
- if minute %= 60; minute < 0 {
- minute += 60
- addHourValue--
- }
- dt[OFFSET_MINUTE] = minute
- addHour(dt, addHourValue)
- return dt
- }
|