testtime

package module
v0.3.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 23, 2024 License: MIT Imports: 5 Imported by: 3

README

testtime

pkg.go.dev

How to use

testtime package provides testtime.Now() and testtime.SetTime(). testtime.SetTime() stores a fixed time to a map with goroutine ID of testtime.SetTime() as a key. When goroutine ID of testtime.Now() is related to a fixed time by testtime.SetTime(), it returns the fixed time otherwise it returns current time which is returned by time.Now().

package main

import (
	"fmt"
	"time"
	"testing"

	"github.com/tenntenn/testtime"
)

func Test(t *testing.T) {

	t.Run("A", func(t *testing.T) {
		// set zero value
		testtime.SetTime(t, time.Time{})
		// true
		if time.Now().IsZero {
			t.Error("error")
		}
	})

	t.Run("B", func(t *testing.T) {
		// set func which return zero value
		f := func() time.Time {
			return time.Time{}
		}
		testtime.SetFunc(t, f)
		// true
		if time.Now().IsZero {
			t.Error("error")
		}
	})

	// false
	if !time.Now().IsZero {
		t.Error("error")
	}
}

The testtime command replace time.Now to testtime.Now. It prints a file path of overlay JSON which can be given to -overlay flag of go test command.

$ go install github.com/tenntenn/testtime/cmd/testtime@latest
$ go test -overlay=`testtime`
PASS
ok  	main	0.156s

The testtime command creates an overlay JSON file and time.go which is replaced time.Now in $GOPATH/pkg/testtime directory. The testtime command does not update these files without -u flag.

$ cat `testtime` | jq
{
  "Replace": {
    "/usr/local/go/src/time/time.go": "/Users/tenntenn/go/pkg/testtime/time_go1.23.1.go"
  }
}

$ diff /usr/local/go/src/time/time.go /Users/tenntenn/go/pkg/testtime/time_go1.23.1.go
94a95,96
> 	"runtime"
> 	"sync"
1159c1161
< func Now() Time {
---
> func _Now() Time {
1695a1698,1726
> 
> // It will be added to GOROOT/src/time/time.go.
> 
> //go:linkname timeMap
> var timeMap sync.Map
> 
> // Now returns a fixed time which is related with the goroutine by SetTime or SetFunc.
> // If the current goroutine is not related with any fixed time or function, Now calls time.Now and returns its returned value.
> func Now() Time {
> 	v, ok := timeMap.Load(goroutineID())
> 	if ok {
> 		return v.(func() Time)()
> 	}
> 	return _Now()
> }
> 
> func goroutineID() string {
> 	var buf [64]byte
> 	n := runtime.Stack(buf[:], false)
> 	// 10: len("goroutine ")
> 	for i := 10; i < n; i++ {
> 		if buf[i] == ' ' {
> 			return string(buf[10:i])
> 		}
> 	}
> 	return ""
> }
> 
> // End of testtime's code

Examples

See _examples directory.

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Now

func Now() time.Time

Now returns a fixed time which is related with the goroutine by SetTime or SetFunc. If the current goroutine is not related with any fixed time or function, Now calls time.Now and returns its returned value.

func Overlayed added in v0.3.0

func Overlayed() bool

Overlayed returns whether time.go in time package was overlayed by testtime or not.

func SetFunc added in v0.2.0

func SetFunc(t *testing.T, f func() time.Time)

SetFunc stores a function which returns time.Time which can be identified by the caller's goroutine. The function will be deleted at the end of test.

func SetTime added in v0.2.0

func SetTime(t *testing.T, tm time.Time)

SetTime stores a fixed time which can be identified by the caller's goroutine. The fixed time will be deleted at the end of test.

Types

This section is empty.

Directories

Path Synopsis
cmd
testtime command

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL