mirror of
				https://github.com/optim-enterprises-bv/kubernetes.git
				synced 2025-11-03 19:58:17 +00:00 
			
		
		
		
	Merge pull request #73973 from smarterclayton/fix_benchmark
Fix the unstructured conversion benchmarks to be correct
This commit is contained in:
		@@ -19,11 +19,13 @@ package testing
 | 
			
		||||
import (
 | 
			
		||||
	"math/rand"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"sort"
 | 
			
		||||
	"testing"
 | 
			
		||||
 | 
			
		||||
	"github.com/google/gofuzz"
 | 
			
		||||
	fuzz "github.com/google/gofuzz"
 | 
			
		||||
	jsoniter "github.com/json-iterator/go"
 | 
			
		||||
 | 
			
		||||
	"k8s.io/api/core/v1"
 | 
			
		||||
	v1 "k8s.io/api/core/v1"
 | 
			
		||||
	"k8s.io/apimachinery/pkg/api/apitesting/fuzzer"
 | 
			
		||||
	apiequality "k8s.io/apimachinery/pkg/api/equality"
 | 
			
		||||
	"k8s.io/apimachinery/pkg/api/meta"
 | 
			
		||||
@@ -99,7 +101,7 @@ func doRoundTrip(t *testing.T, internalVersion schema.GroupVersion, externalVers
 | 
			
		||||
		return
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	newUnstr, err := runtime.NewTestUnstructuredConverter(apiequality.Semantic).ToUnstructured(item)
 | 
			
		||||
	newUnstr, err := runtime.DefaultUnstructuredConverter.ToUnstructured(item)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Errorf("ToUnstructured failed: %v", err)
 | 
			
		||||
		return
 | 
			
		||||
@@ -163,7 +165,7 @@ func TestRoundTripWithEmptyCreationTimestamp(t *testing.T) {
 | 
			
		||||
			// attempt to re-convert unstructured object - conversion should not fail
 | 
			
		||||
			// based on empty metadata fields, such as creationTimestamp
 | 
			
		||||
			newObj := reflect.New(reflect.TypeOf(item).Elem()).Interface().(runtime.Object)
 | 
			
		||||
			err = runtime.NewTestUnstructuredConverter(apiequality.Semantic).FromUnstructured(unstructObj.Object, newObj)
 | 
			
		||||
			err = runtime.DefaultUnstructuredConverter.FromUnstructured(unstructObj.Object, newObj)
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("FromUnstructured failed: %v", err)
 | 
			
		||||
			}
 | 
			
		||||
@@ -171,44 +173,160 @@ func TestRoundTripWithEmptyCreationTimestamp(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkToFromUnstructured(b *testing.B) {
 | 
			
		||||
func BenchmarkToUnstructured(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	convertor := runtime.DefaultUnstructuredConverter
 | 
			
		||||
	b.ResetTimer()
 | 
			
		||||
	for i := 0; i < b.N; i++ {
 | 
			
		||||
		unstr, err := runtime.NewTestUnstructuredConverter(apiequality.Semantic).ToUnstructured(&items[i%size])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		obj := v1.Pod{}
 | 
			
		||||
		if err := runtime.NewTestUnstructuredConverter(apiequality.Semantic).FromUnstructured(unstr, &obj); err != nil {
 | 
			
		||||
		unstr, err := convertor.ToUnstructured(&items[i%size])
 | 
			
		||||
		if err != nil || unstr == nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	b.StopTimer()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkToFromUnstructuredViaJSON(b *testing.B) {
 | 
			
		||||
func BenchmarkFromUnstructured(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	convertor := runtime.DefaultUnstructuredConverter
 | 
			
		||||
	var unstr []map[string]interface{}
 | 
			
		||||
	for i := range items {
 | 
			
		||||
		item, err := convertor.ToUnstructured(&items[i])
 | 
			
		||||
		if err != nil || item == nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		unstr = append(unstr, item)
 | 
			
		||||
	}
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	b.ResetTimer()
 | 
			
		||||
	for i := 0; i < b.N; i++ {
 | 
			
		||||
		data, err := json.Marshal(&items[i%size])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		unstr := map[string]interface{}{}
 | 
			
		||||
		if err := json.Unmarshal(data, &unstr); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		data, err = json.Marshal(unstr)
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		obj := v1.Pod{}
 | 
			
		||||
		if err := json.Unmarshal(data, &obj); err != nil {
 | 
			
		||||
		if err := convertor.FromUnstructured(unstr[i%size], &obj); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	b.StopTimer()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkToUnstructuredViaJSON(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	var data [][]byte
 | 
			
		||||
	for i := range items {
 | 
			
		||||
		item, err := json.Marshal(&items[i])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		data = append(data, item)
 | 
			
		||||
	}
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	b.ResetTimer()
 | 
			
		||||
	for i := 0; i < b.N; i++ {
 | 
			
		||||
		unstr := map[string]interface{}{}
 | 
			
		||||
		if err := json.Unmarshal(data[i%size], &unstr); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	b.StopTimer()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkFromUnstructuredViaJSON(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	var unstr []map[string]interface{}
 | 
			
		||||
	for i := range items {
 | 
			
		||||
		data, err := json.Marshal(&items[i])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		item := map[string]interface{}{}
 | 
			
		||||
		if err := json.Unmarshal(data, &item); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		unstr = append(unstr, item)
 | 
			
		||||
	}
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	b.ResetTimer()
 | 
			
		||||
	for i := 0; i < b.N; i++ {
 | 
			
		||||
		item, err := json.Marshal(unstr[i%size])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		obj := v1.Pod{}
 | 
			
		||||
		if err := json.Unmarshal(item, &obj); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	b.StopTimer()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkToUnstructuredViaJSONIter(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	var keys []string
 | 
			
		||||
	for k := range jsonIterConfig {
 | 
			
		||||
		keys = append(keys, k)
 | 
			
		||||
	}
 | 
			
		||||
	sort.Strings(keys)
 | 
			
		||||
	for _, name := range keys {
 | 
			
		||||
		c := jsonIterConfig[name]
 | 
			
		||||
		b.Run(name, func(b *testing.B) {
 | 
			
		||||
			b.ResetTimer()
 | 
			
		||||
			for i := 0; i < b.N; i++ {
 | 
			
		||||
				data, err := c.Marshal(&items[i%size])
 | 
			
		||||
				if err != nil {
 | 
			
		||||
					b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
				}
 | 
			
		||||
				unstr := map[string]interface{}{}
 | 
			
		||||
				if err := c.Unmarshal(data, &unstr); err != nil {
 | 
			
		||||
					b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			b.StopTimer()
 | 
			
		||||
		})
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
var jsonIterConfig = map[string]jsoniter.API{
 | 
			
		||||
	"default": jsoniter.ConfigDefault,
 | 
			
		||||
	"fastest": jsoniter.ConfigFastest,
 | 
			
		||||
	"compat":  jsoniter.ConfigCompatibleWithStandardLibrary,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func BenchmarkFromUnstructuredViaJSONIter(b *testing.B) {
 | 
			
		||||
	items := benchmarkItems(b)
 | 
			
		||||
	var unstr []map[string]interface{}
 | 
			
		||||
	for i := range items {
 | 
			
		||||
		data, err := jsoniter.Marshal(&items[i])
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		item := map[string]interface{}{}
 | 
			
		||||
		if err := json.Unmarshal(data, &item); err != nil {
 | 
			
		||||
			b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
		}
 | 
			
		||||
		unstr = append(unstr, item)
 | 
			
		||||
	}
 | 
			
		||||
	size := len(items)
 | 
			
		||||
	var keys []string
 | 
			
		||||
	for k := range jsonIterConfig {
 | 
			
		||||
		keys = append(keys, k)
 | 
			
		||||
	}
 | 
			
		||||
	sort.Strings(keys)
 | 
			
		||||
	for _, name := range keys {
 | 
			
		||||
		c := jsonIterConfig[name]
 | 
			
		||||
		b.Run(name, func(b *testing.B) {
 | 
			
		||||
			b.ResetTimer()
 | 
			
		||||
			for i := 0; i < b.N; i++ {
 | 
			
		||||
				item, err := c.Marshal(unstr[i%size])
 | 
			
		||||
				if err != nil {
 | 
			
		||||
					b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
				}
 | 
			
		||||
				obj := v1.Pod{}
 | 
			
		||||
				if err := c.Unmarshal(item, &obj); err != nil {
 | 
			
		||||
					b.Fatalf("unexpected error: %v", err)
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			b.StopTimer()
 | 
			
		||||
		})
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user