Skip to content

Commit f3e6a60

Browse files
committedJun 4, 2014
PR done, all tests succeed and problematic ones are auto-skipped
1 parent db91787 commit f3e6a60

File tree

1 file changed

+54
-16
lines changed

1 file changed

+54
-16
lines changed
 

‎driver_test.go

+54-16
Original file line numberDiff line numberDiff line change
@@ -338,17 +338,28 @@ type timeTest struct {
338338
t time.Time
339339
}
340340

341+
func (t timeTest) genQuery(dbtype string, binaryProtocol bool) string {
342+
var inner string
343+
if binaryProtocol {
344+
inner = "?"
345+
} else {
346+
inner = `"%s"`
347+
}
348+
if len(dbtype) >= 9 && dbtype[:9] == "TIMESTAMP" {
349+
return `SELECT TIMESTAMPADD(SECOND,0,CAST(` + inner + ` AS DATETIME` + dbtype[9:] + `))`
350+
}
351+
return `SELECT CAST(` + inner + ` AS ` + dbtype + `)`
352+
}
353+
341354
func (t timeTest) run(dbt *DBTest, dbtype, tlayout string, binaryProtocol bool) {
342-
const queryBin = `SELECT CAST(? AS %[2]s)`
343-
const queryTxt = `SELECT CAST("%[1]s" AS %[2]s)`
344355
var rows *sql.Rows
345356
var protocol string
346-
if binaryProtocol {
357+
if query := t.genQuery(dbtype, binaryProtocol); binaryProtocol {
347358
protocol = "binary"
348-
rows = dbt.mustQuery(fmt.Sprintf(queryBin, t.s, dbtype), t.t)
359+
rows = dbt.mustQuery(query, t.t)
349360
} else {
350361
protocol = "text"
351-
rows = dbt.mustQuery(fmt.Sprintf(queryTxt, t.s, dbtype))
362+
rows = dbt.mustQuery(fmt.Sprintf(query, t.s))
352363
}
353364
defer rows.Close()
354365
var err error
@@ -396,16 +407,17 @@ func (t timeTest) run(dbt *DBTest, dbtype, tlayout string, binaryProtocol bool)
396407
}
397408

398409
func TestDateTime(t *testing.T) {
399-
afterTime0 := func(d string) time.Time {
410+
afterTime := func(t time.Time, d string) time.Time {
400411
dur, err := time.ParseDuration(d)
401412
if err != nil {
402413
panic(err)
403414
}
404-
return time.Time{}.Add(dur)
415+
return t.Add(dur)
405416
}
406417
// NOTE: MySQL rounds DATETIME(x) up - but that's not included in the tests
407418
format := "2006-01-02 15:04:05.999999"
408419
t0 := time.Time{}
420+
ts0 := time.Date(1970, 1, 1, 0, 0, 0, 0, time.UTC)
409421
tstr0 := "0000-00-00 00:00:00.000000"
410422
testcases := []timeTests{
411423
{"DATE", format[:10], []timeTest{
@@ -425,34 +437,61 @@ func TestDateTime(t *testing.T) {
425437
{t: t0, s: tstr0},
426438
}},
427439
{"TIME", format[11:19], []timeTest{
428-
{t: afterTime0("12345s")},
429-
{t: afterTime0("-12345s")},
440+
{t: afterTime(t0, "12345s")},
441+
{t: afterTime(t0, "-12345s")},
430442
{t: t0, s: tstr0[11:19]},
431443
}},
432444
{"TIME(1)", format[11:21], []timeTest{
433-
{t: afterTime0("12345600ms")},
434-
{t: afterTime0("-12345600ms")},
445+
{t: afterTime(t0, "12345600ms")},
446+
{t: afterTime(t0, "-12345600ms")},
435447
{t: t0, s: tstr0[11:21]},
436448
}},
437449
{"TIME(6)", format[11:], []timeTest{
438-
{t: afterTime0("1234567890123000ns")},
439-
{t: afterTime0("-1234567890123000ns")},
450+
{t: afterTime(t0, "1234567890123000ns")},
451+
{t: afterTime(t0, "-1234567890123000ns")},
440452
{t: t0, s: tstr0[11:]},
441453
}},
454+
{"TIMESTAMP", format[:19], []timeTest{
455+
{t: afterTime(ts0, "12345s")},
456+
{t: ts0, s: "1970-01-01 00:00:00"},
457+
}},
458+
{"TIMESTAMP(1)", format[:21], []timeTest{
459+
{t: afterTime(ts0, "12345600ms")},
460+
{t: ts0, s: "1970-01-01 00:00:00.0"},
461+
}},
462+
{"TIMESTAMP(6)", format, []timeTest{
463+
{t: afterTime(ts0, "1234567890123000ns")},
464+
{t: ts0, s: "1970-01-01 00:00:00.000000"},
465+
}},
442466
}
443467
dsns := map[string]bool{
444468
dsn + "&parseTime=true": true,
445469
dsn + "&sql_mode=ALLOW_INVALID_DATES&parseTime=true": true,
446470
dsn + "&parseTime=false": false,
447471
dsn + "&sql_mode=ALLOW_INVALID_DATES&parseTime=false": false,
448472
}
473+
var withFrac bool
474+
if db, err := sql.Open("mysql", dsn); err != nil {
475+
t.Fatal(err)
476+
} else {
477+
rows, err := db.Query(`SELECT CAST("00:00:00.123" AS TIME(3)) = "00:00:00.123"`)
478+
if err == nil {
479+
withFrac = true
480+
rows.Close()
481+
}
482+
db.Close()
483+
}
449484
for testdsn, parseTime := range dsns {
450485
var _ = parseTime
451486
runTests(t, testdsn, func(dbt *DBTest) {
452487
for _, setups := range testcases {
488+
if t := setups.dbtype; !withFrac && t[len(t)-1:] == ")" {
489+
// skip fractional tests if unsupported by DB
490+
continue
491+
}
453492
for _, setup := range setups.tests {
454493
if setup.s == "" {
455-
// fill time string where Go can reliable produce it
494+
// fill time string whereever Go can reliable produce it
456495
setup.s = setup.t.Format(setups.tlayout)
457496
}
458497
setup.run(dbt, setups.dbtype, setups.tlayout, true)
@@ -1053,9 +1092,8 @@ func TestTimezoneConversion(t *testing.T) {
10531092
dbt.mustExec("CREATE TABLE test (ts TIMESTAMP)")
10541093

10551094
// Insert local time into database (should be converted)
1056-
utc, _ := time.LoadLocation("UTC")
10571095
usCentral, _ := time.LoadLocation("US/Central")
1058-
reftime := time.Date(2014, 05, 30, 18, 03, 17, 0, utc).In(usCentral)
1096+
reftime := time.Date(2014, 05, 30, 18, 03, 17, 0, time.UTC).In(usCentral)
10591097
dbt.mustExec("INSERT INTO test VALUE (?)", reftime)
10601098

10611099
// Retrieve time from DB

0 commit comments

Comments
 (0)
Please sign in to comment.