mirror of
https://github.com/fnproject/fn.git
synced 2022-10-28 21:29:17 +03:00
Add APIErrorWrapper so that underlying errors can be logged (#1246)
This commit is contained in:
@@ -194,3 +194,26 @@ type ErrorWrapper struct {
|
|||||||
func (m *ErrorWrapper) Validate() error {
|
func (m *ErrorWrapper) Validate() error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// APIErrorWrapper wraps an error with an APIError such that the APIError
|
||||||
|
// governs the HTTP response but the root error remains accessible.
|
||||||
|
type APIErrorWrapper interface {
|
||||||
|
APIError
|
||||||
|
RootError() error
|
||||||
|
}
|
||||||
|
|
||||||
|
type apiErrorWrapper struct {
|
||||||
|
APIError
|
||||||
|
root error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (w apiErrorWrapper) RootError() error {
|
||||||
|
return w.root
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewAPIErrorWrapper(apiErr APIError, rootErr error) APIErrorWrapper {
|
||||||
|
return &apiErrorWrapper{
|
||||||
|
APIError: apiErr,
|
||||||
|
root: rootErr,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -34,12 +34,10 @@ func (p *chPlacer) PlaceCall(rp RunnerPool, ctx context.Context, call RunnerCall
|
|||||||
key := call.Model().FnID
|
key := call.Model().FnID
|
||||||
sum64 := siphash.Hash(0, 0x4c617279426f6174, []byte(key))
|
sum64 := siphash.Hash(0, 0x4c617279426f6174, []byte(key))
|
||||||
|
|
||||||
|
var runnerPoolErr error
|
||||||
for {
|
for {
|
||||||
runners, err := rp.Runners(call)
|
var runners []Runner
|
||||||
if err != nil {
|
runners, runnerPoolErr = rp.Runners(call)
|
||||||
state.HandleFindRunnersFailure(err)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
i := int(jumpConsistentHash(sum64, int32(len(runners))))
|
i := int(jumpConsistentHash(sum64, int32(len(runners))))
|
||||||
for j := 0; j < len(runners) && !state.IsDone(); j++ {
|
for j := 0; j < len(runners) && !state.IsDone(); j++ {
|
||||||
@@ -59,6 +57,14 @@ func (p *chPlacer) PlaceCall(rp RunnerPool, ctx context.Context, call RunnerCall
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if runnerPoolErr != nil {
|
||||||
|
// If we haven't been able to place the function and we got an error
|
||||||
|
// from the runner pool, return that error (since we don't have
|
||||||
|
// enough runners to handle the current load and the runner pool is
|
||||||
|
// having trouble).
|
||||||
|
state.HandleFindRunnersFailure(runnerPoolErr)
|
||||||
|
return runnerPoolErr
|
||||||
|
}
|
||||||
return models.ErrCallTimeoutServerBusy
|
return models.ErrCallTimeoutServerBusy
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -28,12 +28,10 @@ func (sp *naivePlacer) PlaceCall(rp RunnerPool, ctx context.Context, call Runner
|
|||||||
state := NewPlacerTracker(ctx, &sp.cfg)
|
state := NewPlacerTracker(ctx, &sp.cfg)
|
||||||
defer state.HandleDone()
|
defer state.HandleDone()
|
||||||
|
|
||||||
|
var runnerPoolErr error
|
||||||
for {
|
for {
|
||||||
runners, err := rp.Runners(call)
|
var runners []Runner
|
||||||
if err != nil {
|
runners, runnerPoolErr = rp.Runners(call)
|
||||||
state.HandleFindRunnersFailure(err)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
for j := 0; j < len(runners) && !state.IsDone(); j++ {
|
for j := 0; j < len(runners) && !state.IsDone(); j++ {
|
||||||
|
|
||||||
@@ -51,5 +49,13 @@ func (sp *naivePlacer) PlaceCall(rp RunnerPool, ctx context.Context, call Runner
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if runnerPoolErr != nil {
|
||||||
|
// If we haven't been able to place the function and we got an error
|
||||||
|
// from the runner pool, return that error (since we don't have
|
||||||
|
// enough runners to handle the current load and the runner pool is
|
||||||
|
// having trouble).
|
||||||
|
state.HandleFindRunnersFailure(runnerPoolErr)
|
||||||
|
return runnerPoolErr
|
||||||
|
}
|
||||||
return models.ErrCallTimeoutServerBusy
|
return models.ErrCallTimeoutServerBusy
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -27,6 +27,9 @@ func handleErrorResponse(c *gin.Context, err error) {
|
|||||||
// HandleErrorResponse used to handle response errors in the same way.
|
// HandleErrorResponse used to handle response errors in the same way.
|
||||||
func HandleErrorResponse(ctx context.Context, w http.ResponseWriter, err error) {
|
func HandleErrorResponse(ctx context.Context, w http.ResponseWriter, err error) {
|
||||||
log := common.Logger(ctx)
|
log := common.Logger(ctx)
|
||||||
|
if w, ok := err.(models.APIErrorWrapper); ok {
|
||||||
|
log = log.WithField("root_error", w.RootError())
|
||||||
|
}
|
||||||
|
|
||||||
if ctx.Err() == context.Canceled {
|
if ctx.Err() == context.Canceled {
|
||||||
log.Info("client context cancelled")
|
log.Info("client context cancelled")
|
||||||
|
|||||||
Reference in New Issue
Block a user