github.com/avenga/couper@v1.12.2/logging/upstream_log_test.go (about)

     1  package logging_test
     2  
     3  import (
     4  	"context"
     5  	"net/http"
     6  	"net/http/httptest"
     7  	"reflect"
     8  	"testing"
     9  
    10  	"github.com/sirupsen/logrus"
    11  
    12  	"github.com/avenga/couper/internal/test"
    13  	"github.com/avenga/couper/logging"
    14  )
    15  
    16  var _ http.RoundTripper = &testRoundTripper{}
    17  
    18  type testRoundTripper struct {
    19  	response *http.Response
    20  }
    21  
    22  func (t *testRoundTripper) RoundTrip(req *http.Request) (*http.Response, error) {
    23  	resp := *t.response
    24  	resp.Request = req
    25  	return &resp, nil
    26  }
    27  
    28  func TestUpstreamLog_RoundTrip(t *testing.T) {
    29  	helper := test.New(t)
    30  	logger, hook := test.NewLogger()
    31  
    32  	type testcase struct {
    33  		description string
    34  		url         string
    35  		expFields   logrus.Fields
    36  	}
    37  
    38  	testcases := []testcase{
    39  		{
    40  			description: "pathless url",
    41  			url:         "http://test.com",
    42  			expFields: logrus.Fields{
    43  				"request": logrus.Fields{
    44  					"path": "",
    45  				},
    46  			},
    47  		},
    48  		{
    49  			description: "proto https",
    50  			url:         "https://example.com",
    51  			expFields: logrus.Fields{
    52  				"request": logrus.Fields{
    53  					"proto": "https",
    54  				},
    55  			},
    56  		},
    57  		{
    58  			description: "proto http",
    59  			url:         "http://example.com",
    60  			expFields: logrus.Fields{
    61  				"request": logrus.Fields{
    62  					"proto": "http",
    63  				},
    64  			},
    65  		},
    66  		{
    67  			description: "method status constant",
    68  			url:         "http://example.com",
    69  			expFields: logrus.Fields{
    70  				"request": logrus.Fields{
    71  					"method": http.MethodGet,
    72  				},
    73  				"response": logrus.Fields{
    74  					"status": 200,
    75  				},
    76  				"method": http.MethodGet,
    77  				"status": 200,
    78  			},
    79  		},
    80  		{
    81  			description: "explicit port",
    82  			url:         "http://localhost:8080/",
    83  			expFields: logrus.Fields{
    84  				"request": logrus.Fields{
    85  					"host":   "localhost",
    86  					"origin": "localhost:8080",
    87  					"path":   "/",
    88  					"port":   "8080",
    89  				},
    90  			},
    91  		},
    92  		{
    93  			description: "implicit port https",
    94  			url:         "https://couper.io/",
    95  			expFields: logrus.Fields{
    96  				"request": logrus.Fields{
    97  					"host":   "couper.io",
    98  					"origin": "couper.io",
    99  					"path":   "/",
   100  				},
   101  			},
   102  		},
   103  		{
   104  			description: "implicit port http",
   105  			url:         "http://example.com",
   106  			expFields: logrus.Fields{
   107  				"request": logrus.Fields{
   108  					"host":   "example.com",
   109  					"origin": "example.com",
   110  					"path":   "",
   111  				},
   112  			},
   113  		},
   114  		{
   115  			description: "required request fields",
   116  			url:         "http://localhost:8080/test",
   117  			expFields: logrus.Fields{
   118  				"request": logrus.Fields{
   119  					"host":   "localhost",
   120  					"origin": "localhost:8080",
   121  					"path":   "/test",
   122  					"method": http.MethodGet,
   123  					"proto":  "http",
   124  					"port":   "8080",
   125  				},
   126  				"response": logrus.Fields{
   127  					"status": 200,
   128  				},
   129  				"method": http.MethodGet,
   130  				"uid":    nil,
   131  				"status": 200,
   132  			},
   133  		},
   134  	}
   135  
   136  	for _, tc := range testcases {
   137  		t.Run(tc.description, func(subT *testing.T) {
   138  
   139  			hook.Reset()
   140  
   141  			myRT := &testRoundTripper{
   142  				response: &http.Response{
   143  					StatusCode: http.StatusOK,
   144  				},
   145  			}
   146  
   147  			upstreamLog := logging.NewUpstreamLog(logger.WithContext(context.TODO()), myRT, true)
   148  
   149  			req := httptest.NewRequest(http.MethodGet, tc.url, nil)
   150  			_, err := upstreamLog.RoundTrip(req)
   151  			helper.Must(err)
   152  
   153  			entry := hook.LastEntry()
   154  			for key, expFields := range tc.expFields {
   155  				value, exist := entry.Data[key]
   156  				if !exist {
   157  					subT.Errorf("Expected log field %s, got nothing", key)
   158  				}
   159  
   160  				switch ef := expFields.(type) {
   161  				case logrus.Fields:
   162  					for k, expected := range ef {
   163  						var result interface{}
   164  						switch fields := value.(type) {
   165  						case logging.Fields:
   166  							r, ok := fields[k]
   167  							if !ok {
   168  								subT.Errorf("Expected log field %s.%s, got nothing", key, k)
   169  							}
   170  							result = r
   171  						}
   172  
   173  						if !reflect.DeepEqual(expected, result) {
   174  							subT.Errorf("Want: %v for key %s, got: %v", expected, k, result)
   175  						}
   176  					}
   177  				default:
   178  					if !reflect.DeepEqual(expFields, value) {
   179  						subT.Errorf("Want: %v for key %s, got: %v", expFields, key, value)
   180  					}
   181  				}
   182  			}
   183  		})
   184  	}
   185  }