dep ensure

This commit is contained in:
Benjamin Elder
2018-10-24 17:24:58 -07:00
parent 41845522f6
commit 163515c5a0
6525 changed files with 84 additions and 3291220 deletions

View File

@@ -1 +0,0 @@
/coverage.txt

View File

@@ -1,14 +0,0 @@
language: go
go:
- 1.8.x
- 1.x
before_install:
- go get -t -v ./...
script:
- ./test.sh
after_success:
- bash <(curl -s https://codecov.io/bash)

View File

@@ -1,49 +0,0 @@
# concurrent
[![Sourcegraph](https://sourcegraph.com/github.com/modern-go/concurrent/-/badge.svg)](https://sourcegraph.com/github.com/modern-go/concurrent?badge)
[![GoDoc](http://img.shields.io/badge/go-documentation-blue.svg?style=flat-square)](http://godoc.org/github.com/modern-go/concurrent)
[![Build Status](https://travis-ci.org/modern-go/concurrent.svg?branch=master)](https://travis-ci.org/modern-go/concurrent)
[![codecov](https://codecov.io/gh/modern-go/concurrent/branch/master/graph/badge.svg)](https://codecov.io/gh/modern-go/concurrent)
[![rcard](https://goreportcard.com/badge/github.com/modern-go/concurrent)](https://goreportcard.com/report/github.com/modern-go/concurrent)
[![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://raw.githubusercontent.com/modern-go/concurrent/master/LICENSE)
* concurrent.Map: backport sync.Map for go below 1.9
* concurrent.Executor: goroutine with explicit ownership and cancellable
# concurrent.Map
because sync.Map is only available in go 1.9, we can use concurrent.Map to make code portable
```go
m := concurrent.NewMap()
m.Store("hello", "world")
elem, found := m.Load("hello")
// elem will be "world"
// found will be true
```
# concurrent.Executor
```go
executor := concurrent.NewUnboundedExecutor()
executor.Go(func(ctx context.Context) {
everyMillisecond := time.NewTicker(time.Millisecond)
for {
select {
case <-ctx.Done():
fmt.Println("goroutine exited")
return
case <-everyMillisecond.C:
// do something
}
}
})
time.Sleep(time.Second)
executor.StopAndWaitForever()
fmt.Println("executor stopped")
```
attach goroutine to executor instance, so that we can
* cancel it by stop the executor with Stop/StopAndWait/StopAndWaitForever
* handle panic by callback: the default behavior will no longer crash your application

View File

@@ -1,18 +0,0 @@
package concurrent_test
import (
"github.com/modern-go/concurrent"
"testing"
)
func TestMap_Load(t *testing.T) {
m := concurrent.NewMap()
m.Store("hello", "world")
value, found := m.Load("hello")
if !found {
t.Fail()
}
if value != "world" {
t.Fail()
}
}

View File

@@ -1,12 +0,0 @@
#!/usr/bin/env bash
set -e
echo "" > coverage.txt
for d in $(go list ./... | grep -v vendor); do
go test -coverprofile=profile.out -coverpkg=github.com/modern-go/concurrent $d
if [ -f profile.out ]; then
cat profile.out >> coverage.txt
rm profile.out
fi
done

View File

@@ -1,54 +0,0 @@
package concurrent_test
import (
"context"
"fmt"
"time"
"github.com/modern-go/concurrent"
)
func ExampleUnboundedExecutor_Go() {
executor := concurrent.NewUnboundedExecutor()
executor.Go(func(ctx context.Context) {
fmt.Println("abc")
})
time.Sleep(time.Second)
// output: abc
}
func ExampleUnboundedExecutor_StopAndWaitForever() {
executor := concurrent.NewUnboundedExecutor()
executor.Go(func(ctx context.Context) {
everyMillisecond := time.NewTicker(time.Millisecond)
for {
select {
case <-ctx.Done():
fmt.Println("goroutine exited")
return
case <-everyMillisecond.C:
// do something
}
}
})
time.Sleep(time.Second)
executor.StopAndWaitForever()
fmt.Println("executor stopped")
// output:
// goroutine exited
// executor stopped
}
func ExampleUnboundedExecutor_Go_panic() {
concurrent.HandlePanic = func(recovered interface{}, funcName string) {
fmt.Println(funcName)
}
executor := concurrent.NewUnboundedExecutor()
executor.Go(willPanic)
time.Sleep(time.Second)
// output:
// github.com/modern-go/concurrent_test.willPanic
}
func willPanic(ctx context.Context) {
panic("!!!")
}

View File

@@ -1 +0,0 @@
/vendor

View File

@@ -1,15 +0,0 @@
# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
[[projects]]
name = "github.com/modern-go/concurrent"
packages = ["."]
revision = "e0a39a4cb4216ea8db28e22a69f4ec25610d513a"
version = "1.0.0"
[solve-meta]
analyzer-name = "dep"
analyzer-version = 1
inputs-digest = "daee8a88b3498b61c5640056665b8b9eea062006f5e596bbb6a3ed9119a11ec7"
solver-name = "gps-cdcl"
solver-version = 1

View File

@@ -1,35 +0,0 @@
# Gopkg.toml example
#
# Refer to https://golang.github.io/dep/docs/Gopkg.toml.html
# for detailed Gopkg.toml documentation.
#
# required = ["github.com/user/thing/cmd/thing"]
# ignored = ["github.com/user/project/pkgX", "bitbucket.org/user/project/pkgA/pkgY"]
#
# [[constraint]]
# name = "github.com/user/project"
# version = "1.0.0"
#
# [[constraint]]
# name = "github.com/user/project2"
# branch = "dev"
# source = "github.com/myfork/project2"
#
# [[override]]
# name = "github.com/x/y"
# version = "2.4.0"
#
# [prune]
# non-go = false
# go-tests = true
# unused-packages = true
ignored = ["github.com/modern-go/test","github.com/modern-go/test/must","github.com/modern-go/test/should"]
[[constraint]]
name = "github.com/modern-go/concurrent"
version = "1.0.0"
[prune]
go-tests = true
unused-packages = true

View File

@@ -1,2 +0,0 @@
# reflect2
reflect api that avoids runtime reflect.Value cost

View File

@@ -1,18 +0,0 @@
package test
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_map(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
valType := reflect2.TypeOf(map[int]int{}).(reflect2.MapType)
m := map[int]int{}
valType.SetIndex(&m, pInt(1), pInt(1))
if m[1] != 1 {
t.Fail()
}
}

View File

@@ -1,38 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_array(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("New", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([2]int{})
obj := valType.New()
(*(obj.(*[2]int)))[0] = 100
(*(obj.(*[2]int)))[1] = 200
return obj
}))
t.Run("Indirect", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([2]int{})
return valType.Indirect(&[2]int{})
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := [2]int{}
valType := api.TypeOf(obj).(reflect2.ArrayType)
valType.SetIndex(&obj, 0, pInt(100))
valType.SetIndex(&obj, 1, pInt(200))
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := [2]int{1, 2}
valType := api.TypeOf(obj).(reflect2.ArrayType)
return []interface{} {
valType.GetIndex(&obj, 0),
valType.GetIndex(&obj, 1),
}
}))
}

View File

@@ -1,41 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"unsafe"
"github.com/modern-go/test/must"
"context"
)
func Test_int(t *testing.T) {
t.Run("New", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(1)
obj := valType.New()
*obj.(*int) = 100
return obj
}))
t.Run("PackEFace", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(1)
hundred := 100
must.Equal(&hundred, valType.PackEFace(unsafe.Pointer(&hundred)))
}))
t.Run("Indirect", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(1)
hundred := 100
must.Equal(100, valType.Indirect(&hundred))
}))
t.Run("Indirect", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(1)
hundred := 100
must.Equal(100, valType.UnsafeIndirect(unsafe.Pointer(&hundred)))
}))
t.Run("Set", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(1)
i := 1
j := 10
valType.Set(&i, &j)
return i
}))
}

View File

@@ -1,44 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_map_elem_array(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int][2]*int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, [2]*int{(*int)(reflect2.PtrOf(1)), (*int)(reflect2.PtrOf(2))})
valType.SetIndex(obj, 3, [2]*int{(*int)(reflect2.PtrOf(3)), (*int)(reflect2.PtrOf(4))})
return obj
}))
t.Run("SetIndex zero length array", testOp(func(api reflect2.API) interface{} {
obj := map[int][0]*int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, [0]*int{})
valType.SetIndex(obj, 3, [0]*int{})
return obj
}))
t.Run("SetIndex single ptr array", testOp(func(api reflect2.API) interface{} {
obj := map[int][1]*int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, [1]*int{(*int)(reflect2.PtrOf(1))})
valType.SetIndex(obj, 3, [1]*int{})
return obj
}))
t.Run("SetIndex single chan array", testOp(func(api reflect2.API) interface{} {
obj := map[int][1]chan int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, [1]chan int{})
valType.SetIndex(obj, 3, [1]chan int{})
return obj
}))
t.Run("SetIndex single func array", testOp(func(api reflect2.API) interface{} {
obj := map[int][1]func(){}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, [1]func(){})
valType.SetIndex(obj, 3, [1]func(){})
return obj
}))
}

View File

@@ -1,34 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"github.com/modern-go/test/must"
"context"
)
func Test_map_elem_bytes(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int][]byte{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, []byte("hello"))
valType.SetIndex(obj, 3, nil)
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := map[int][]byte{}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
hello := []byte("hello")
valType.UnsafeSetIndex(reflect2.PtrOf(obj), reflect2.PtrOf(2), reflect2.PtrOf(hello))
valType.UnsafeSetIndex(reflect2.PtrOf(obj), reflect2.PtrOf(3), nil)
must.Equal([]byte("hello"), obj[2])
must.Nil(obj[3])
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := map[int][]byte{2: []byte("hello")}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
elem := valType.UnsafeGetIndex(reflect2.PtrOf(obj), reflect2.PtrOf(2))
must.Equal([]byte("hello"), valType.Elem().PackEFace(elem))
}))
}

View File

@@ -1,51 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
"github.com/modern-go/test"
"context"
)
func Test_map_elem_eface(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]interface{}{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, 4)
valType.SetIndex(obj, 3, nil)
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]interface{}{3: 9, 2: nil}
valType := api.TypeOf(obj).(reflect2.MapType)
return []interface{}{
valType.GetIndex(obj, 3),
valType.GetIndex(obj, 2),
valType.GetIndex(obj, 0),
}
}))
t.Run("TryGetIndex", test.Case(func(ctx context.Context) {
obj := map[int]interface{}{3: 9, 2: nil}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
elem, found := valType.TryGetIndex(obj, 3)
must.Equal(9, elem)
must.Pass(found)
elem, found = valType.TryGetIndex(obj, 2)
must.Nil(elem)
must.Pass(found)
elem, found = valType.TryGetIndex(obj, 0)
must.Nil(elem)
must.Pass(!found)
}))
t.Run("Iterate", testOp(func(api reflect2.API) interface{} {
obj := map[int]interface{}{2: 4}
valType := api.TypeOf(obj).(reflect2.MapType)
iter := valType.Iterate(obj)
must.Pass(iter.HasNext(), "api", api)
key1, elem1 := iter.Next()
must.Pass(!iter.HasNext(), "api", api)
return []interface{}{key1, elem1}
}))
}

View File

@@ -1,23 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_map_elem_map(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
var pMap = func(val map[int]int) *map[int]int {
return &val
}
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]map[int]int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(&obj, pInt(2), pMap(map[int]int{4:4}))
valType.SetIndex(&obj, pInt(3), pMap(map[int]int{9:9}))
valType.SetIndex(&obj, pInt(3), pMap(nil))
return obj
}))
}

View File

@@ -1,57 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"time"
)
func Test_map_elem_struct(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]time.Time{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, time.Time{})
valType.SetIndex(obj, 3, time.Time{})
return obj
}))
t.Run("SetIndex single ptr struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 *int
}
obj := map[int]TestObject{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, TestObject{})
valType.SetIndex(obj, 3, TestObject{})
return obj
}))
t.Run("SetIndex single map struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 map[int]int
}
obj := map[int]TestObject{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, TestObject{})
valType.SetIndex(obj, 3, TestObject{})
return obj
}))
t.Run("SetIndex single chan struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 chan int
}
obj := map[int]TestObject{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, TestObject{})
valType.SetIndex(obj, 3, TestObject{})
return obj
}))
t.Run("SetIndex single func struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 func()
}
obj := map[int]TestObject{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, 2, TestObject{})
valType.SetIndex(obj, 3, TestObject{})
return obj
}))
}

View File

@@ -1,43 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
)
func Test_map_key_eface(t *testing.T) {
var pEFace = func(val interface{}) interface{} {
return &val
}
var pInt = func(val int) *int {
return &val
}
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[interface{}]int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(&obj, pEFace(2), pInt(4))
valType.SetIndex(&obj, pEFace(3), pInt(9))
valType.SetIndex(&obj, pEFace(nil), pInt(9))
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[interface{}]int{3: 9, 2: 4}
valType := api.TypeOf(obj).(reflect2.MapType)
return []interface{}{
valType.GetIndex(&obj, pEFace(3)),
valType.GetIndex(&obj, pEFace(0)),
valType.GetIndex(&obj, pEFace(nil)),
valType.GetIndex(&obj, pEFace("")),
}
}))
t.Run("Iterate", testOp(func(api reflect2.API) interface{} {
obj := map[interface{}]int{2: 4}
valType := api.TypeOf(obj).(reflect2.MapType)
iter := valType.Iterate(obj)
must.Pass(iter.HasNext(), "api", api)
key1, elem1 := iter.Next()
must.Pass(!iter.HasNext(), "api", api)
return []interface{}{key1, elem1}
}))
}

View File

@@ -1,47 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
)
type intError int
func (err intError) Error() string {
return ""
}
func Test_map_iface_key(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[error]int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(obj, intError(2), 4)
valType.SetIndex(obj, intError(2), 9)
valType.SetIndex(obj, nil, 9)
must.Panic(func() {
valType.SetIndex(obj, "", 9)
})
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[error]int{intError(3): 9, intError(2): 4}
valType := api.TypeOf(obj).(reflect2.MapType)
must.Panic(func() {
valType.GetIndex(obj, "")
})
return []interface{}{
valType.GetIndex(obj, intError(3)),
valType.GetIndex(obj, nil),
}
}))
t.Run("Iterate", testOp(func(api reflect2.API) interface{} {
obj := map[error]int{intError(2): 4}
valType := api.TypeOf(obj).(reflect2.MapType)
iter := valType.Iterate(obj)
must.Pass(iter.HasNext(), "api", api)
key1, elem1 := iter.Next()
must.Pass(!iter.HasNext(), "api", api)
return []interface{}{key1, elem1}
}))
}

View File

@@ -1,51 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
"github.com/modern-go/test"
"unsafe"
"context"
)
func Test_map_key_ptr(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[*int]int{}
valType := api.TypeOf(obj).(reflect2.MapType)
key := pInt(2)
valType.SetIndex(obj, &key, 4)
valType.SetIndex(obj, &key, 9)
//valType.SetIndex(obj, nil, 9)
return obj[pInt(2)]
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := map[*int]int{}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
v := pInt(2)
valType.UnsafeSetIndex(reflect2.PtrOf(obj), unsafe.Pointer(v), reflect2.PtrOf(4))
must.Equal(4, obj[v])
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[*int]int{pInt(3): 9, pInt(2): 4}
valType := api.TypeOf(obj).(reflect2.MapType)
return []interface{}{
valType.GetIndex(obj, pInt(3)),
valType.GetIndex(obj, pInt(2)),
valType.GetIndex(obj, nil),
}
}))
t.Run("Iterate", testOp(func(api reflect2.API) interface{} {
obj := map[*int]int{pInt(2): 4}
valType := api.TypeOf(obj).(reflect2.MapType)
iter := valType.Iterate(&obj)
must.Pass(iter.HasNext(), "api", api)
key1, elem1 := iter.Next()
must.Pass(!iter.HasNext(), "api", api)
return []interface{}{key1, elem1}
}))
}

View File

@@ -1,121 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
"github.com/modern-go/test"
"unsafe"
"reflect"
"context"
)
func Test_map(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("New", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(map[int]int{})
m := valType.New().(*map[int]int)
return m
}))
t.Run("IsNil", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(map[int]int{})
var nilMap map[int]int
m := map[int]int{}
return []interface{}{
valType.IsNil(&nilMap),
valType.IsNil(&m),
}
}))
t.Run("MakeMap", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(map[int]int{}).(reflect2.MapType)
m := *(valType.MakeMap(0).(*map[int]int))
m[2] = 4
m[3] = 9
return m
}))
t.Run("UnsafeMakeMap", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(map[int]int{}).(reflect2.MapType)
m := *(*map[int]int)(valType.UnsafeMakeMap(0))
m[2] = 4
m[3] = 9
}))
t.Run("PackEFace", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(map[int]int{}).(reflect2.MapType)
m := valType.UnsafeMakeMap(0)
must.Equal(&map[int]int{}, valType.PackEFace(unsafe.Pointer(m)))
}))
t.Run("Indirect", testOp(func(api reflect2.API) interface{} {
valType := reflect2.TypeOf(map[int]int{})
return valType.Indirect(&map[int]int{})
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]int{}
valType := api.TypeOf(obj).(reflect2.MapType)
valType.SetIndex(&obj, pInt(2), pInt(4))
valType.SetIndex(&obj, pInt(3), pInt(9))
must.Equal(4, obj[2])
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := map[int]int{}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
valType.UnsafeSetIndex(unsafe.Pointer(&obj), reflect2.PtrOf(2), reflect2.PtrOf(4))
must.Equal(map[int]int{2: 4}, obj)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := map[int]int{3: 9, 2: 4}
valType := api.TypeOf(obj).(reflect2.MapType)
return []interface{}{
*valType.GetIndex(&obj, pInt(3)).(*int),
valType.GetIndex(&obj, pInt(0)).(*int),
}
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := map[int]int{3: 9, 2: 4}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
elem := valType.UnsafeGetIndex(unsafe.Pointer(&obj), reflect2.PtrOf(3))
must.Equal(9, *(*int)(elem))
}))
t.Run("Iterate", testOp(func(api reflect2.API) interface{} {
obj := map[int]int{2: 4}
valType := api.TypeOf(obj).(reflect2.MapType)
iter := valType.Iterate(&obj)
must.Pass(iter.HasNext(), "api", api)
key1, elem1 := iter.Next()
must.Pass(!iter.HasNext(), "api", api)
return []interface{}{key1, elem1}
}))
t.Run("UnsafeIterate", test.Case(func(ctx context.Context) {
obj := map[int]int{2: 4}
valType := reflect2.TypeOf(obj).(reflect2.MapType)
iter := valType.UnsafeIterate(unsafe.Pointer(&obj))
must.Pass(iter.HasNext())
key, elem := iter.UnsafeNext()
must.Equal(2, *(*int)(key))
must.Equal(4, *(*int)(elem))
}))
}
func Benchmark_map_unsafe(b *testing.B) {
obj := map[int]int{}
valType := reflect2.TypeOf(obj).(*reflect2.UnsafeMapType)
m := unsafe.Pointer(&obj)
b.ReportAllocs()
b.ResetTimer()
for i := 0; i < b.N; i++ {
valType.UnsafeSetIndex(m, reflect2.PtrOf(2), reflect2.PtrOf(4))
}
}
func Benchmark_map_safe(b *testing.B) {
obj := map[int]int{}
val := reflect.ValueOf(obj)
b.ReportAllocs()
b.ResetTimer()
for i := 0; i < b.N; i++ {
val.SetMapIndex(reflect.ValueOf(2), reflect.ValueOf(4))
}
}

View File

@@ -1,18 +0,0 @@
package tests
import (
"github.com/modern-go/reflect2"
"testing"
"github.com/modern-go/test/must"
"github.com/modern-go/test"
"context"
)
func testOp(f func(api reflect2.API) interface{}) func(t *testing.T) {
return test.Case(func(ctx context.Context) {
unsafeResult := f(reflect2.ConfigUnsafe)
safeResult := f(reflect2.ConfigSafe)
must.Equal(safeResult, unsafeResult)
})
}

View File

@@ -1,37 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_slice_array(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := [][1]int{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, [1]int{1})
valType.SetIndex(obj, 1, [1]int{2})
return obj
}))
t.Run("SetIndex single ptr struct", testOp(func(api reflect2.API) interface{} {
obj := [][1]*int{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, [1]*int{})
valType.SetIndex(obj, 1, [1]*int{})
return obj
}))
t.Run("SetIndex single chan struct", testOp(func(api reflect2.API) interface{} {
obj := [][1]chan int{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, [1]chan int{})
valType.SetIndex(obj, 1, [1]chan int{})
return obj
}))
t.Run("SetIndex single func struct", testOp(func(api reflect2.API) interface{} {
obj := [][1]func(){{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, [1]func(){})
valType.SetIndex(obj, 1, [1]func(){})
return obj
}))
}

View File

@@ -1,16 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_slice_bytes(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := [][]byte{[]byte("hello"), []byte("world")}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(&obj, 0, []byte("hi"))
valType.SetIndex(&obj, 1, []byte("there"))
return obj
}))
}

View File

@@ -1,78 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"github.com/modern-go/test/must"
"unsafe"
"github.com/modern-go/test/should"
"fmt"
"context"
)
func Test_slice_eface(t *testing.T) {
t.Run("MakeSlice", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]interface{}{}).(reflect2.SliceType)
obj := valType.MakeSlice(5, 10)
obj.([]interface{})[0] = 100
obj.([]interface{})[4] = 20
return obj
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []interface{}{1, nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
elem0 := interface{}(100)
valType.SetIndex(obj, 0, &elem0)
elem1 := interface{}(20)
valType.SetIndex(obj, 1, &elem1)
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := []interface{}{1, 2}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
var elem0 interface{} = 100
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 0, unsafe.Pointer(&elem0))
var elem1 interface{} = 10
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 1, unsafe.Pointer(&elem1))
must.Equal([]interface{}{100, 10}, obj)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := []interface{}{1, nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
fmt.Println(api, *valType.GetIndex(obj, 0).(*interface{}))
return []interface{}{
valType.GetIndex(obj, 0),
valType.GetIndex(obj, 1),
}
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := []interface{}{1, nil}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
elem0 := valType.UnsafeGetIndex(reflect2.PtrOf(obj), 0)
must.Equal(1, *(*interface{})(elem0))
}))
t.Run("Append", testOp(func(api reflect2.API) interface{} {
obj := make([]interface{}, 2, 3)
obj[0] = 1
obj[1] = 2
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.Append(&obj, 3)
// will trigger grow
valType.Append(&obj, 4)
return obj
}))
t.Run("UnsafeAppend", test.Case(func(ctx context.Context) {
obj := make([]interface{}, 2, 3)
obj[0] = 1
obj[1] = 2
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
ptr := reflect2.PtrOf(obj)
var elem2 interface{} = 3
valType.UnsafeAppend(ptr, unsafe.Pointer(&elem2))
var elem3 interface{} = 4
valType.UnsafeAppend(ptr, unsafe.Pointer(&elem3))
should.Equal([]interface{}{1, 2, 3, 4}, valType.PackEFace(ptr))
}))
}

View File

@@ -1,81 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"errors"
"github.com/modern-go/test"
"unsafe"
"github.com/modern-go/test/must"
"context"
)
func Test_slice_iface(t *testing.T) {
var pError = func(msg string) *error {
err := errors.New(msg)
return &err
}
t.Run("MakeSlice", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]error{}).(reflect2.SliceType)
obj := *(valType.MakeSlice(5, 10).(*[]error))
obj[0] = errors.New("hello")
obj[4] = errors.New("world")
return obj
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []error{errors.New("hello"), nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(&obj, 0, pError("hi"))
valType.SetIndex(&obj, 1, pError("world"))
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := []error{errors.New("hello"), nil}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
elem0 := errors.New("hi")
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 0, unsafe.Pointer(&elem0))
elem1 := errors.New("world")
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 1, unsafe.Pointer(&elem1))
must.Equal([]error{elem0, elem1}, obj)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := []error{errors.New("hello"), nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
return []interface{}{
valType.GetIndex(&obj, 0),
valType.GetIndex(&obj, 1),
}
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := []error{errors.New("hello"), nil}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
elem0 := valType.UnsafeGetIndex(reflect2.PtrOf(obj), 0)
must.Equal(errors.New("hello"), *(*error)(elem0))
}))
t.Run("Append", testOp(func(api reflect2.API) interface{} {
obj := make([]error, 2, 3)
obj[0] = errors.New("1")
obj[1] = errors.New("2")
valType := api.TypeOf(obj).(reflect2.SliceType)
ptr := &obj
valType.Append(ptr, pError("3"))
// will trigger grow
valType.Append(ptr, pError("4"))
return ptr
}))
t.Run("UnsafeAppend", test.Case(func(ctx context.Context) {
obj := make([]error, 2, 3)
obj[0] = errors.New("1")
obj[1] = errors.New("2")
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
ptr := reflect2.PtrOf(obj)
elem2 := errors.New("3")
valType.UnsafeAppend(ptr, unsafe.Pointer(&elem2))
elem3 := errors.New("4")
valType.UnsafeAppend(ptr, unsafe.Pointer(&elem3))
must.Equal(&[]error{
obj[0], obj[1], elem2, elem3,
}, valType.PackEFace(ptr))
}))
}

View File

@@ -1,43 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_slice_map(t *testing.T) {
t.Run("MakeSlice", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]map[int]int{}).(reflect2.SliceType)
obj := valType.MakeSlice(5, 10)
obj.([]map[int]int)[0] = map[int]int{1:1}
obj.([]map[int]int)[4] = map[int]int{2:2}
return obj
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []map[int]int{{1: 1}, nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, &map[int]int{10:10})
valType.SetIndex(obj, 1, &map[int]int{2:2})
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := []map[int]int{{1:1}, nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
return []interface{}{
valType.GetIndex(&obj, 0),
valType.GetIndex(&obj, 1),
valType.GetIndex(obj, 0),
valType.GetIndex(obj, 1),
}
}))
t.Run("Append", testOp(func(api reflect2.API) interface{} {
obj := make([]map[int]int, 2, 3)
obj[0] = map[int]int{1:1}
obj[1] = map[int]int{2:2}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.Append(obj, map[int]int{3:3})
// will trigger grow
valType.Append(obj, map[int]int{4:4})
return obj
}))
}

View File

@@ -1,58 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"unsafe"
"github.com/modern-go/test/must"
"context"
)
func Test_slice_ptr(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("MakeSlice", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]*int{}).(reflect2.SliceType)
obj := valType.MakeSlice(5, 10)
obj.([]*int)[0] = pInt(1)
obj.([]*int)[4] = pInt(5)
return obj
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []*int{pInt(1), nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, pInt(2))
valType.SetIndex(obj, 1, pInt(3))
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := []*int{pInt(1), nil}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 0, unsafe.Pointer(pInt(2)))
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 1, unsafe.Pointer(pInt(1)))
must.Equal([]*int{pInt(2), pInt(1)}, obj)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := []*int{pInt(1), nil}
valType := api.TypeOf(obj).(reflect2.SliceType)
return []interface{}{
valType.GetIndex(&obj, 0),
valType.GetIndex(&obj, 1),
valType.GetIndex(obj, 0),
valType.GetIndex(obj, 1),
}
}))
t.Run("Append", testOp(func(api reflect2.API) interface{} {
obj := make([]*int, 2, 3)
obj[0] = pInt(1)
obj[1] = pInt(2)
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.Append(obj, pInt(3))
// will trigger grow
valType.Append(obj, pInt(4))
return obj
}))
}

View File

@@ -1,16 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_slice_string(t *testing.T) {
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []string{"hello", "world"}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(&obj, 0, "hi")
valType.SetIndex(&obj, 1, "there")
return obj
}))
}

View File

@@ -1,53 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_slice_struct(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 float64
Field2 float64
}
obj := []TestObject{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, &TestObject{1, 3})
valType.SetIndex(obj, 1, &TestObject{2, 4})
return obj
}))
t.Run("SetIndex single ptr struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 *int
}
obj := []TestObject{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, &TestObject{pInt(1)})
valType.SetIndex(obj, 1, &TestObject{pInt(2)})
return obj
}))
t.Run("SetIndex single chan struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 chan int
}
obj := []TestObject{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, TestObject{})
valType.SetIndex(obj, 1, TestObject{})
return obj
}))
t.Run("SetIndex single func struct", testOp(func(api reflect2.API) interface{} {
type TestObject struct {
Field1 func()
}
obj := []TestObject{{}, {}}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(obj, 0, TestObject{})
valType.SetIndex(obj, 1, TestObject{})
return obj
}))
}

View File

@@ -1,115 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"github.com/modern-go/test/must"
"context"
)
func Test_slice(t *testing.T) {
var pInt = func(val int) *int {
return &val
}
t.Run("New", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]int{})
obj := *valType.New().(*[]int)
obj = append(obj, 1)
return obj
}))
t.Run("IsNil", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]int{})
var nilSlice []int
s := []int{}
return []interface{}{
valType.IsNil(&nilSlice),
valType.IsNil(&s),
valType.IsNil(nil),
}
}))
t.Run("SetNil", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]int{}).(reflect2.SliceType)
s := []int{1}
valType.SetNil(&s)
return s
}))
t.Run("Set", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]int{}).(reflect2.SliceType)
s1 := []int{1}
s2 := []int{2}
valType.Set(&s1, &s2)
return s1
}))
t.Run("MakeSlice", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf([]int{}).(reflect2.SliceType)
obj := *(valType.MakeSlice(5, 10).(*[]int))
obj[0] = 100
obj[4] = 20
return obj
}))
t.Run("UnsafeMakeSlice", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf([]int{}).(reflect2.SliceType)
obj := valType.UnsafeMakeSlice(5, 10)
must.Equal(&[]int{0, 0, 0, 0, 0}, valType.PackEFace(obj))
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
obj := []int{1, 2}
valType := api.TypeOf(obj).(reflect2.SliceType)
valType.SetIndex(&obj, 0, pInt(100))
valType.SetIndex(&obj, 1, pInt(20))
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
obj := []int{1, 2}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 0, reflect2.PtrOf(100))
valType.UnsafeSetIndex(reflect2.PtrOf(obj), 1, reflect2.PtrOf(10))
must.Equal([]int{100, 10}, obj)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := []int{1, 2}
valType := api.TypeOf(obj).(reflect2.SliceType)
return []interface{}{
valType.GetIndex(&obj, 1).(*int),
}
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := []int{1, 2}
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
elem0 := valType.UnsafeGetIndex(reflect2.PtrOf(obj), 0)
must.Equal(1, *(*int)(elem0))
elem1 := valType.UnsafeGetIndex(reflect2.PtrOf(obj), 1)
must.Equal(2, *(*int)(elem1))
}))
t.Run("Append", testOp(func(api reflect2.API) interface{} {
obj := make([]int, 2, 3)
obj[0] = 1
obj[1] = 2
valType := api.TypeOf(obj).(reflect2.SliceType)
ptr := &obj
valType.Append(ptr, pInt(3))
// will trigger grow
valType.Append(ptr, pInt(4))
return ptr
}))
t.Run("UnsafeAppend", test.Case(func(ctx context.Context) {
obj := make([]int, 2, 3)
obj[0] = 1
obj[1] = 2
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
ptr := reflect2.PtrOf(obj)
valType.UnsafeAppend(ptr, reflect2.PtrOf(3))
valType.UnsafeAppend(ptr, reflect2.PtrOf(4))
must.Equal(&[]int{1, 2, 3, 4}, valType.PackEFace(ptr))
}))
t.Run("Grow", testOp(func(api reflect2.API) interface{} {
obj := make([]int, 2, 3)
obj[0] = 1
obj[1] = 2
valType := reflect2.TypeOf(obj).(reflect2.SliceType)
valType.Grow(&obj, 4)
return obj
}))
}

View File

@@ -1,28 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
)
func Test_struct_eface(t *testing.T) {
type TestObject struct {
Field1 interface{}
}
var pEFace = func(val interface{}) interface{} {
return &val
}
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(TestObject{}).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
obj := TestObject{}
field1.Set(&obj, pEFace(100))
return obj
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := TestObject{Field1: 100}
valType := api.TypeOf(obj).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
return field1.Get(&obj)
}))
}

View File

@@ -1,25 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test/must"
"github.com/modern-go/test"
"context"
)
func Test_struct_ptr(t *testing.T) {
type TestObject struct {
Field1 *int
}
t.Run("PackEFace", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(TestObject{})
ptr := valType.UnsafeNew()
must.Equal(&TestObject{}, valType.PackEFace(ptr))
}))
t.Run("Indirect", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(TestObject{})
must.Equal(TestObject{}, valType.Indirect(&TestObject{}))
}))
}

View File

@@ -1,64 +0,0 @@
package tests
import (
"testing"
"github.com/modern-go/reflect2"
"github.com/modern-go/test"
"unsafe"
"github.com/modern-go/test/must"
"context"
)
func Test_struct(t *testing.T) {
type TestObject struct {
Field1 int
Field2 int
}
var pInt = func(val int) *int {
return &val
}
t.Run("New", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(TestObject{})
obj := valType.New()
obj.(*TestObject).Field1 = 20
obj.(*TestObject).Field2 = 100
return obj
}))
t.Run("PackEFace", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(TestObject{})
ptr := valType.UnsafeNew()
must.Equal(&TestObject{}, valType.PackEFace(ptr))
}))
t.Run("Indirect", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(TestObject{})
must.Equal(TestObject{}, valType.Indirect(&TestObject{}))
}))
t.Run("SetIndex", testOp(func(api reflect2.API) interface{} {
valType := api.TypeOf(TestObject{}).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
obj := TestObject{}
field1.Set(&obj, pInt(100))
return obj
}))
t.Run("UnsafeSetIndex", test.Case(func(ctx context.Context) {
valType := reflect2.TypeOf(TestObject{}).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
obj := TestObject{}
field1.UnsafeSet(unsafe.Pointer(&obj), reflect2.PtrOf(100))
must.Equal(100, obj.Field1)
}))
t.Run("GetIndex", testOp(func(api reflect2.API) interface{} {
obj := TestObject{Field1: 100}
valType := api.TypeOf(obj).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
return field1.Get(&obj)
}))
t.Run("UnsafeGetIndex", test.Case(func(ctx context.Context) {
obj := TestObject{Field1: 100}
valType := reflect2.TypeOf(obj).(reflect2.StructType)
field1 := valType.FieldByName("Field1")
value := field1.UnsafeGet(unsafe.Pointer(&obj))
must.Equal(100, *(*int)(value))
}))
}