137 lines
2.9 KiB
Go
137 lines
2.9 KiB
Go
package util
|
|
|
|
import (
|
|
"fmt"
|
|
"net/http"
|
|
"reflect"
|
|
"strings"
|
|
|
|
"github.com/gin-gonic/gin"
|
|
"github.com/gin-gonic/gin/binding"
|
|
"github.guxuan/haibei/pkg/encoding/json"
|
|
"github.guxuan/haibei/pkg/errors"
|
|
"github.guxuan/haibei/pkg/logging"
|
|
"go.uber.org/zap"
|
|
)
|
|
|
|
// Get access token from header or query parameter
|
|
func GetToken(c *gin.Context) string {
|
|
var token string
|
|
auth := c.GetHeader("Authorization")
|
|
prefix := "Bearer "
|
|
|
|
if auth != "" && strings.HasPrefix(auth, prefix) {
|
|
token = auth[len(prefix):]
|
|
} else {
|
|
token = auth
|
|
}
|
|
|
|
if token == "" {
|
|
token = c.Query("accessToken")
|
|
}
|
|
|
|
return token
|
|
}
|
|
|
|
// Get body data from context
|
|
func GetBodyData(c *gin.Context) []byte {
|
|
if v, ok := c.Get(ReqBodyKey); ok {
|
|
if b, ok := v.([]byte); ok {
|
|
return b
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// Parse body json data to struct
|
|
func ParseJSON(c *gin.Context, obj interface{}) error {
|
|
if err := c.ShouldBindJSON(obj); err != nil {
|
|
return errors.BadRequest("", "Failed to parse json: %s", err.Error())
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// Parse query parameter to struct
|
|
func ParseQuery(c *gin.Context, obj interface{}) error {
|
|
if err := c.ShouldBindQuery(obj); err != nil {
|
|
return errors.BadRequest("", "Failed to parse query: %s", err.Error())
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// Parse body form data to struct
|
|
func ParseForm(c *gin.Context, obj interface{}) error {
|
|
if err := c.ShouldBindWith(obj, binding.Form); err != nil {
|
|
return errors.BadRequest("", "Failed to parse form: %s", err.Error())
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// Response json data with status code
|
|
func ResJSON(c *gin.Context, status int, v interface{}) {
|
|
buf, err := json.Marshal(v)
|
|
if err != nil {
|
|
panic(err)
|
|
}
|
|
|
|
c.Set(ResBodyKey, buf)
|
|
c.Data(status, "application/json; charset=utf-8", buf)
|
|
c.Abort()
|
|
}
|
|
|
|
func ResSuccess(c *gin.Context, v interface{}) {
|
|
ResJSON(c, http.StatusOK, ResponseResult{
|
|
Success: true,
|
|
Data: v,
|
|
})
|
|
}
|
|
|
|
func ResOK(c *gin.Context) {
|
|
ResJSON(c, http.StatusOK, ResponseResult{
|
|
Success: true,
|
|
})
|
|
}
|
|
|
|
func ResPage(c *gin.Context, v interface{}, pr *PaginationResult) {
|
|
var total int64
|
|
if pr != nil {
|
|
total = pr.Total
|
|
}
|
|
|
|
reflectValue := reflect.Indirect(reflect.ValueOf(v))
|
|
if reflectValue.IsNil() {
|
|
v = make([]interface{}, 0)
|
|
}
|
|
|
|
ResJSON(c, http.StatusOK, ResponseResult{
|
|
Success: true,
|
|
Data: v,
|
|
Total: total,
|
|
})
|
|
}
|
|
|
|
func ResError(c *gin.Context, err error, status ...int) {
|
|
var ierr *errors.Error
|
|
if e, ok := errors.As(err); ok {
|
|
ierr = e
|
|
} else {
|
|
ierr = errors.FromError(errors.InternalServerError("", err.Error()))
|
|
}
|
|
|
|
code := int(ierr.Code)
|
|
if len(status) > 0 {
|
|
code = status[0]
|
|
}
|
|
|
|
if code >= 500 {
|
|
ctx := c.Request.Context()
|
|
ctx = logging.NewTag(ctx, logging.TagKeySystem)
|
|
ctx = logging.NewStack(ctx, fmt.Sprintf("%+v", err))
|
|
logging.Context(ctx).Error("Internal server error", zap.Error(err))
|
|
ierr.Detail = http.StatusText(http.StatusInternalServerError)
|
|
}
|
|
|
|
ierr.Code = int32(code)
|
|
ResJSON(c, code, ResponseResult{Error: ierr})
|
|
}
|