gzip_test.go 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147
  1. package gzip
  2. import (
  3. "compress/gzip"
  4. "fmt"
  5. "io/ioutil"
  6. "net/http"
  7. "net/http/httptest"
  8. "net/http/httputil"
  9. "net/url"
  10. "strconv"
  11. "testing"
  12. "github.com/gin-gonic/gin"
  13. "github.com/stretchr/testify/assert"
  14. )
  15. const (
  16. testResponse = "Gzip Test Response "
  17. testReverseResponse = "Gzip Test Reverse Response "
  18. )
  19. func init() {
  20. gin.SetMode(gin.ReleaseMode)
  21. }
  22. type rServer struct{}
  23. func (s *rServer) ServeHTTP(rw http.ResponseWriter, req *http.Request) {
  24. fmt.Fprint(rw, testReverseResponse)
  25. }
  26. type closeNotifyingRecorder struct {
  27. *httptest.ResponseRecorder
  28. closed chan bool
  29. }
  30. func newCloseNotifyingRecorder() *closeNotifyingRecorder {
  31. return &closeNotifyingRecorder{
  32. httptest.NewRecorder(),
  33. make(chan bool, 1),
  34. }
  35. }
  36. func (c *closeNotifyingRecorder) close() {
  37. c.closed <- true
  38. }
  39. func (c *closeNotifyingRecorder) CloseNotify() <-chan bool {
  40. return c.closed
  41. }
  42. func newServer() *gin.Engine {
  43. // init reverse proxy server
  44. rServer := httptest.NewServer(new(rServer))
  45. target, _ := url.Parse(rServer.URL)
  46. rp := httputil.NewSingleHostReverseProxy(target)
  47. router := gin.New()
  48. router.Use(Gzip(DefaultCompression))
  49. router.GET("/", func(c *gin.Context) {
  50. c.Header("Content-Length", strconv.Itoa(len(testResponse)))
  51. c.String(200, testResponse)
  52. })
  53. router.Any("/reverse", func(c *gin.Context) {
  54. rp.ServeHTTP(c.Writer, c.Request)
  55. })
  56. return router
  57. }
  58. func TestGzip(t *testing.T) {
  59. req, _ := http.NewRequest("GET", "/", nil)
  60. req.Header.Add("Accept-Encoding", "gzip")
  61. w := httptest.NewRecorder()
  62. r := newServer()
  63. r.ServeHTTP(w, req)
  64. assert.Equal(t, w.Code, 200)
  65. assert.Equal(t, w.Header().Get("Content-Encoding"), "gzip")
  66. assert.Equal(t, w.Header().Get("Vary"), "Accept-Encoding")
  67. assert.NotEqual(t, w.Header().Get("Content-Length"), "0")
  68. assert.NotEqual(t, w.Body.Len(), 19)
  69. assert.Equal(t, fmt.Sprint(w.Body.Len()), w.Header().Get("Content-Length"))
  70. gr, err := gzip.NewReader(w.Body)
  71. assert.NoError(t, err)
  72. defer gr.Close()
  73. body, _ := ioutil.ReadAll(gr)
  74. assert.Equal(t, string(body), testResponse)
  75. }
  76. func TestGzipPNG(t *testing.T) {
  77. req, _ := http.NewRequest("GET", "/image.png", nil)
  78. req.Header.Add("Accept-Encoding", "gzip")
  79. router := gin.New()
  80. router.Use(Gzip(DefaultCompression))
  81. router.GET("/image.png", func(c *gin.Context) {
  82. c.String(200, "this is a PNG!")
  83. })
  84. w := httptest.NewRecorder()
  85. router.ServeHTTP(w, req)
  86. assert.Equal(t, w.Code, 200)
  87. assert.Equal(t, w.Header().Get("Content-Encoding"), "")
  88. assert.Equal(t, w.Header().Get("Vary"), "")
  89. assert.Equal(t, w.Body.String(), "this is a PNG!")
  90. }
  91. func TestNoGzip(t *testing.T) {
  92. req, _ := http.NewRequest("GET", "/", nil)
  93. w := httptest.NewRecorder()
  94. r := newServer()
  95. r.ServeHTTP(w, req)
  96. assert.Equal(t, w.Code, 200)
  97. assert.Equal(t, w.Header().Get("Content-Encoding"), "")
  98. assert.Equal(t, w.Header().Get("Content-Length"), "19")
  99. assert.Equal(t, w.Body.String(), testResponse)
  100. }
  101. func TestGzipWithReverseProxy(t *testing.T) {
  102. req, _ := http.NewRequest("GET", "/reverse", nil)
  103. req.Header.Add("Accept-Encoding", "gzip")
  104. w := newCloseNotifyingRecorder()
  105. r := newServer()
  106. r.ServeHTTP(w, req)
  107. assert.Equal(t, w.Code, 200)
  108. assert.Equal(t, w.Header().Get("Content-Encoding"), "gzip")
  109. assert.Equal(t, w.Header().Get("Vary"), "Accept-Encoding")
  110. assert.NotEqual(t, w.Header().Get("Content-Length"), "0")
  111. assert.NotEqual(t, w.Body.Len(), 19)
  112. assert.Equal(t, fmt.Sprint(w.Body.Len()), w.Header().Get("Content-Length"))
  113. gr, err := gzip.NewReader(w.Body)
  114. assert.NoError(t, err)
  115. defer gr.Close()
  116. body, _ := ioutil.ReadAll(gr)
  117. assert.Equal(t, string(body), testReverseResponse)
  118. }