httptest.go 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. package httptest
  2. import (
  3. "crypto/tls"
  4. "net/http"
  5. "net/http/httptest"
  6. "testing"
  7. "github.com/kataras/iris"
  8. "github.com/kataras/iris/context"
  9. "github.com/kataras/iris/core/router"
  10. "github.com/iris-contrib/httpexpect/v2"
  11. )
  12. type (
  13. // OptionSetter sets a configuration field to the configuration
  14. OptionSetter interface {
  15. // Set receives a pointer to the Configuration type and does the job of filling it
  16. Set(c *Configuration)
  17. }
  18. // OptionSet implements the OptionSetter
  19. OptionSet func(c *Configuration)
  20. )
  21. // Set is the func which makes the OptionSet an OptionSetter, this is used mostly
  22. func (o OptionSet) Set(c *Configuration) {
  23. o(c)
  24. }
  25. // Configuration httptest configuration
  26. type Configuration struct {
  27. // URL the base url.
  28. // Defaults to empty string "".
  29. URL string
  30. // Debug if true then debug messages from the httpexpect will be shown when a test runs
  31. // Defaults to false.
  32. Debug bool
  33. // LogLevel sets the application's log level.
  34. // Defaults to "disable" when testing.
  35. LogLevel string
  36. }
  37. // Set implements the OptionSetter for the Configuration itself
  38. func (c Configuration) Set(main *Configuration) {
  39. main.URL = c.URL
  40. main.Debug = c.Debug
  41. if c.LogLevel != "" {
  42. main.LogLevel = c.LogLevel
  43. }
  44. }
  45. var (
  46. // URL if set then it sets the httptest's BaseURL.
  47. // Defaults to empty string "".
  48. URL = func(schemeAndHost string) OptionSet {
  49. return func(c *Configuration) {
  50. c.URL = schemeAndHost
  51. }
  52. }
  53. // Debug if true then debug messages from the httpexpect will be shown when a test runs
  54. // Defaults to false.
  55. Debug = func(val bool) OptionSet {
  56. return func(c *Configuration) {
  57. c.Debug = val
  58. }
  59. }
  60. // LogLevel sets the application's log level "val".
  61. // Defaults to disabled when testing.
  62. LogLevel = func(val string) OptionSet {
  63. return func(c *Configuration) {
  64. c.LogLevel = val
  65. }
  66. }
  67. )
  68. // DefaultConfiguration returns the default configuration for the httptest.
  69. func DefaultConfiguration() *Configuration {
  70. return &Configuration{URL: "", Debug: false, LogLevel: "disable"}
  71. }
  72. // New Prepares and returns a new test framework based on the "app".
  73. // You can find example on the https://github.com/kataras/iris/tree/master/_examples/testing/httptest
  74. func New(t *testing.T, app *iris.Application, setters ...OptionSetter) *httpexpect.Expect {
  75. conf := DefaultConfiguration()
  76. for _, setter := range setters {
  77. setter.Set(conf)
  78. }
  79. // set the logger or disable it (default).
  80. app.Logger().SetLevel(conf.LogLevel)
  81. if err := app.Build(); err != nil {
  82. if conf.LogLevel != "disable" {
  83. app.Logger().Println(err.Error())
  84. return nil
  85. }
  86. }
  87. testConfiguration := httpexpect.Config{
  88. BaseURL: conf.URL,
  89. Client: &http.Client{
  90. Transport: httpexpect.NewBinder(app),
  91. Jar: httpexpect.NewJar(),
  92. },
  93. Reporter: httpexpect.NewAssertReporter(t),
  94. }
  95. if conf.Debug {
  96. testConfiguration.Printers = []httpexpect.Printer{
  97. httpexpect.NewDebugPrinter(t, true),
  98. }
  99. }
  100. return httpexpect.WithConfig(testConfiguration)
  101. }
  102. // NewInsecure same as New but receives a single host instead of the whole framework.
  103. // Useful for testing running TLS servers.
  104. func NewInsecure(t *testing.T, setters ...OptionSetter) *httpexpect.Expect {
  105. conf := DefaultConfiguration()
  106. for _, setter := range setters {
  107. setter.Set(conf)
  108. }
  109. transport := &http.Transport{
  110. TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
  111. }
  112. testConfiguration := httpexpect.Config{
  113. BaseURL: conf.URL,
  114. Client: &http.Client{
  115. Transport: transport,
  116. Jar: httpexpect.NewJar(),
  117. },
  118. Reporter: httpexpect.NewAssertReporter(t),
  119. }
  120. if conf.Debug {
  121. testConfiguration.Printers = []httpexpect.Printer{
  122. httpexpect.NewDebugPrinter(t, true),
  123. }
  124. }
  125. return httpexpect.WithConfig(testConfiguration)
  126. }
  127. // Aliases for "net/http/httptest" package. See `Do` package-level function.
  128. var (
  129. NewRecorder = httptest.NewRecorder
  130. NewRequest = httptest.NewRequest
  131. )
  132. // Do is a simple helper which can be used to test handlers individually
  133. // with the "net/http/httptest" package.
  134. // This package contains aliases for `NewRequest` and `NewRecorder` too.
  135. //
  136. // For a more efficient testing please use the `New` function instead.
  137. func Do(w http.ResponseWriter, r *http.Request, handler iris.Handler, irisConfigurators ...iris.Configurator) {
  138. app := new(iris.Application)
  139. app.Configure(iris.WithConfiguration(iris.DefaultConfiguration()), iris.WithLogLevel("disable"))
  140. app.Configure(irisConfigurators...)
  141. app.HTTPErrorHandler = router.NewDefaultHandler(app.ConfigurationReadOnly(), app.Logger())
  142. app.ContextPool = context.New(func() interface{} {
  143. return context.NewContext(app)
  144. })
  145. ctx := app.ContextPool.Acquire(w, r)
  146. handler(ctx)
  147. app.ContextPool.Release(ctx)
  148. }