Skip to content

Commit 7370a6d

Browse files
committed
update
1 parent fe3abc0 commit 7370a6d

File tree

12 files changed

+219
-112
lines changed

12 files changed

+219
-112
lines changed

README.md

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,17 @@
1212
- swagger
1313
-
1414

15+
## 项目说明
16+
17+
## 日志说明
18+
controller 如果出现异常则直接返回相关请求错误,不进行日志打印
19+
service 如果出现非
20+
dao出现异常,封装daoerr并返回,不进行打印,统一处理
21+
22+
1523

1624
info日志和sql日志分离,这样可以用于后续的监控或者是数据展示,可以用于数据分析等
17-
stack日志优化打印,其实已经可以了但是还是想要更加完善yidai9n
25+
stack日志优化打印,其实已经可以了但是还是想要更加完善
1826

1927
将分页逻辑抽离出去,不要和整个模板混在一起
2028
我们可以弄个什么适配器什么的,搞个分页器,这样只要传递条件就可以了,然后会默认的去走分页的逻辑

src/base/httper/http_handle.go

Lines changed: 36 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -1,68 +1,68 @@
11
package httper
22

33
import (
4-
"fmt"
54
"net/http"
65

76
"github.com/gin-gonic/gin"
8-
"github.com/pkg/errors"
97

108
"base/logger"
9+
"base/mistake"
1110
"base/validator"
1211
)
1312

14-
// 统一处理异常,统一处理日志,统一处理返回
15-
func HandleResponse(c *gin.Context, err error, data interface{}) {
16-
// 如果没有错误,就是正常请求
17-
if err == nil {
18-
SendResponseSuccess(c, "操作成功", data)
19-
return
20-
}
21-
22-
// 针对不同的错误类型进行处理
23-
switch errors.Cause(err).(type) {
24-
default:
25-
logStackInfo(err)
26-
SendResponseFail(c, http.StatusBadRequest, err.Error())
27-
}
28-
29-
return
30-
}
31-
3213
// 绑定参数并验证参数
3314
// true: 确实存在问题,会返回400错误
3415
// false: 不存在问题,验证通过
3516
func BindAndCheck(ctx *gin.Context, data interface{}) bool {
3617
// 参数映射
3718
if err := ctx.Bind(data); err != nil {
38-
HandleResponse(ctx, err, nil)
19+
HandleResponse(ctx, mistake.NewReqErr("请求参数绑定异常"), nil)
3920
return true
4021
}
4122

4223
// 验证参数
4324
if err := validator.GlobalValidate.Check(data); err != nil {
44-
HandleResponse(ctx, err, nil)
25+
HandleResponse(ctx, mistake.NewReqErr(err.Error()), nil)
4526
return true
4627
}
4728

4829
return false
4930
}
5031

51-
// 堆栈信息接口用于内部转换使用
52-
type stackTracer interface {
53-
StackTrace() errors.StackTrace
54-
}
32+
// 统一处理异常,统一处理日志,统一处理返回
33+
func HandleResponse(c *gin.Context, err error, data interface{}) {
34+
// 如果没有错误,就是正常请求
35+
if err == nil {
36+
SendResponseSuccess(c, "操作成功", data)
37+
return
38+
}
5539

56-
// 判断如果包含堆栈信息的封装就打印出相关堆栈信息,如果没有封装就打印原本错误信息
57-
func logStackInfo(err error) {
58-
if e, ok := err.(stackTracer); ok {
59-
stacks := e.StackTrace()
60-
var stackEntries []string
61-
for _, v := range stacks {
62-
stackEntries = append(stackEntries, fmt.Sprintf("%+v", v))
40+
// 针对不同的错误类型进行处理
41+
switch err.(type) {
42+
// 如果是请求参数异常,返回 400 直接返回err的错误信息
43+
case *mistake.ReqErr:
44+
SendResponseFail(c, http.StatusBadRequest, err.Error())
45+
46+
// 服务异常错误,返回 400 返回err的错误message信息,并打印日志记录
47+
case *mistake.ServiceErr:
48+
e := err.(*mistake.ServiceErr)
49+
if e.Err == nil {
50+
logger.Error(e.Message, "\n", e.Stack)
51+
} else {
52+
logger.Error(e.Message, "\n", e.Err, "\n", e.Stack)
6353
}
64-
logger.Error(stackEntries)
65-
} else {
66-
logger.Error(err)
54+
SendResponseFail(c, http.StatusBadRequest, e.Message)
55+
56+
// 数据层异常,返回 400 打印错误日志记录,这个错误信息不能返回到前端
57+
case *mistake.DaoErr:
58+
e := err.(*mistake.DaoErr)
59+
logger.Error(e.Err, "\n", e.Stack)
60+
SendResponseFail(c, http.StatusBadRequest, "数据异常")
61+
62+
// 未知错误,返回 500,证明此错误没有进行包装,直接被返回
63+
default:
64+
logger.Error(err, logger.LogStack(0, 0))
65+
SendResponseFail(c, http.StatusInternalServerError, "服务器端异常")
6766
}
67+
return
6868
}

src/base/logger/zap_impl.go

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,10 @@
11
package logger
22

33
import (
4+
"bytes"
5+
"fmt"
6+
"runtime"
7+
"strings"
48
"time"
59

610
"go.uber.org/zap"
@@ -12,7 +16,7 @@ var myLogger *ZapLogger
1216
var levelMapping = levelMap()
1317

1418
// 初始化日志框架
15-
func InitLogger(projectName, logPath string, maxAge, rotationTime time.Duration, level string) {
19+
func InitLogger(projectName, level, logPath string, maxAge, rotationTime time.Duration) {
1620
zaplog.InitZap(projectName, logPath, maxAge, rotationTime)
1721
// 设置打印堆栈深度,设置日志级别
1822
myLogger = &ZapLogger{
@@ -119,3 +123,26 @@ func (z *ZapLogger) Level() LogLevel {
119123
func (z *ZapLogger) SetLevel(l LogLevel) {
120124
z.level = l
121125
}
126+
127+
// 返回当前调用堆栈信息
128+
// start 起始调用栈层级
129+
// end 结束调用栈层级 输入0则会添加调用栈信息直到没有
130+
func LogStack(start, end int) string {
131+
stack := bytes.Buffer{}
132+
for i := start; i < end || end == 0; i++ {
133+
pc, str, line, _ := runtime.Caller(i)
134+
if line == 0 {
135+
break
136+
}
137+
138+
// 根据项目名称截短输出路径
139+
projectName := zaplog.YourProjectName
140+
index := strings.Index(str, projectName)
141+
if index != -1 {
142+
index = index + len(projectName) + 1
143+
str = str[index:]
144+
}
145+
stack.WriteString(fmt.Sprintf("%s:%d %s\n", str, line, runtime.FuncForPC(pc).Name()))
146+
}
147+
return stack.String()
148+
}

src/base/logger/zaplog/zap_log.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,15 +13,15 @@ import (
1313
"go.uber.org/zap/zapcore"
1414
)
1515

16-
var yourProjectName = "golang-web-template"
16+
var YourProjectName = "golang-web-template"
1717

1818
// projectName: 项目名称
1919
// logPath: 日志打印目录
2020
// maxAge: 日志最大存在时间,单位:天
2121
// rotationTime: 日志切分时间,单位:小时
2222
func InitZap(projectName, logPath string, maxAge, rotationTime time.Duration) {
2323
if len(projectName) != 0 {
24-
yourProjectName = projectName
24+
YourProjectName = projectName
2525
}
2626

2727
maxAge = maxAge * 24 * time.Hour
@@ -101,11 +101,11 @@ func InitZap(projectName, logPath string, maxAge, rotationTime time.Duration) {
101101
// 自定义打印路径,减少输出日志打印路径长度,根据输入项目名进行减少
102102
func customCallerEncoder(caller zapcore.EntryCaller, enc zapcore.PrimitiveArrayEncoder) {
103103
str := caller.String()
104-
index := strings.Index(str, yourProjectName)
104+
index := strings.Index(str, YourProjectName)
105105
if index == -1 {
106106
enc.AppendString(caller.FullPath())
107107
} else {
108-
index = index + len(yourProjectName) + 1
108+
index = index + len(YourProjectName) + 1
109109
enc.AppendString(str[index:])
110110
}
111111
}

src/base/mistake/common_err.go

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,54 @@
11
package mistake
2+
3+
import (
4+
"base/logger"
5+
)
6+
7+
// 请求参数异常
8+
type ReqErr struct {
9+
Message string
10+
}
11+
12+
func (e *ReqErr) Error() string {
13+
return e.Message
14+
}
15+
16+
func NewReqErr(message string) *ReqErr {
17+
return &ReqErr{Message: message}
18+
}
19+
20+
// 业务服务异常
21+
type ServiceErr struct {
22+
Message string
23+
Err error
24+
Stack string
25+
}
26+
27+
func (e *ServiceErr) Error() string {
28+
return e.Message
29+
}
30+
31+
func NewServiceErr(err error, message string) *ServiceErr {
32+
return &ServiceErr{
33+
Message: message,
34+
Err: err,
35+
Stack: logger.LogStack(2, 5),
36+
}
37+
}
38+
39+
// 数据层异常
40+
type DaoErr struct {
41+
Err error
42+
Stack string
43+
}
44+
45+
func (e *DaoErr) Error() string {
46+
return e.Err.Error()
47+
}
48+
49+
func NewDaoErr(err error) *DaoErr {
50+
return &DaoErr{
51+
Err: err,
52+
Stack: logger.LogStack(2, 5),
53+
}
54+
}

src/base/pager/pagination.go

Lines changed: 13 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,44 +1,43 @@
11
package pager
22

33
import (
4-
"errors"
54
"reflect"
65
)
76

87
// 分页模型
98
type PageModel struct {
10-
Page int `json:"page"`
9+
PageNum int `json:"page_num"`
1110
PageSize int `json:"page_size"`
1211
TotalPages int64 `json:"total_pages"`
1312
TotalRecords int64 `json:"total_records"`
1413
Records interface{} `json:"records"`
1514
}
1615

1716
// 构造分页对象
18-
// page: 当前页码
17+
// pageNum: 当前页码,从1开始
1918
// pageSize: 每页条数
2019
// totalRecords: 总条数
2120
// records: 分页数据,必须为slice,不能为nil或者其他对象,可以是空的slice
22-
func NewPageModel(page, pageSize int, totalRecords int64, records interface{}) *PageModel {
21+
func NewPageModel(pageNum, pageSize int, totalRecords int64, records interface{}) *PageModel {
2322
sliceValue := reflect.Indirect(reflect.ValueOf(records))
2423
if sliceValue.Kind() != reflect.Slice {
2524
panic("分页异常,需要传入一个slice类型")
2625
}
27-
28-
if page <= 0 {
29-
page = 1
30-
}
3126
if pageSize <= 0 {
32-
pageSize = 10
27+
panic("分页异常,每页条数必须为正数")
28+
}
29+
30+
if pageNum <= 0 {
31+
pageNum = 1
3332
}
3433
if totalRecords < 0 {
3534
totalRecords = 0
3635
}
3736

38-
totalPages, _ := calcTotalPages(int64(pageSize), totalRecords)
37+
totalPages := calcTotalPages(int64(pageSize), totalRecords)
3938

4039
return &PageModel{
41-
Page: page,
40+
PageNum: pageNum,
4241
PageSize: pageSize,
4342
TotalPages: totalPages,
4443
TotalRecords: totalRecords,
@@ -47,23 +46,15 @@ func NewPageModel(page, pageSize int, totalRecords int64, records interface{}) *
4746
}
4847

4948
// 计算页码逻辑
50-
func calcTotalPages(pageSize, totalRecords int64) (totalPages int64, err error) {
51-
if pageSize <= 0 {
52-
return 0, errors.New("page size should be positive integer")
53-
}
54-
55-
if totalRecords < 0 {
56-
return 0, errors.New("total records should not be negative integer")
57-
}
58-
49+
func calcTotalPages(pageSize, totalRecords int64) (totalPages int64) {
5950
if totalRecords == 0 {
60-
return 0, nil
51+
return 0
6152
}
6253

6354
if totalRecords%pageSize == 0 {
6455
totalPages = totalRecords / pageSize
6556
} else {
6657
totalPages = totalRecords/pageSize + 1
6758
}
68-
return totalPages, nil
59+
return totalPages
6960
}

src/base/validator/validator.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -58,10 +58,10 @@ func (m *MyValidator) Check(value interface{}) error {
5858
// 将所有的参数错误进行翻译然后拼装成字符串返回
5959
errBuf := bytes.Buffer{}
6060
for i := 0; i < len(errs); i++ {
61-
errBuf.WriteString(errs[i].Translate(m.Trans) + "\n ")
61+
errBuf.WriteString(errs[i].Translate(m.Trans) + " \n")
6262
}
6363

64-
// 删除掉最后一个换行符和空格
64+
// 删除掉最后一个空格和换行符
6565
errStr := errBuf.String()
6666
return errors.New(errStr[:len(errStr)-2])
6767
}

src/controller/user_controller.go

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,8 +65,8 @@ func UpdateUser(ctx *gin.Context) {
6565
httper.HandleResponse(ctx, err, nil)
6666
}
6767

68-
// @Summary 查询用户
69-
// @Description 查询用户
68+
// @Summary 根据id查询用户
69+
// @Description 根据id查询用户
7070
// @Tags User
7171
// @Accept json
7272
// @Produce json
@@ -79,6 +79,25 @@ func GetUser(ctx *gin.Context) {
7979
httper.HandleResponse(ctx, errors.New("参数错误"), nil)
8080
return
8181
}
82+
8283
u, err := service.GetUser(id)
8384
httper.HandleResponse(ctx, err, u)
8485
}
86+
87+
// @Summary 分页查询用户
88+
// @Description 分页查询用户
89+
// @Tags User
90+
// @Accept json
91+
// @Produce json
92+
// @Param data body val.UpdateUserReq true "分页用户条件信息"
93+
// @Success 200 {object} val.GetUsersReq
94+
// @Router /users [get]
95+
func ListUser(ctx *gin.Context) {
96+
getUsersReq := &val.GetUsersReq{}
97+
if httper.BindAndCheck(ctx, getUsersReq) {
98+
return
99+
}
100+
101+
pageModel, err := service.ListUser(getUsersReq)
102+
httper.HandleResponse(ctx, err, pageModel)
103+
}

0 commit comments

Comments
 (0)