gitee.com/ks-custle/core-gm@v0.0.0-20230922171213-b83bdd97b62c/httpsnoop/capture_metrics_test.go (about)

     1  package httpsnoop
     2  
     3  import (
     4  	"io"
     5  	"io/ioutil"
     6  	"log"
     7  	"os"
     8  	"strings"
     9  	"testing"
    10  	"time"
    11  
    12  	http "gitee.com/ks-custle/core-gm/gmhttp"
    13  	"gitee.com/ks-custle/core-gm/gmhttp/httptest"
    14  )
    15  
    16  func TestCaptureMetrics(t *testing.T) {
    17  	// Some of the edge cases tested below cause the net/http pkg to log some
    18  	// messages that add a lot of noise to the `go test -v` output, so we discard
    19  	// the log here.
    20  	log.SetOutput(ioutil.Discard)
    21  	defer log.SetOutput(os.Stderr)
    22  
    23  	tests := []struct {
    24  		Handler      http.Handler
    25  		WantDuration time.Duration
    26  		WantWritten  int64
    27  		WantCode     int
    28  		WantErr      string
    29  	}{
    30  		{
    31  			Handler:  http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {}),
    32  			WantCode: http.StatusOK,
    33  		},
    34  		{
    35  			Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    36  				w.WriteHeader(http.StatusBadRequest)
    37  				w.WriteHeader(http.StatusNotFound)
    38  				w.Write([]byte("foo"))
    39  				w.Write([]byte("bar"))
    40  				time.Sleep(25 * time.Millisecond)
    41  			}),
    42  			WantCode:     http.StatusBadRequest,
    43  			WantWritten:  6,
    44  			WantDuration: 25 * time.Millisecond,
    45  		},
    46  		{
    47  			Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    48  				w.Write([]byte("foo"))
    49  				w.WriteHeader(http.StatusNotFound)
    50  			}),
    51  			WantCode: http.StatusOK,
    52  		},
    53  		{
    54  			Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    55  				rrf := w.(io.ReaderFrom)
    56  				rrf.ReadFrom(strings.NewReader("reader from is ok"))
    57  			}),
    58  			WantWritten: 17,
    59  			WantCode:    http.StatusOK,
    60  		},
    61  		{
    62  			Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    63  				panic("oh no")
    64  			}),
    65  			WantErr: "EOF",
    66  		},
    67  	}
    68  
    69  	for i, test := range tests {
    70  		func() {
    71  			ch := make(chan Metrics, 1)
    72  			h := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    73  				ch <- CaptureMetrics(test.Handler, w, r)
    74  			})
    75  			s := httptest.NewServer(h)
    76  			defer s.Close()
    77  			res, err := http.Get(s.URL)
    78  			if !errContains(err, test.WantErr) {
    79  				t.Errorf("test %d: got=%s want=%s", i, err, test.WantErr)
    80  			}
    81  			if err != nil {
    82  				return
    83  			}
    84  			defer res.Body.Close()
    85  			m := <-ch
    86  			if m.Code != test.WantCode {
    87  				t.Errorf("test %d: got=%d want=%d", i, m.Code, test.WantCode)
    88  			} else if m.Duration < test.WantDuration {
    89  				t.Errorf("test %d: got=%s want=%s", i, m.Duration, test.WantDuration)
    90  			} else if m.Written < test.WantWritten {
    91  				t.Errorf("test %d: got=%d want=%d", i, m.Written, test.WantWritten)
    92  			}
    93  		}()
    94  	}
    95  }
    96  
    97  func errContains(err error, s string) bool {
    98  	var errS string
    99  	if err == nil {
   100  		errS = ""
   101  	} else {
   102  		errS = err.Error()
   103  	}
   104  	return strings.Contains(errS, s)
   105  }