gitee.com/liuxuezhan/go-micro-v1.18.0@v1.0.0/service_test.go (about)

     1  package micro
     2  
     3  import (
     4  	"context"
     5  	"errors"
     6  	"sync"
     7  	"testing"
     8  
     9  	glog "github.com/go-log/log"
    10  	"gitee.com/liuxuezhan/go-micro-v1.18.0/client"
    11  	proto "gitee.com/liuxuezhan/go-micro-v1.18.0/debug/service/proto"
    12  	"gitee.com/liuxuezhan/go-micro-v1.18.0/registry/memory"
    13  	"gitee.com/liuxuezhan/go-micro-v1.18.0/util/log"
    14  	"gitee.com/liuxuezhan/go-micro-v1.18.0/util/test"
    15  )
    16  
    17  func testShutdown(wg *sync.WaitGroup, cancel func()) {
    18  	// add 1
    19  	wg.Add(1)
    20  	// shutdown the service
    21  	cancel()
    22  	// wait for stop
    23  	wg.Wait()
    24  }
    25  
    26  func testService(ctx context.Context, wg *sync.WaitGroup, name string) Service {
    27  	// set no op logger
    28  	log.SetLogger(glog.DefaultLogger)
    29  
    30  	// add self
    31  	wg.Add(1)
    32  
    33  	r := memory.NewRegistry(memory.Services(test.Data))
    34  
    35  	// create service
    36  	return NewService(
    37  		Name(name),
    38  		Context(ctx),
    39  		Registry(r),
    40  		AfterStart(func() error {
    41  			wg.Done()
    42  			return nil
    43  		}),
    44  		AfterStop(func() error {
    45  			wg.Done()
    46  			return nil
    47  		}),
    48  	)
    49  }
    50  
    51  func testRequest(ctx context.Context, c client.Client, name string) error {
    52  	// test call debug
    53  	req := c.NewRequest(
    54  		name,
    55  		"Debug.Health",
    56  		new(proto.HealthRequest),
    57  	)
    58  
    59  	rsp := new(proto.HealthResponse)
    60  
    61  	err := c.Call(context.TODO(), req, rsp)
    62  	if err != nil {
    63  		return err
    64  	}
    65  
    66  	if rsp.Status != "ok" {
    67  		return errors.New("service response: " + rsp.Status)
    68  	}
    69  
    70  	return nil
    71  }
    72  
    73  // TestService tests running and calling a service
    74  func TestService(t *testing.T) {
    75  	// waitgroup for server start
    76  	var wg sync.WaitGroup
    77  
    78  	// cancellation context
    79  	ctx, cancel := context.WithCancel(context.Background())
    80  
    81  	// start test server
    82  	service := testService(ctx, &wg, "test.service")
    83  
    84  	go func() {
    85  		// wait for service to start
    86  		wg.Wait()
    87  
    88  		// make a test call
    89  		if err := testRequest(ctx, service.Client(), "test.service"); err != nil {
    90  			t.Fatal(err)
    91  		}
    92  
    93  		// shutdown the service
    94  		testShutdown(&wg, cancel)
    95  	}()
    96  
    97  	// start service
    98  	if err := service.Run(); err != nil {
    99  		t.Fatal(err)
   100  	}
   101  }
   102  
   103  func benchmarkService(b *testing.B, n int, name string) {
   104  	// stop the timer
   105  	b.StopTimer()
   106  
   107  	// waitgroup for server start
   108  	var wg sync.WaitGroup
   109  
   110  	// cancellation context
   111  	ctx, cancel := context.WithCancel(context.Background())
   112  
   113  	// create test server
   114  	service := testService(ctx, &wg, name)
   115  
   116  	// start the server
   117  	go func() {
   118  		if err := service.Run(); err != nil {
   119  			b.Fatal(err)
   120  		}
   121  	}()
   122  
   123  	// wait for service to start
   124  	wg.Wait()
   125  
   126  	// make a test call to warm the cache
   127  	for i := 0; i < 10; i++ {
   128  		if err := testRequest(ctx, service.Client(), name); err != nil {
   129  			b.Fatal(err)
   130  		}
   131  	}
   132  
   133  	// start the timer
   134  	b.StartTimer()
   135  
   136  	// number of iterations
   137  	for i := 0; i < b.N; i++ {
   138  		// for concurrency
   139  		for j := 0; j < n; j++ {
   140  			wg.Add(1)
   141  
   142  			go func() {
   143  				err := testRequest(ctx, service.Client(), name)
   144  				wg.Done()
   145  				if err != nil {
   146  					b.Fatal(err)
   147  				}
   148  			}()
   149  		}
   150  
   151  		// wait for test completion
   152  		wg.Wait()
   153  	}
   154  
   155  	// stop the timer
   156  	b.StopTimer()
   157  
   158  	// shutdown service
   159  	testShutdown(&wg, cancel)
   160  }
   161  
   162  func BenchmarkService1(b *testing.B) {
   163  	benchmarkService(b, 1, "test.service.1")
   164  }
   165  
   166  func BenchmarkService8(b *testing.B) {
   167  	benchmarkService(b, 8, "test.service.8")
   168  }
   169  
   170  func BenchmarkService16(b *testing.B) {
   171  	benchmarkService(b, 16, "test.service.16")
   172  }
   173  
   174  func BenchmarkService32(b *testing.B) {
   175  	benchmarkService(b, 32, "test.service.32")
   176  }
   177  
   178  func BenchmarkService64(b *testing.B) {
   179  	benchmarkService(b, 64, "test.service.64")
   180  }