1 安装wire
1.1 通过命令直接安装
go install github.com/google/wire/cmd/wire@latest
1.2 通过go get方式安装
go get github.com/google/wire/cmd/wire
进入目录编译
cd C:\Users\leell\go\pkg\mod\github.com\google\wire@v0.6.0\cmd\wire
go build
然后将wire.exe移动到 C:\Users\leell\go\bin目录下
具体目录通过go env进行查看
C:\Users\leell\go>go env
set GO111MODULE=on
set GOARCH=amd64
set GOBIN=C:\Users\leell\go\bin
2 配置业务代码
我没有按照beego的默认目录,而是通过自定义app包名进行业务模块化
2.1 分类模块
app/category/category_controller.go
type Controller struct {
beego.Controller
service *Service
}
func NewController(service *Service) *Controller {
return &Controller{service: service}
}
app/category/category_service.go
type Service struct {
dao *Dao
}
func NewService(dao *Dao) *Service {
return &Service{dao}
}
app/category/category_dao.go
type Dao struct {
}
func NewDao() *Dao {
return &Dao{}
}
app/category/module.go
var CategorySet = wire.NewSet(NewController, NewService, NewDao)
2.2 项目wire定义总提供者provider
provider/provider.go
var AppSet = wire.NewSet(NewBeanFactory, category.CategorySet)
2.3 给项目一个bean工厂
这点有点像spring的beanfactory,这里主要是:
(1)解决beego路由一开始执行init能够得到所有controller的实例
(2)go项目中存在recycle的循环依赖,这里就可以用beanFactory做一个中间过度
var (
appBeanFactory *BeanFactory
once sync.Once
)
type BeanFactory struct {
CategoryController *category.Controller
CollectVideoController *controllers.CollectVideoController
}
func NewBeanFactory(categoryController *category.Controller) *BeanFactory {
once.Do(func() {
appBeanFactory = &BeanFactory{
CategoryController: categoryController,
}
})
return appBeanFactory
}
3 wire配置代码及生成gen代码
wire/wire.go
//go:build wireinject
// +build wireinject
package wire
import (
"zhiqu/provider"
)
import "github.com/google/wire"
// wire.go 初始化模块
func NewApp() (*provider.BeanFactory, error) {
panic(wire.Build(provider.AppSet))
}
执行wire命令生成gen代码得到wire/wire_gen.go
wire gen wire/wire.go
生成最终代码文件内容
wire/wire_gen.go
// Code generated by Wire. DO NOT EDIT.
//go:generate go run -mod=mod github.com/google/wire/cmd/wire
//go:build !wireinject
// +build !wireinject
package wire
import (
"zhiqu/app/category"
"zhiqu/provider"
)
// Injectors from wire.go:
// wire.go 初始化模块
func NewApp() (*provider.BeanFactory, error) {
categoryDao := category.NewDao()
categoryService := category.NewService(categoryDao)
categoryController := category.NewController(categoryService)
beanFactory := provider.NewBeanFactory(categoryController)
return beanFactory, nil
}
4 路由配置
routers/router.go
// Package routers @APIVersion 1.0.0
// @Title beego Test API
// @Description beego has a very cool tools to autogenerate documents for your API
// @Contact astaxie@gmail.com
// @TermsOfServiceUrl http://beego.me/
// @License Apache 2.0
// @LicenseUrl http://www.apache.org/licenses/LICENSE-2.0.html
package routers
import (
beego "github.com/beego/beego/v2/server/web"
"zhiqu/wire"
)
func init() {
//通过wire获取beanfactory
beanFactory, err := wire.NewApp()
if err != nil {
panic(err)
}
ns := beego.NewNamespace("/v1",
beego.NSNamespace("/category",
beego.NSInclude(
beanFactory.CategoryController,
),
)
)
// 注册Swagger路由
//beego.SetStaticPath("/swagger", "swagger")
beego.AddNamespace(ns)
}
可以看出在路由文件中添加了wire生成的gen代码的获取的beanfactory工厂,然后将所有的单例go对象交由wire进行管理
5 根据controller上的注解生成路由自动映射
命令:由于我想做成业务模块化,而不是默认mvc的目录结构,所以添加-ctrlDir=app指定包含controller的目录app
C:\Users\leell\go\src\zhiqu>bee generate routers -ctrlDir=app
2024/04/27 19:09:54 WARN ▶ 0001 Your configuration file is outdated. Please do consider updating it.
______
| ___ \
| |_/ / ___ ___
| ___ \ / _ \ / _ \
| |_/ /| __/| __/
\____/ \___| \___| v2.1.0
2024/04/27 19:09:54 WARN ▶ 0002 Your configuration file is outdated. Please do consider updating it.
2024/04/27 19:09:54 INFO ▶ 0003 input parameter: [routers -ctrlDir=app]
2024/04/27 19:09:54 INFO ▶ 0004 read controller info from directory[app], and output routers to [routers/commentsRouter.go]
2024/04/27 19:09:56.660 [I] [gen_routes.go:421] generate router from comments
2024/04/27 19:09:56 INFO ▶ 0005 using routers as routers file's package
2024/04/27 19:09:56 SUCCESS ▶ 0006 Routers successfully generated!
最终生成的路由匹配文件内容
routers/commentsRouter.go
package routers
import (
beego "github.com/beego/beego/v2/server/web"
"github.com/beego/beego/v2/server/web/context/param"
)
func init() {
beego.GlobalControllerRouter["zhiqu/app/category:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/category:Controller"],
beego.ControllerComments{
Method: "Post",
Router: `/`,
AllowHTTPMethods: []string{"post"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
beego.GlobalControllerRouter["zhiqu/app/category:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/category:Controller"],
beego.ControllerComments{
Method: "GetAll",
Router: `/`,
AllowHTTPMethods: []string{"get"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
beego.GlobalControllerRouter["zhiqu/app/category:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/category:Controller"],
beego.ControllerComments{
Method: "GetOne",
Router: `/:id`,
AllowHTTPMethods: []string{"get"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
beego.GlobalControllerRouter["zhiqu/app/category:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/category:Controller"],
beego.ControllerComments{
Method: "Put",
Router: `/:id`,
AllowHTTPMethods: []string{"put"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
beego.GlobalControllerRouter["zhiqu/app/category:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/category:Controller"],
beego.ControllerComments{
Method: "Delete",
Router: `/:id`,
AllowHTTPMethods: []string{"delete"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
beego.GlobalControllerRouter["zhiqu/app/login:Controller"] = append(beego.GlobalControllerRouter["zhiqu/app/login:Controller"],
beego.ControllerComments{
Method: "Login",
Router: `/`,
AllowHTTPMethods: []string{"post"},
MethodParams: param.Make(),
Filters: nil,
Params: nil})
}