2023-08-09 14:31:23 +03:00
|
|
|
package handler
|
|
|
|
|
|
|
|
import (
|
|
|
|
"context"
|
2023-08-11 20:12:15 +03:00
|
|
|
"go.unistack.org/micro/v3/logger"
|
2023-08-09 14:31:23 +03:00
|
|
|
pb "go.unistack.org/unistack-org/pkgdash/proto/go_generate"
|
|
|
|
"net/http"
|
|
|
|
|
|
|
|
"github.com/pkg/errors"
|
|
|
|
)
|
|
|
|
|
|
|
|
type encoder interface {
|
|
|
|
Success(rw http.ResponseWriter, response interface{}) error
|
|
|
|
Error(rw http.ResponseWriter, err *pb.Error, status int) error
|
|
|
|
}
|
|
|
|
|
|
|
|
type writer interface {
|
|
|
|
Response(ctx context.Context, rw http.ResponseWriter, value interface{})
|
|
|
|
}
|
|
|
|
|
2023-08-11 20:12:15 +03:00
|
|
|
// nolint
|
2023-08-09 14:31:23 +03:00
|
|
|
type stackTracer interface {
|
|
|
|
StackTrace() errors.StackTrace
|
|
|
|
}
|
|
|
|
|
|
|
|
type Writer struct {
|
|
|
|
encoder encoder
|
|
|
|
}
|
|
|
|
|
|
|
|
func NewWriter(encoder encoder) (*Writer, error) {
|
|
|
|
if encoder == nil {
|
|
|
|
return nil, errors.New("empty encoder")
|
|
|
|
}
|
|
|
|
return &Writer{encoder: encoder}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (w *Writer) Response(ctx context.Context, rw http.ResponseWriter, value interface{}) {
|
|
|
|
var err error
|
|
|
|
|
|
|
|
if v, ok := value.(error); ok {
|
|
|
|
err = w.error(ctx, rw, v)
|
|
|
|
} else {
|
|
|
|
err = w.success(rw, value)
|
|
|
|
}
|
|
|
|
|
|
|
|
if err != nil {
|
|
|
|
logger.Error(ctx, "Response writing error: ", err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func (w *Writer) error(ctx context.Context, rw http.ResponseWriter, err error) error {
|
|
|
|
e, status := mapError(ctx, err)
|
|
|
|
/*
|
|
|
|
switch {
|
|
|
|
case status >= http.StatusInternalServerError:
|
|
|
|
logger.Errorf(ctx, "error: %s, code: %s, http status: %d, uuid: %s", err, e.Code, status, e.Uuid)
|
|
|
|
|
|
|
|
if err, ok := err.(stackTracer); ok {
|
|
|
|
logger.Errorf(ctx, "error stacktrace: %+v, uuid: %s", err.StackTrace(), e.Uuid)
|
|
|
|
}
|
|
|
|
|
|
|
|
default:
|
|
|
|
logger.Infof(ctx, "error: %s, code: %s, http status: %d, uuid: %s", err, e.Code, status, e.Uuid)
|
|
|
|
|
|
|
|
if err, ok := err.(stackTracer); ok {
|
|
|
|
logger.Infof(ctx, "error stacktrace: %+v, uuid: %s", err.StackTrace(), e.Uuid)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
return w.encoder.Error(rw, e, status)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (w *Writer) success(rw http.ResponseWriter, value interface{}) error {
|
|
|
|
return w.encoder.Success(rw, value)
|
|
|
|
}
|