You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
OneAuth/libs/base/api_handler.go

93 lines
1.9 KiB
Go

3 years ago
package base
import (
3 years ago
"errors"
3 years ago
"github.com/json-iterator/go"
"github.com/veypi/OneAuth/libs/oerr"
"github.com/veypi/OneAuth/libs/tools"
3 years ago
"github.com/veypi/OneBD"
"github.com/veypi/OneBD/rfc"
"github.com/veypi/utils/log"
3 years ago
"gorm.io/gorm"
3 years ago
"strconv"
"sync"
"time"
)
var json = jsoniter.ConfigFastest
3 years ago
func JSONResponse(m OneBD.Meta, data interface{}, err error) {
if err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
err = oerr.ResourceNotExist
}
}
if m.Method() == rfc.MethodHead {
if err != nil {
m.SetHeader("status", "0")
m.SetHeader("code", strconv.Itoa(int(oerr.OfType(err.Error()))))
m.SetHeader("err", err.Error())
} else {
m.SetHeader("status", "1")
}
return
}
res := map[string]interface{}{
"status": 1,
}
if err != nil {
res["status"] = 0
res["code"] = oerr.OfType(err.Error())
res["err"] = err.Error()
} else {
res["status"] = 1
res["content"] = data
}
p, err := json.Marshal(res)
if err != nil {
log.Warn().Err(err).Msg("encode json data error")
return
}
3 years ago
m.Header().Set("Access-Control-Allow-Origin", "*")
3 years ago
_, _ = m.Write(p)
}
3 years ago
type ApiHandler struct {
OneBD.BaseHandler
UserHandler
3 years ago
}
func (h *ApiHandler) Init(m OneBD.Meta) error {
return tools.MultiIniter(m, &h.BaseHandler, &h.UserHandler)
3 years ago
}
func (h *ApiHandler) OnResponse(data interface{}) {
3 years ago
JSONResponse(h.Meta(), data, nil)
3 years ago
}
func (h *ApiHandler) OnError(err error) {
log.WithNoCaller.Warn().Err(err).Msg(h.Meta().RequestPath())
3 years ago
JSONResponse(h.Meta(), nil, err)
3 years ago
}
var ioNumLimit = make(map[string]time.Time)
var limitLocker = sync.RWMutex{}
func (h *ApiHandler) SetAccessDelta(d time.Duration) error {
// 尽量对写操作加频率限制
now := time.Now()
limitLocker.Lock()
label := h.Meta().RemoteAddr() + h.Meta().RequestPath()
last, ok := ioNumLimit[label]
defer func() {
ioNumLimit[label] = now
limitLocker.Unlock()
}()
if !ok {
return nil
} else if now.Sub(last) >= d {
return nil
}
return oerr.AccessTooFast
}