Coder Social home page Coder Social logo

blog-service's People

Contributors

eddycjy avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

blog-service's Issues

gorm 2.0 callback

第二章 2.6 节中, models 回调用的是 gorm 1.0 版本,请问在 gorm 2.0 版本中如何处理?

2.3.2 配置管理 配置文件热更新后问题

配置文件热更新后,对于某些已使用的地方是无效的
main.go

       //  对于以下变量即使global.ServerSetting发生变化也是不会更新的
	gin.SetMode(global.ServerSetting.RunMode)

	router := routers.NewRouter()
	s := &http.Server{
		Addr:           ":" + global.ServerSetting.HttpPort,
		Handler:        router,
		ReadTimeout:    global.ServerSetting.ReadTimeout,
		WriteTimeout:   global.ServerSetting.WriteTimeout,
		MaxHeaderBytes: 1 << 20,
	}
       ...

router.go

        ...
        //  因为超时中间件参数是值传递,所以即使global.AppSetting.DefaultContextTimeout发生改变,该中间件还是只会使用首次注册时的参数值
	r.Use(middleware.ContextTimeout(global.AppSetting.DefaultContextTimeout))

解决:
修改context_timeout.go
ContextTimeout的值传递改为引用传递

func ContextTimeout(d *time.Duration) gin.HandlerFunc {
	return func(c *gin.Context) {
		ctx, cancel := context.WithTimeout(c.Request.Context(), *d)
                defer cancel()

		c.Request = c.Request.WithContext(ctx)
		c.Next()
	}
}

2.3.1 Error struct定义有警告

struct field code has json tag but is not exported。在网上找发现是字段首字母没大写,但用了json导致的。我看code,msg,details是通过下面的方法返回的,这样写有什么好处吗?

修改配置 热更新 时间配置的时候没有转化为纳秒,程序启动有转化为纳秒(其实不需要转化为纳秒,配置文件直接配置为 14s类似这样)

程序启动:

global.AppSetting.DefaultContextTimeout *= time.Second
global.JWTSetting.Expire *= time.Second
global.ServerSetting.ReadTimeout *= time.Second
global.ServerSetting.WriteTimeout *= time.Second

热更新:

func (s *Setting) ReloadAllSection() error {
	for k, v := range sections {
		err := s.ReadSection(k, v)
		if err != nil {
			return err
		}
	}

	return nil
}

2.5 为接口做参数校验 这一章 出现了 imported from implicitly required module

win10系统
go 1.16
复制文章源码或当前目录下源码到系统报错

`go: blog-service/pkg/app: package github.com/go-playground/universal-translator imported from implicitly required module; to add missing requirements, run:
go get github.com/go-playground/[email protected]
go: blog-service/internal/middleware: package github.com/go-playground/locales/en imported from implicitly required module; to add missing requirements, run:
go get github.com/go-playground/locales/[email protected]
go: blog-service/internal/middleware: package github.com/go-playground/locales/zh imported from implicitly required module; to add missing requirements, run:
go get github.com/go-playground/locales/[email protected]
go: blog-service/internal/middleware: package github.com/go-playground/locales/zh_Hant_TW imported from implicitly required module; to add missing requirements, run:
go get github.com/go-playground/locales/[email protected]
go: blog-service/internal/middleware: package github.com/go-playground/universal-translator imported from implicitly required module; to add missing requirements, run:
go get github.com/go-playground/[email protected]

Compilation finished with exit code 1`
image

spelling error

hello, There is a spelling error here.
File:internal/middleware/recovery.go:17:defailtMailer->defaultMailer

在完成 2.3.2 配置管理 后编译总提示yaml文件解析有问题

报错内容:
init.setupSetting err: While parsing config: yaml: line 11: did not find expected key

我将yaml直接替换为示例文件中的 yaml 编译是没问题的,但是把示例文件中除此章节涉及内容外多余部分删除,只保留此小节涉及内容,编译就会报错,挺奇怪。
反复检查很多次,并不是 yaml 格式的问题。

go 20下编译报错

github.com/go-programming-tour-book/blog-service/internal/routers

internal\routers\router.go:39:19: undefined: middleware.Tracing

logger 库中 withCaller 错误

withCaller() 的调用现在放在 mian.setupLogger 函数里,导致不管怎么打印,日志里的 callers 字段的值都是指向 main.init 函数。

我自己挪到了 Logger.Output 函数里

image

Cannot convert 'nil' to type 'any'

defer func() {
if err := recover(); err != nil {
global.Logger.WithCallersFrames().Errorf(c, "panic recover err: %v", err)

			err := defailtMailer.SendMail(
				global.EmailSetting.To,
				fmt.Sprintf("异常抛出,发生时间: %d", time.Now().Unix()),
				fmt.Sprintf("错误信息: %v", err),
			)
			if err != nil {
				global.Logger.Panicf(c, "mail.SendMail err: %v", err)
			}

			app.NewResponse(c).ToErrorResponse(errcode.ServerError)
			c.Abort()
		}
	}()

接口并发请求时报fatal error

测试方式: ab -c 10 -n 100 localhost:8000/debug/vars

测试结果:

fatal error: concurrent map read and map write

goroutine 139 [running]:
runtime.throw(0x4a46303, 0x21)
	/usr/local/go/src/runtime/panic.go:1116 +0x72 fp=0xc001b0c208 sp=0xc001b0c1d8 pc=0x4034962
runtime.mapaccess2(0x491bee0, 0xc0005cb080, 0xc001b0c288, 0x0, 0xc001a39601)
	/usr/local/go/src/runtime/map.go:469 +0x258 fp=0xc001b0c248 sp=0xc001b0c208 pc=0x400fbd8
github.com/go-playground/validator/v10.(*Validate).RegisterTranslation(0xc00008e4e0, 0x4a31dce, 0xc, 0x4bbb0e0, 0xc001a3bb60, 0xc001acc690, 0x4a6d278, 0x0, 0x0)
	/Users/hxj/godevspace/pkg/mod/github.com/go-playground/validator/[email protected]/validator_instance.go:261 +0xb0 fp=0xc001b0c2a8 sp=0xc001b0c248 pc=0x43ea6c0
github.com/go-playground/validator/v10/translations/zh.RegisterDefaultTranslations(0xc00008e4e0, 0x4bbb0e0, 0xc001a3bb60, 0x0, 0x62fdf00)
	/Users/hxj/godevspace/pkg/mod/github.com/go-playground/validator/[email protected]/translations/zh/zh.go:1321 +0x4f9 fp=0xc001b0d3b0 sp=0xc001b0c2a8 pc=0x480bfd9
github.com/go-programming-tour-book/blog-service/internal/middleware.Translations.func1(0xc000398000)
	/Users/hxj/Work/work_go/go-programming-tour-book/blog-service/internal/middleware/translations.go:30 +0x1ea fp=0xc001b0d458 sp=0xc001b0d3b0 pc=0x4816a8a
github.com/gin-gonic/gin.(*Context).Next(0xc000398000)
	/Users/hxj/godevspace/pkg/mod/github.com/gin-gonic/[email protected]/context.go:161 +0x3b fp=0xc001b0d478 sp=0xc001b0d458 pc=0x45e9f8b
github.com/go-programming-tour-book/blog-service/internal/middleware.ContextTimeout.func1(0xc000398000)
	/Users/hxj/Work/work_go/go-programming-tour-book/blog-service/internal/middleware/context_timeout.go:16 +0x14f fp=0xc001b0d4f8 sp=0xc001b0d478 pc=0x48161df
github.com/gin-gonic/gin.(*Context).Next(0xc000398000)
	/Users/hxj/godevspace/pkg/mod/github.com/gin-gonic/[email protected]/context.go:161 +0x3b fp=0xc001b0d518 sp=0xc001b0d4f8 pc=0x45e9f8b
github.com/go-programming-tour-book/blog-service/internal/middleware.RateLimiter.func1(0xc000398000)
	/Users/hxj/Work/work_go/go-programming-tour-book/blog-service/internal/middleware/limiter.go:23 +0x89 fp=0xc001b0d568 sp=0xc001b0d518 pc=0x4816449

修复方式: 去掉 translations.go中间件,将中间件中的函数内容放到main.go文件中,函数体:


// 在global包中定义全局变量

var Trans  ut.Translator

// InitTrans 初始化翻译器
func InitTrans(locale string) (err error) {
	// 修改gin框架中的Validator引擎属性,实现自定制
	if v, ok := binding.Validator.Engine().(*validator.Validate); ok {
		zhT := zh.New() // 中文翻译器
		enT := en.New() // 英文翻译器
		// 第一个参数是备用(fallback)的语言环境
		// 后面的参数是应该支持的语言环境(支持多个)
		// uni := ut.New(zhT, zhT) 也是可以的
		uni := ut.New(enT, zhT, enT)

		// locale 通常取决于 http 请求头的 'Accept-Language'
		var ok bool
		// 也可以使用 uni.FindTranslator(...) 传入多个locale进行查找
		global.Trans, ok = uni.GetTranslator(locale)
		if !ok {
			return fmt.Errorf("uni.GetTranslator(%s) failed", locale)
		}
		// 注册翻译器
		switch locale {
		case "en":
			err = enTranslations.RegisterDefaultTranslations(v, global.Trans)
		case "zh":
			err = zhTranslations.RegisterDefaultTranslations(v, global.Trans)
		default:
			err = enTranslations.RegisterDefaultTranslations(v, global.Trans)
		}
		return
	}
	return
}

在main()函数中调用:

func main() {

        if err := InitTrans("zh"); err != nil {
		fmt.Printf("init trans failed, err:%v\n", err)
		return
	}
        ......
}

修改pkg/app/form.go文件中的

BindAndValid(){
// 直接用全局变量
for key, value := range verrs.Translate(global.Trans) {
 ....
}
}

model/article.go Update执行失败

日志信息:

2020/07/16 00:03:10 {"caller":["/home/vaniot/dev/blog-service/main.go: 21 main.init.0"],"level":"error","message":"svc.UpdateArticle err: sql: expected 10 arguments, got 9","time":1594828990988757269}

关于书2.11节热更新的问题

按照书上的代码,我可以监听到热更新,接着我想测试一下是否可用。
我把runmode从debug改成了test,当我访问一个接口的时候控制台仍然会有logger输出,也就是说gin的模式并没有被更新。
我在想是不是调用了reloadallsection这个方法的时候,只是把global里的变量改了。
类似的情况还可以比如说更改端口号,更改数据库密码等等。都是只能监听到这些值的更新,但并没有影响到程序,还是得重启一遍才生效。
请大神们指点一下。

2.2.5 路由管理,代码中 {} 的作用是什么?

package routers

import (
	"github.com/gin-gonic/gin"
	v1 "github.com/qiuyuhome/go-gin-blog-api/internal/routers/api/v1"
)

func NewRouter() *gin.Engine {
	r := gin.New()
	r.Use(gin.Logger())
	r.Use(gin.Recovery())

	article := v1.NewArticle()
	tag := v1.NewTag()
	apiv1 := r.Group("/api/v1")

	// todo, 下面的 {} 的作用是什么?
	{
		apiv1.POST("/tags", tag.Create)
		apiv1.DELETE("/tags/:id", tag.Delete)
		apiv1.PUT("/tags/:id", tag.Update)
		apiv1.PATCH("/tags/:id/state", tag.Update)
		apiv1.GET("/tags", tag.List)
	
		apiv1.POST("/articles", article.Create)
		apiv1.DELETE("/articles/:id", article.Delete)
		apiv1.PUT("/articles/:id", article.Update)
		apiv1.PATCH("/articles/:id/state", article.Update)
		apiv1.GET("/articles/:id", article.Get)
		apiv1.GET("/articles", article.List)
	}

	return r
}

不理解这个 {} 的作用是什么? 去掉了也可以的。麻烦解答一下呗。

swagger 注解 json格式错误

项目中为
地址

// @Param tag_id body string true "标签ID"
// @Param title body string true "文章标题"
// @Param desc body string false "文章简述"
// @Param cover_image_url body string true "封面图片地址"
// @Param content body string true "文章内容"
// @Param created_by body int true "创建者"

实质应为

type Article struct {
	*Model
	Title         string `json:"title"`
	Desc          string `json:"desc"`
	Content       string `json:"content"`
	CoverImageUrl string `json:"cover_image_url"`
	State         uint8  `json:"state"`
}

@Param - body  Article  true  "标签ID"

参考:swaggo/gin-swagger#20

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.