✨ Add options, mostly transformers
This commit is contained in:
parent
b1e4c28dfe
commit
b4b4f041d7
4 changed files with 121 additions and 11 deletions
|
|
@ -7,7 +7,16 @@ import (
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
)
|
)
|
||||||
|
|
||||||
func ErrorMiddleware() gin.HandlerFunc {
|
func ErrorMiddleware(opts ...Option) gin.HandlerFunc {
|
||||||
|
conf := config{}
|
||||||
|
for _, opt := range opts {
|
||||||
|
conf = opt(conf)
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(conf.transformers) == 0 {
|
||||||
|
conf.transformers = []Transformer{ginTransformer}
|
||||||
|
}
|
||||||
|
|
||||||
return func(c *gin.Context) {
|
return func(c *gin.Context) {
|
||||||
c.Next()
|
c.Next()
|
||||||
err := c.Errors.Last()
|
err := c.Errors.Last()
|
||||||
|
|
@ -16,24 +25,27 @@ func ErrorMiddleware() gin.HandlerFunc {
|
||||||
}
|
}
|
||||||
|
|
||||||
var re rErrors.ResponsableError
|
var re rErrors.ResponsableError
|
||||||
|
|
||||||
errors.As(err, &re)
|
errors.As(err, &re)
|
||||||
|
// If we have at least one that's a ResponsableError, we should use it
|
||||||
for _, err = range c.Errors {
|
for _, err = range c.Errors {
|
||||||
errors.As(err, &re)
|
|
||||||
if re != nil {
|
if re != nil {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
errors.As(err, &re)
|
||||||
}
|
}
|
||||||
|
|
||||||
// @todo we need to add some way to do custom handling
|
// Next, let's check our transformers
|
||||||
|
for _, trans := range conf.transformers {
|
||||||
|
if re != nil {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
re = trans(err)
|
||||||
|
}
|
||||||
|
|
||||||
// @todo Refactor this with 👆
|
// Still couldn't find one, so it's a 500
|
||||||
if re == nil {
|
if re == nil {
|
||||||
switch err.Type {
|
|
||||||
case gin.ErrorTypePrivate:
|
|
||||||
re = rErrors.NewInternalError("%w", err)
|
re = rErrors.NewInternalError("%w", err)
|
||||||
default:
|
|
||||||
re = rErrors.NewBadRequest("%w", err)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
c.JSON(re.Status(), re)
|
c.JSON(re.Status(), re)
|
||||||
|
|
|
||||||
|
|
@ -43,6 +43,10 @@ func (s *MiddlewareTestSuite) do(err ...error) {
|
||||||
|
|
||||||
func (s *MiddlewareTestSuite) doParse(err ...error) map[string]any {
|
func (s *MiddlewareTestSuite) doParse(err ...error) map[string]any {
|
||||||
s.do(err...)
|
s.do(err...)
|
||||||
|
return s.parse()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *MiddlewareTestSuite) parse() map[string]any {
|
||||||
var out map[string]any
|
var out map[string]any
|
||||||
jsonErr := json.Unmarshal(s.w.Body.Bytes(), &out)
|
jsonErr := json.Unmarshal(s.w.Body.Bytes(), &out)
|
||||||
s.Assert().Nil(jsonErr)
|
s.Assert().Nil(jsonErr)
|
||||||
|
|
@ -98,3 +102,18 @@ func (s *MiddlewareTestSuite) TestOtherError() {
|
||||||
s.Assert().Equal("Unknown Error", outMsg)
|
s.Assert().Equal("Unknown Error", outMsg)
|
||||||
s.Assert().Equal(http.StatusInternalServerError, s.w.Code)
|
s.Assert().Equal(http.StatusInternalServerError, s.w.Code)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *MiddlewareTestSuite) TestNoWorkingTransformer() {
|
||||||
|
var noop Transformer = func(err error) rErrors.ResponsableError {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
err := errors.New("Foo")
|
||||||
|
s.ctx.Error(err)
|
||||||
|
ErrorMiddleware(WithTransformer(noop))(s.ctx)
|
||||||
|
|
||||||
|
out := s.parse()
|
||||||
|
outMsg, ok := out["error"].(string)
|
||||||
|
s.Assert().True(ok)
|
||||||
|
s.Assert().Equal("Unknown Error", outMsg)
|
||||||
|
s.Assert().Equal(http.StatusInternalServerError, s.w.Code)
|
||||||
|
}
|
||||||
|
|
|
||||||
41
options.go
Normal file
41
options.go
Normal file
|
|
@ -0,0 +1,41 @@
|
||||||
|
package handler
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
|
||||||
|
rErrors "codeberg.org/danjones000/responsable-errors"
|
||||||
|
"github.com/gin-gonic/gin"
|
||||||
|
)
|
||||||
|
|
||||||
|
type config struct {
|
||||||
|
transformers []Transformer
|
||||||
|
}
|
||||||
|
|
||||||
|
type Transformer func(error) rErrors.ResponsableError
|
||||||
|
|
||||||
|
type Option func(config) config
|
||||||
|
|
||||||
|
func WithTransformer(tr Transformer) Option {
|
||||||
|
return func(c config) config {
|
||||||
|
c.transformers = append(c.transformers, tr)
|
||||||
|
return c
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func WithDefaultTransformer() Option {
|
||||||
|
return WithTransformer(ginTransformer)
|
||||||
|
}
|
||||||
|
|
||||||
|
func ginTransformer(er error) rErrors.ResponsableError {
|
||||||
|
var err *gin.Error
|
||||||
|
if !errors.As(er, &err) {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
switch err.Type {
|
||||||
|
case gin.ErrorTypePrivate:
|
||||||
|
return rErrors.NewInternalError("%w", err)
|
||||||
|
default:
|
||||||
|
return rErrors.NewBadRequest("%w", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
38
options_test.go
Normal file
38
options_test.go
Normal file
|
|
@ -0,0 +1,38 @@
|
||||||
|
package handler
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
rErrors "codeberg.org/danjones000/responsable-errors"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
)
|
||||||
|
|
||||||
|
var someErr error = errors.New("I am a teapot")
|
||||||
|
|
||||||
|
var noop Transformer = func(err error) rErrors.ResponsableError {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestWithTrans(t *testing.T) {
|
||||||
|
c := config{}
|
||||||
|
c = WithTransformer(noop)(c)
|
||||||
|
assert.Len(t, c.transformers, 1)
|
||||||
|
exp := fmt.Sprintf("%p", noop)
|
||||||
|
fd := fmt.Sprintf("%p", c.transformers[0])
|
||||||
|
assert.Equal(t, exp, fd)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestWithDef(t *testing.T) {
|
||||||
|
c := config{}
|
||||||
|
c = WithDefaultTransformer()(c)
|
||||||
|
assert.Len(t, c.transformers, 1)
|
||||||
|
exp := fmt.Sprintf("%p", ginTransformer)
|
||||||
|
fd := fmt.Sprintf("%p", c.transformers[0])
|
||||||
|
assert.Equal(t, exp, fd)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestGinTransNotGinError(t *testing.T) {
|
||||||
|
assert.Nil(t, ginTransformer(someErr))
|
||||||
|
}
|
||||||
Loading…
Add table
Add a link
Reference in a new issue