Compare commits
No commits in common. "8008fd4ddb6e5236284a8b9e43c431f8f591ab6e" and "c0cbff775f3831b251053cc165ba1d0c8362fe2c" have entirely different histories.
8008fd4ddb
...
c0cbff775f
40
.gitignore
vendored
40
.gitignore
vendored
@ -4,43 +4,3 @@ __debug_*
|
|||||||
*.tar
|
*.tar
|
||||||
*.zip
|
*.zip
|
||||||
*.gz
|
*.gz
|
||||||
|
|
||||||
|
|
||||||
# Binaries for programs and plugins
|
|
||||||
*.exe
|
|
||||||
*.exe~
|
|
||||||
*.dll
|
|
||||||
*.so
|
|
||||||
*.dylib
|
|
||||||
bin/
|
|
||||||
# Test binary, built with `go test -c`
|
|
||||||
*.test
|
|
||||||
|
|
||||||
# Output of the go coverage tool, specifically when used with LiteIDE
|
|
||||||
*.out
|
|
||||||
|
|
||||||
# Dependency directories (remove the comment below to include it)
|
|
||||||
# vendor/
|
|
||||||
|
|
||||||
#vscode
|
|
||||||
|
|
||||||
.vscode/*
|
|
||||||
!.vscode/settings.json
|
|
||||||
!.vscode/tasks.json
|
|
||||||
!.vscode/launch.json
|
|
||||||
!.vscode/extensions.json
|
|
||||||
!.vscode/*.code-snippets
|
|
||||||
|
|
||||||
# Local History for Visual Studio Code
|
|
||||||
.history/
|
|
||||||
|
|
||||||
# Built Visual Studio Code Extensions
|
|
||||||
*.vsix
|
|
||||||
|
|
||||||
__debug_bin
|
|
||||||
__debug_bin*
|
|
||||||
|
|
||||||
.idea
|
|
||||||
.vscode
|
|
||||||
|
|
||||||
screenlog.*
|
|
||||||
19
README.md
19
README.md
@ -3,33 +3,16 @@
|
|||||||
#### 介绍
|
#### 介绍
|
||||||
公共协议, 每个服务需要git submodule 拉 xxx/proto 目录下. 然后使用序列.
|
公共协议, 每个服务需要git submodule 拉 xxx/proto 目录下. 然后使用序列.
|
||||||
|
|
||||||
```
|
|
||||||
安装protoc protoc-25.0-linux-x86_64.zip
|
|
||||||
```
|
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# 去掉SUMDB的验证
|
git submodule add https://gitee.com/fusenpack/proto
|
||||||
go env -w GOSUMDB="off"
|
|
||||||
|
|
||||||
git submodule add git@gitlab.fusenpack.com:backend/proto.git
|
|
||||||
```
|
```
|
||||||
然后执行
|
然后执行
|
||||||
```bash
|
```bash
|
||||||
go install \
|
|
||||||
github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-grpc-gateway \
|
|
||||||
github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-openapiv2 \
|
|
||||||
google.golang.org/protobuf/cmd/protoc-gen-go \
|
|
||||||
google.golang.org/grpc/cmd/protoc-gen-go-grpc
|
|
||||||
|
|
||||||
go run proto/goutils/proto_build/main.go
|
go run proto/goutils/proto_build/main.go
|
||||||
或者
|
或者
|
||||||
在proto/goutils/proto_build/main_test.go执行测试 TestMain
|
在proto/goutils/proto_build/main_test.go执行测试 TestMain
|
||||||
|
|
||||||
./update_fspkg_master.sh # 执行更新最新的包
|
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#### 软件架构
|
#### 软件架构
|
||||||
软件架构说明
|
软件架构说明
|
||||||
|
|
||||||
|
|||||||
@ -54,10 +54,10 @@ func main() {
|
|||||||
|
|
||||||
if len(args) == 0 || args[0] == "service" {
|
if len(args) == 0 || args[0] == "service" {
|
||||||
ServiceMain()
|
ServiceMain()
|
||||||
} else if args[0] == "client" {
|
} else if args[0] == "gateway" {
|
||||||
GenClientMain()
|
GatewayMain()
|
||||||
} else {
|
} else {
|
||||||
log.Println("Invalid argument. Usage: go run main.go [service|client]")
|
log.Println("Invalid argument. Usage: go run main.go [service|gateway]")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -83,10 +83,6 @@ func ServiceMain() {
|
|||||||
|
|
||||||
defer createFileNotExists("protoc.sh", 0755, func(f io.Writer) error {
|
defer createFileNotExists("protoc.sh", 0755, func(f io.Writer) error {
|
||||||
shellstr := `#! /bin/bash
|
shellstr := `#! /bin/bash
|
||||||
if [ ! -d "proto" ] || [ -z "$(ls -A proto)" ]; then
|
|
||||||
git submodule init
|
|
||||||
git submodule update
|
|
||||||
fi
|
|
||||||
go run -gcflags="-N" proto/goutils/proto_build/main.go`
|
go run -gcflags="-N" proto/goutils/proto_build/main.go`
|
||||||
f.Write([]byte(shellstr))
|
f.Write([]byte(shellstr))
|
||||||
return nil
|
return nil
|
||||||
@ -108,26 +104,35 @@ go run -gcflags="-N" proto/goutils/proto_build/main.go`
|
|||||||
// log.Println("Found proto folder at:", workerSpaceDir, ServiceNames, projectLastName, projectName)
|
// log.Println("Found proto folder at:", workerSpaceDir, ServiceNames, projectLastName, projectName)
|
||||||
}
|
}
|
||||||
|
|
||||||
func GenClientMain() {
|
func GatewayMain() {
|
||||||
|
|
||||||
log.Println("项目目录:", workspaceDir)
|
log.Println("项目目录:", workspaceDir)
|
||||||
checkProtoMessageName(workspaceDir + "/" + "proto/service")
|
checkProtoMessageName(workspaceDir + "/" + "proto/service")
|
||||||
|
|
||||||
packageName := "service"
|
packageName := "service"
|
||||||
|
ServerCodePath := "server"
|
||||||
genDir := "gen/go"
|
genDir := "gen/go"
|
||||||
|
ServiceName, projectName, projectLastName := getServiceNameAndProjectName(ServerCodePath)
|
||||||
|
if ServiceName == "" {
|
||||||
|
err := os.MkdirAll("server", 0755)
|
||||||
|
if err != nil {
|
||||||
|
log.Println(err)
|
||||||
|
}
|
||||||
|
createFileWithPermNotExists("server/service_config.ini", func(f io.Writer) error {
|
||||||
|
return tpl.ExecuteTemplate(f, "service_config.tpl", nil)
|
||||||
|
})
|
||||||
|
panic("必须填写server/service_config.ini文件的项目名称与proto对应名称")
|
||||||
|
}
|
||||||
|
|
||||||
defer createFileNotExists("protoc.sh", 0755, func(f io.Writer) error {
|
defer createFileNotExists("protoc.sh", 0755, func(f io.Writer) error {
|
||||||
shellstr := `#! /bin/bash
|
shellstr := `#! /bin/bash
|
||||||
if [ ! -d "proto" ] || [ -z "$(ls -A proto)" ]; then
|
go run -gcflags="-N" proto/goutils/proto_build/main.go gateway`
|
||||||
git submodule init
|
|
||||||
git submodule update
|
|
||||||
fi
|
|
||||||
go run -gcflags="-N" proto/goutils/proto_build/main.go client`
|
|
||||||
f.Write([]byte(shellstr))
|
f.Write([]byte(shellstr))
|
||||||
return nil
|
return nil
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// genDir := fmt.Sprintf("gen/go/%s", PackageName)
|
||||||
|
|
||||||
serviceProtoDir := fmt.Sprintf("proto/%s", packageName)
|
serviceProtoDir := fmt.Sprintf("proto/%s", packageName)
|
||||||
|
|
||||||
err := os.MkdirAll(genDir+"/"+packageName, 0755)
|
err := os.MkdirAll(genDir+"/"+packageName, 0755)
|
||||||
@ -135,16 +140,10 @@ go run -gcflags="-N" proto/goutils/proto_build/main.go client`
|
|||||||
log.Println(err)
|
log.Println(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
projectName := "gitlab.fusenpack.com/backend/grpc"
|
|
||||||
|
|
||||||
CheckGomodBasicPackage()
|
|
||||||
ExecProtoc(workspaceDir, serviceProtoDir, genDir, packageName, projectName)
|
ExecProtoc(workspaceDir, serviceProtoDir, genDir, packageName, projectName)
|
||||||
GitignoreGenCheck()
|
|
||||||
ExecCreateAutoGrpc(genDir, packageName)
|
ExecCreateAutoGrpc(genDir, packageName)
|
||||||
|
ExecCreateConfig(ServiceName, projectLastName)
|
||||||
createFileNotExists("update_fspkg_master.sh", 0755, func(f io.Writer) error {
|
ExecCreateGatewayAutoGrpc(genDir, packageName, projectLastName)
|
||||||
return tpl.ExecuteTemplate(f, "update_fspkg_master.tpl", nil)
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func ExecCreateConfig(ServiceName, ProjectName string) {
|
func ExecCreateConfig(ServiceName, ProjectName string) {
|
||||||
@ -191,11 +190,16 @@ func CheckGomodBasicPackage() {
|
|||||||
if !regexp.MustCompile(`fusen-basic `).Match(data) {
|
if !regexp.MustCompile(`fusen-basic `).Match(data) {
|
||||||
log.Println(isRewrite, len(content))
|
log.Println(isRewrite, len(content))
|
||||||
isRewrite = true
|
isRewrite = true
|
||||||
content += "\n\nreplace fusen-basic v0.0.0 => gitlab.fusenpack.com/backend/basic v0.0.1"
|
content += "\n\nreplace fusen-basic v0.0.0 => gitee.com/fusenpack/fusen-basic v0.0.1"
|
||||||
|
}
|
||||||
|
|
||||||
|
if !regexp.MustCompile(`fusen-model `).Match(data) {
|
||||||
|
isRewrite = true
|
||||||
|
content += "\n\nreplace fusen-model v0.0.0 => gitee.com/fusenpack/fusen-model v0.0.1"
|
||||||
}
|
}
|
||||||
|
|
||||||
if isRewrite {
|
if isRewrite {
|
||||||
log.Println("rewrite go.mod => add <fusen-basic>")
|
log.Println("rewrite go.mod => add <fusen-basic> <fusen-model>")
|
||||||
err = os.WriteFile("./go.mod", []byte(content), 0644)
|
err = os.WriteFile("./go.mod", []byte(content), 0644)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
@ -208,7 +212,7 @@ func ExecProtoc(workerSpaceDir, serviceProtoDir, genDir, packageName string, pro
|
|||||||
|
|
||||||
allServiceNames := getAllServiceName()
|
allServiceNames := getAllServiceName()
|
||||||
|
|
||||||
protoCmdStr := fmt.Sprintf(`protoc -I %s --go_out %s --go_opt paths=source_relative --go-grpc_out %s --go-grpc_opt paths=source_relative `, "proto", genDir, genDir)
|
protoCmdStr := fmt.Sprintf(`protoc -I %s --go_out %s --go_opt paths=source_relative --go-grpc_out %s --go-grpc_opt paths=source_relative --grpc-gateway_out %s --grpc-gateway_opt paths=source_relative`, "proto", genDir, genDir, genDir)
|
||||||
for _, sname := range allServiceNames {
|
for _, sname := range allServiceNames {
|
||||||
protoCmdStr += importFileCmdStr(serviceNameEncode(packageName, sname), projectName)
|
protoCmdStr += importFileCmdStr(serviceNameEncode(packageName, sname), projectName)
|
||||||
}
|
}
|
||||||
@ -263,12 +267,6 @@ func ExecCreateAutoLogic(workerSpaceDir string, ServiceName string, genDir, pack
|
|||||||
// 处理main.go文件
|
// 处理main.go文件
|
||||||
defer func() {
|
defer func() {
|
||||||
// name := underscoreToLowerCamelCase(ServiceName)
|
// name := underscoreToLowerCamelCase(ServiceName)
|
||||||
|
|
||||||
// name := underscoreToLowerCamelCase(ServiceName)
|
|
||||||
createFile("server/main_gen.go", func(f io.Writer) error {
|
|
||||||
return tpl.ExecuteTemplate(f, "main_gen.tpl", mtpl)
|
|
||||||
})
|
|
||||||
|
|
||||||
createFileWithPermNotExists("server/main.go", func(f io.Writer) error {
|
createFileWithPermNotExists("server/main.go", func(f io.Writer) error {
|
||||||
return tpl.ExecuteTemplate(f, "main.tpl", mtpl)
|
return tpl.ExecuteTemplate(f, "main.tpl", mtpl)
|
||||||
})
|
})
|
||||||
@ -294,41 +292,15 @@ func ExecCreateAutoLogic(workerSpaceDir string, ServiceName string, genDir, pack
|
|||||||
for _, info := range infos {
|
for _, info := range infos {
|
||||||
// logicStructNames = append(logicStructNames, info.StructName)
|
// logicStructNames = append(logicStructNames, info.StructName)
|
||||||
|
|
||||||
var methods []map[string]interface{}
|
var methods []map[string]string
|
||||||
|
|
||||||
for _, met := range info.Method {
|
for _, met := range info.Method {
|
||||||
var dup map[string]bool = make(map[string]bool)
|
|
||||||
|
|
||||||
var paramsName []string
|
methodMap := map[string]string{
|
||||||
var paramsAndType []string
|
|
||||||
for i, param := range met.Params {
|
|
||||||
var p string
|
|
||||||
if param == "context.Context" {
|
|
||||||
dup["ctx"] = true
|
|
||||||
p = "ctx"
|
|
||||||
} else {
|
|
||||||
plist := strings.Split(param, ".")
|
|
||||||
lowerName := strings.ToLower(plist[len(plist)-1])
|
|
||||||
if strings.Contains(lowerName, "req") {
|
|
||||||
if _, ok := dup["ctx"]; ok {
|
|
||||||
p = "req"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if _, ok := dup[p]; ok {
|
|
||||||
p = fmt.Sprintf("param%d", i)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
param = p + " " + param
|
|
||||||
paramsAndType = append(paramsAndType, param)
|
|
||||||
paramsName = append(paramsName, p)
|
|
||||||
}
|
|
||||||
|
|
||||||
methodMap := map[string]interface{}{
|
|
||||||
"StructName": info.StructName,
|
"StructName": info.StructName,
|
||||||
"MethodType": met.MethodType,
|
|
||||||
"MethodName": met.MethodName,
|
"MethodName": met.MethodName,
|
||||||
"ParamsName": paramsName,
|
"ParamCtx": met.Params[0],
|
||||||
"Params": paramsAndType,
|
"ParamReq": met.Params[1],
|
||||||
"MethodReturn": met.Returns[0],
|
"MethodReturn": met.Returns[0],
|
||||||
"MethodResponse": met.Returns[0][1:],
|
"MethodResponse": met.Returns[0][1:],
|
||||||
}
|
}
|
||||||
@ -369,9 +341,8 @@ func ExecCreateAutoLogic(workerSpaceDir string, ServiceName string, genDir, pack
|
|||||||
// log.Println(genTypesBuffer.String())
|
// log.Println(genTypesBuffer.String())
|
||||||
formatted, err := format.Source(genTypesBuffer.Bytes())
|
formatted, err := format.Source(genTypesBuffer.Bytes())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Println(genTypesBuffer.String())
|
log.Printf("格式化代码失败:%v\n", err)
|
||||||
// panic(fmt.Sprintf("格式化代码失败:%v\n", err))
|
return
|
||||||
formatted = genTypesBuffer.Bytes()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
_, err = f.Write(formatted)
|
_, err = f.Write(formatted)
|
||||||
@ -392,7 +363,7 @@ func ExecCreateAutoLogic(workerSpaceDir string, ServiceName string, genDir, pack
|
|||||||
ss.StructServiceName = info.ServiceName
|
ss.StructServiceName = info.ServiceName
|
||||||
|
|
||||||
for _, method := range methods {
|
for _, method := range methods {
|
||||||
fileName := convertToSnakeCase(method["MethodName"].(string))
|
fileName := convertToSnakeCase(method["MethodName"])
|
||||||
method["ProjectName"] = projectName
|
method["ProjectName"] = projectName
|
||||||
method["PackageName"] = logicPackageName
|
method["PackageName"] = logicPackageName
|
||||||
createFileWithPermNotExists(fmt.Sprintf("%s/%s_logic.go", logicPath, fileName), func(f io.Writer) error {
|
createFileWithPermNotExists(fmt.Sprintf("%s/%s_logic.go", logicPath, fileName), func(f io.Writer) error {
|
||||||
@ -413,15 +384,15 @@ func ExecCreateTest(genDir, projectName, packageName, serviceName string) {
|
|||||||
|
|
||||||
genDir = genDir + "/" + packageName
|
genDir = genDir + "/" + packageName
|
||||||
|
|
||||||
var struCollection []*GrpcMethodTest
|
var struCollection []*HttpGrpcMethodTest
|
||||||
for _, gwPath := range getSuffixFilesPath(genDir, strings.ToLower(serviceName)+"_grpc.pb.go") {
|
for _, gwPath := range getSuffixFilesPath(genDir, strings.ToLower(serviceName)+".pb.gw.go") {
|
||||||
struCollection = append(struCollection, genGatewayTestFunction(gwPath)...)
|
struCollection = append(struCollection, genGatewayTestFunction(gwPath)...)
|
||||||
}
|
}
|
||||||
|
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
err := tpl.ExecuteTemplate(&buf, "http_grpc_method_test.tpl", map[string]any{
|
err := tpl.ExecuteTemplate(&buf, "http_grpc_method_test.tpl", map[string]any{
|
||||||
"ProjectName": projectName,
|
"ProjectName": projectName,
|
||||||
"GrpcTestStructs": struCollection,
|
"HttpGrpcTestStructs": struCollection,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
@ -734,15 +705,16 @@ func genGatewayWithNacosFunction(grpcPath string, gatewayBuf *bytes.Buffer) (fun
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
type GrpcMethodTest struct {
|
type HttpGrpcMethodTest struct {
|
||||||
RequestVar string
|
RequestVar string
|
||||||
RequestStruct string
|
RequestStruct string
|
||||||
Params []string
|
|
||||||
MethodName string
|
MethodName string
|
||||||
|
HttpMethod string
|
||||||
|
UrlPath string
|
||||||
ServiceName string
|
ServiceName string
|
||||||
}
|
}
|
||||||
|
|
||||||
func genGatewayTestFunction(grpcPath string) (createdCollection []*GrpcMethodTest) {
|
func genGatewayTestFunction(grpcPath string) (createdCollection []*HttpGrpcMethodTest) {
|
||||||
// workerSpaceDir+"/gen/go/service/auth_grpc.pb.go"
|
// workerSpaceDir+"/gen/go/service/auth_grpc.pb.go"
|
||||||
// 解析Go源文件
|
// 解析Go源文件
|
||||||
fset := token.NewFileSet()
|
fset := token.NewFileSet()
|
||||||
@ -752,72 +724,74 @@ func genGatewayTestFunction(grpcPath string) (createdCollection []*GrpcMethodTes
|
|||||||
os.Exit(1)
|
os.Exit(1)
|
||||||
}
|
}
|
||||||
|
|
||||||
// var i = 0
|
|
||||||
for _, decl := range node.Decls {
|
for _, decl := range node.Decls {
|
||||||
// 检查是否是接口声明
|
// 检查是否是接口声明
|
||||||
if fdec, ok := decl.(*ast.GenDecl); ok && fdec.Tok == token.TYPE {
|
if fdec, ok := decl.(*ast.FuncDecl); ok && fdec.Name.IsExported() && strings.HasSuffix(fdec.Name.Name, "HandlerServer") {
|
||||||
// ast.Print(fset, fdec)
|
|
||||||
for _, spec := range fdec.Specs {
|
|
||||||
if typeSpec, ok := spec.(*ast.TypeSpec); ok && strings.HasSuffix(typeSpec.Name.Name, "Server") && !strings.HasPrefix(typeSpec.Name.Name, "Unsafe") && !strings.Contains(typeSpec.Name.Name, "_") {
|
|
||||||
|
|
||||||
serviceName := typeSpec.Name.Name
|
created := &HttpGrpcMethodTest{}
|
||||||
serviceName = serviceName[:len(serviceName)-6]
|
// 修改函数执行内容
|
||||||
ast.Inspect(typeSpec, func(interfaceNode ast.Node) bool {
|
ast.Inspect(fdec.Body, func(n ast.Node) bool {
|
||||||
|
|
||||||
if methodDecl, ok := interfaceNode.(*ast.Ident); ok && methodDecl.IsExported() {
|
if callExpr, ok := n.(*ast.CallExpr); ok {
|
||||||
// log.Println(ftype.)
|
|
||||||
if methodDecl.Obj != nil {
|
|
||||||
if methodDecl.Obj.Kind == ast.Fun {
|
|
||||||
// log.Println(typeSpec.Name.Name)
|
|
||||||
// log.Println(methodDecl.Name)
|
|
||||||
|
|
||||||
created := GrpcMethodTest{}
|
if expr, ok := callExpr.Fun.(*ast.Ident); ok && strings.HasPrefix(expr.Name, "local_request") {
|
||||||
|
// log.Println(expr.Obj.Decl.(*ast.FuncDecl))
|
||||||
|
|
||||||
created.ServiceName = serviceName
|
created.ServiceName = strings.Split(expr.Name, "_")[2]
|
||||||
created.MethodName = methodDecl.Name
|
|
||||||
|
ast.Inspect(expr.Obj.Decl.(*ast.FuncDecl).Body, func(n ast.Node) bool {
|
||||||
|
|
||||||
|
if protoValue, ok := n.(*ast.ValueSpec); ok && protoValue.Names[0].Name == "protoReq" {
|
||||||
|
// log.Println(getTypeString(protoValue.Type))
|
||||||
|
created.RequestStruct = getTypeString(protoValue.Type)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if expr, ok := n.(*ast.SelectorExpr); ok {
|
||||||
|
if exprServer, ok := expr.X.(*ast.Ident); ok && exprServer.Name == "server" {
|
||||||
|
// log.Println(expr.Sel.Name, expr.X)
|
||||||
|
created.MethodName = expr.Sel.Name
|
||||||
|
createdCollection = append(createdCollection, created)
|
||||||
created.RequestVar = "var" + created.MethodName + "Req"
|
created.RequestVar = "var" + created.MethodName + "Req"
|
||||||
field := methodDecl.Obj.Decl.(*ast.Field)
|
|
||||||
ftype := field.Type.(*ast.FuncType)
|
|
||||||
if len(ftype.Params.List) == 2 {
|
|
||||||
if reqstruct, ok := ftype.Params.List[1].Type.(*ast.StarExpr); ok {
|
|
||||||
rname := reqstruct.X.(*ast.Ident)
|
|
||||||
created.RequestStruct = rname.Name
|
|
||||||
createdCollection = append(createdCollection, &created)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// ast.Print(fset, ftype)
|
|
||||||
|
|
||||||
}
|
created = &HttpGrpcMethodTest{}
|
||||||
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ast.Print(fset, n)
|
|
||||||
// i++
|
|
||||||
// log.Println(i)
|
|
||||||
// if i == 7 {
|
|
||||||
// log.Println()
|
|
||||||
// }
|
|
||||||
// printer.Fprint(os.Stdout, fset, n)
|
|
||||||
// io.WriteString(os.Stdout, "\n")
|
|
||||||
// if ftype, ok := n.(*ast.FuncType); ok {
|
|
||||||
// log.Println(getTypeString(ftype))
|
|
||||||
// ast.Print(fset, ftype)
|
|
||||||
// }
|
|
||||||
|
|
||||||
return true
|
return true
|
||||||
})
|
})
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// log.Println(callExpr.Fun)
|
||||||
|
// getTypeString(callExpr.Fun)
|
||||||
|
if expr, ok := callExpr.Fun.(*ast.SelectorExpr); ok && expr.Sel.Name == "Handle" {
|
||||||
|
|
||||||
|
var x = callExpr.Args[0].(*ast.BasicLit)
|
||||||
|
// log.Println(x, x.Value)
|
||||||
|
created.HttpMethod = x.Value
|
||||||
|
ast.Inspect(callExpr, func(n ast.Node) bool {
|
||||||
|
if callExprHandler, ok := n.(*ast.CallExpr); ok {
|
||||||
|
if expr, ok := callExprHandler.Fun.(*ast.SelectorExpr); ok && expr.Sel.Name == "WithHTTPPathPattern" {
|
||||||
|
var x = callExprHandler.Args[0].(*ast.BasicLit)
|
||||||
|
created.UrlPath = x.Value
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// created.RequestVar = "var" + created.MethodName + "Req"
|
return true
|
||||||
|
})
|
||||||
// 修改函数执行内容
|
return true
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
return true
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -868,7 +842,7 @@ func getGrpcFileClientNames(genDir string) (result []*ClientParam) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func importFileCmdStr(importFile string, projectName string) string {
|
func importFileCmdStr(importFile string, projectName string) string {
|
||||||
shellStr := " {{.ImportFile}} --go_opt=M{{.ImportFile}}={{.ProjectName}} --go-grpc_opt=M{{.ImportFile}}={{.ProjectName}}"
|
shellStr := " {{.ImportFile}} --go_opt=M{{.ImportFile}}={{.ProjectName}} --go-grpc_opt=M{{.ImportFile}}={{.ProjectName}} --grpc-gateway_opt=M{{.ImportFile}}={{.ProjectName}} "
|
||||||
|
|
||||||
tmpl, err := template.New("shell").Parse(shellStr)
|
tmpl, err := template.New("shell").Parse(shellStr)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -890,7 +864,6 @@ func importFileCmdStr(importFile string, projectName string) string {
|
|||||||
log.Printf("模板执行失败:%v\n", err)
|
log.Printf("模板执行失败:%v\n", err)
|
||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
// log.Println(buf.String())
|
|
||||||
return buf.String()
|
return buf.String()
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -944,15 +917,13 @@ func getAllServiceName() (result []string) {
|
|||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
for _, e := range dirEntrys {
|
for _, e := range dirEntrys {
|
||||||
if filepath.Ext(e.Name()) == ".proto" {
|
|
||||||
result = append(result, e.Name()[0:len(e.Name())-6])
|
result = append(result, e.Name()[0:len(e.Name())-6])
|
||||||
}
|
}
|
||||||
}
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// 获取项目的参数
|
// 获取项目的参数
|
||||||
func getServiceNameAndProjectName(dir string) (serviceName string, projectName string, goModeName string) {
|
func getServiceNameAndProjectName(dir string) (serviceName string, projectName string, projectLastName string) {
|
||||||
|
|
||||||
ifile, err := ini.Load(dir + "/service_config.ini")
|
ifile, err := ini.Load(dir + "/service_config.ini")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -989,18 +960,7 @@ func getServiceNameAndProjectName(dir string) (serviceName string, projectName s
|
|||||||
}
|
}
|
||||||
|
|
||||||
paths := strings.Split(projectName, "/")
|
paths := strings.Split(projectName, "/")
|
||||||
goModeName = paths[len(paths)-1]
|
projectLastName = paths[len(paths)-1]
|
||||||
|
|
||||||
moddata, err := os.ReadFile("go.mod")
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
result := regexp.MustCompile(`module\s+([a-zA-Z_\-]+)`).FindAllStringSubmatch(string(moddata), 1)
|
|
||||||
if len(result) == 0 {
|
|
||||||
panic("无法找到go.mod 获取 module信息")
|
|
||||||
}
|
|
||||||
goModeName = result[0][1]
|
|
||||||
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -1078,23 +1038,9 @@ func parseGoFile(filePath string) (ClientParams []*ClientParam) {
|
|||||||
// fieldName := field.Names[0].Name
|
// fieldName := field.Names[0].Name
|
||||||
// log.Println("Field:", fieldName)
|
// log.Println("Field:", fieldName)
|
||||||
}
|
}
|
||||||
} else if iface, ok := typeSpec.Type.(*ast.InterfaceType); ok {
|
} else if _, ok := typeSpec.Type.(*ast.InterfaceType); ok {
|
||||||
interfaceName := typeSpec.Name.Name
|
interfaceName := typeSpec.Name.Name
|
||||||
|
|
||||||
if len(iface.Methods.List) >= 3 {
|
|
||||||
if len(iface.Methods.List[2].Names) == 0 {
|
|
||||||
|
|
||||||
// log.Println(name0, name1)
|
|
||||||
if getTypeString(iface.Methods.List[2].Type) == "grpc.ClientStream" {
|
|
||||||
// MethodType = "stream"
|
|
||||||
// log.Println(interfaceName)
|
|
||||||
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if strings.HasSuffix(interfaceName, "Client") {
|
if strings.HasSuffix(interfaceName, "Client") {
|
||||||
Param.ClientName = interfaceName[0 : len(interfaceName)-6]
|
Param.ClientName = interfaceName[0 : len(interfaceName)-6]
|
||||||
}
|
}
|
||||||
@ -1121,7 +1067,6 @@ func parseGoFile(filePath string) (ClientParams []*ClientParam) {
|
|||||||
|
|
||||||
type GrpcServerMethod struct {
|
type GrpcServerMethod struct {
|
||||||
MethodName string
|
MethodName string
|
||||||
MethodType string
|
|
||||||
Params []string
|
Params []string
|
||||||
Returns []string
|
Returns []string
|
||||||
}
|
}
|
||||||
@ -1161,30 +1106,10 @@ func ParseGrpcServerInfo(grpcPath string) (infos []*GrpcServerInfo) {
|
|||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
if strings.Contains(ifaceSpec.Name.Name, "_") {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
if strings.HasPrefix(ifaceSpec.Name.Name, "Unsafe") {
|
if strings.HasPrefix(ifaceSpec.Name.Name, "Unsafe") {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(ifaceType.Methods.List) == 3 {
|
|
||||||
if len(ifaceType.Methods.List[0].Names) == 1 && len(ifaceType.Methods.List[1].Names) == 1 {
|
|
||||||
name0 := ifaceType.Methods.List[0].Names[0].Name
|
|
||||||
name1 := ifaceType.Methods.List[1].Names[0].Name
|
|
||||||
if name0 == "SendAndClose" && name1 == "Recv" {
|
|
||||||
// log.Println(name0, name1)
|
|
||||||
if getTypeString(ifaceType.Methods.List[2].Type) == "grpc.ServerStream" {
|
|
||||||
// MethodType = "stream"
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ServiceName := ifaceSpec.Name.Name[0 : len(ifaceSpec.Name.Name)-6]
|
ServiceName := ifaceSpec.Name.Name[0 : len(ifaceSpec.Name.Name)-6]
|
||||||
info := &GrpcServerInfo{
|
info := &GrpcServerInfo{
|
||||||
ServiceName: ServiceName,
|
ServiceName: ServiceName,
|
||||||
@ -1197,40 +1122,29 @@ func ParseGrpcServerInfo(grpcPath string) (infos []*GrpcServerInfo) {
|
|||||||
// 打印接口方法
|
// 打印接口方法
|
||||||
for _, method := range ifaceType.Methods.List {
|
for _, method := range ifaceType.Methods.List {
|
||||||
|
|
||||||
if len(method.Names) == 0 {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
if !isUpper(method.Names[0].Name) {
|
if !isUpper(method.Names[0].Name) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
m := &GrpcServerMethod{
|
m := &GrpcServerMethod{}
|
||||||
MethodType: "rpc",
|
|
||||||
}
|
|
||||||
info.Method = append(info.Method, m)
|
info.Method = append(info.Method, m)
|
||||||
// 方法名称
|
// 方法名称
|
||||||
// log.Println("方法名:", method.Names[0].Name)
|
// log.Println("方法名:", method.Names[0].Name)
|
||||||
// MethodName := method.Names[0].Name
|
// MethodName := method.Names[0].Name
|
||||||
m.MethodName = method.Names[0].Name
|
m.MethodName = method.Names[0].Name
|
||||||
// 方法参数
|
// 方法参数
|
||||||
mparams := method.Type.(*ast.FuncType).Params.List
|
if len(method.Type.(*ast.FuncType).Params.List) > 0 {
|
||||||
switch len(mparams) {
|
// log.Println("参数:")
|
||||||
case 2:
|
// params := method.Type.(*ast.FuncType).Params
|
||||||
for _, field := range mparams {
|
// log.Println(params.NumFields(), params.List)
|
||||||
|
// log.Println(string(src[method.Pos()-1 : method.End()-1]))
|
||||||
|
|
||||||
|
for _, field := range method.Type.(*ast.FuncType).Params.List {
|
||||||
// log.Printf("%s %s\n", field.Names, getTypeString(field.Type, packageName, 0))
|
// log.Printf("%s %s\n", field.Names, getTypeString(field.Type, packageName, 0))
|
||||||
m.Params = append(m.Params, getTypeString(field.Type, packageName))
|
m.Params = append(m.Params, getTypeString(field.Type, packageName))
|
||||||
}
|
}
|
||||||
case 1:
|
} else {
|
||||||
m.MethodType = "stream"
|
|
||||||
for _, field := range mparams {
|
|
||||||
// log.Printf("%s %s\n", field.Names, getTypeString(field.Type, packageName, 0))
|
|
||||||
m.Params = append(m.Params, getTypeString(field.Type, packageName))
|
|
||||||
}
|
|
||||||
case 0:
|
|
||||||
log.Println("无参数")
|
log.Println("无参数")
|
||||||
default:
|
|
||||||
panic("诡异的结构")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 方法返回值
|
// 方法返回值
|
||||||
@ -1321,34 +1235,6 @@ func _getTypeString(expr ast.Expr, packageName *string, level int) string {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func createFile(filename string, do func(f io.Writer) error) error {
|
|
||||||
// 检测文件是否存在
|
|
||||||
|
|
||||||
file, err := os.OpenFile(filename, os.O_CREATE|os.O_TRUNC|os.O_WRONLY, 0644)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
defer file.Close()
|
|
||||||
|
|
||||||
var buf = bytes.NewBuffer(nil)
|
|
||||||
err = do(buf)
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
data, err := format.Source(buf.Bytes())
|
|
||||||
if err != nil {
|
|
||||||
_, err = file.Write(buf.Bytes())
|
|
||||||
} else {
|
|
||||||
_, err = file.Write(data)
|
|
||||||
}
|
|
||||||
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func createFileWithPermNotExists(filename string, do func(f io.Writer) error) error {
|
func createFileWithPermNotExists(filename string, do func(f io.Writer) error) error {
|
||||||
// 检测文件是否存在
|
// 检测文件是否存在
|
||||||
_, err := os.Stat(filename)
|
_, err := os.Stat(filename)
|
||||||
@ -1537,28 +1423,3 @@ func getGrpcFileServiceName(decl ast.Decl) (string, string, bool) {
|
|||||||
}
|
}
|
||||||
return "", "", false
|
return "", "", false
|
||||||
}
|
}
|
||||||
|
|
||||||
// 检测gitignore gen是否存在
|
|
||||||
func GitignoreGenCheck() {
|
|
||||||
|
|
||||||
gitignoreFile := "./.gitignore"
|
|
||||||
|
|
||||||
data, err := os.ReadFile(gitignoreFile)
|
|
||||||
if err != nil {
|
|
||||||
log.Println(err.Error())
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, line := range strings.Split(string(data), "\n") {
|
|
||||||
if strings.Trim(line, " ") == "gen" {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
data = append(data, []byte("\ngen\n")...)
|
|
||||||
|
|
||||||
err = os.WriteFile(gitignoreFile, data, 0644)
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@ -9,5 +9,5 @@ func TestMain(t *testing.T) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func TestGateway(t *testing.T) {
|
func TestGateway(t *testing.T) {
|
||||||
GenClientMain()
|
GatewayMain()
|
||||||
}
|
}
|
||||||
|
|||||||
10
goutils/proto_build/tpls/auto_grpc_gateway_nacos.tpl
Normal file
10
goutils/proto_build/tpls/auto_grpc_gateway_nacos.tpl
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
package service
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"net/http"
|
||||||
|
|
||||||
|
"github.com/grpc-ecosystem/grpc-gateway/v2/runtime"
|
||||||
|
"google.golang.org/grpc"
|
||||||
|
)
|
||||||
|
|
||||||
20
goutils/proto_build/tpls/auto_grpc_gateway_register.tpl
Normal file
20
goutils/proto_build/tpls/auto_grpc_gateway_register.tpl
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
package logic
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"{{.ProjectName}}/gen/go/service"
|
||||||
|
|
||||||
|
"github.com/grpc-ecosystem/grpc-gateway/v2/runtime"
|
||||||
|
"google.golang.org/grpc"
|
||||||
|
)
|
||||||
|
|
||||||
|
func AutoRegisterHandler(ctx context.Context, mux *runtime.ServeMux, opts ...grpc.DialOption) error {
|
||||||
|
var err error
|
||||||
|
{{range .FuncNames}}
|
||||||
|
err = service.{{.}}(ctx, mux, opts...)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
{{end}}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
@ -4,7 +4,6 @@ import (
|
|||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"reflect"
|
"reflect"
|
||||||
"fusen-basic/env"
|
|
||||||
|
|
||||||
"github.com/nacos-group/nacos-sdk-go/v2/clients/naming_client"
|
"github.com/nacos-group/nacos-sdk-go/v2/clients/naming_client"
|
||||||
"github.com/nacos-group/nacos-sdk-go/v2/vo"
|
"github.com/nacos-group/nacos-sdk-go/v2/vo"
|
||||||
@ -15,10 +14,6 @@ import (
|
|||||||
var namingClient naming_client.INamingClient
|
var namingClient naming_client.INamingClient
|
||||||
var groupName string
|
var groupName string
|
||||||
|
|
||||||
func init() {
|
|
||||||
AutoGrpcInit(env.StartAutoGrpc())
|
|
||||||
}
|
|
||||||
|
|
||||||
// AutoGrpcInit auto grpc 必须调用初始化
|
// AutoGrpcInit auto grpc 必须调用初始化
|
||||||
func AutoGrpcInit(obj any) {
|
func AutoGrpcInit(obj any) {
|
||||||
value := reflect.ValueOf(obj)
|
value := reflect.ValueOf(obj)
|
||||||
@ -54,13 +49,11 @@ func Auto{{.ClientName}}Client(ctx context.Context) {{.ClientName}}Client {
|
|||||||
GroupName: groupName,
|
GroupName: groupName,
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := 0; i < 10; i++ {
|
|
||||||
insService, err := namingClient.SelectOneHealthyInstance(sel)
|
insService, err := namingClient.SelectOneHealthyInstance(sel)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Println(err)
|
log.Println(err)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
if insService.Enable && insService.Healthy {
|
|
||||||
|
|
||||||
conn, err := grpc.DialContext(ctx, fmt.Sprintf("%s:%d", insService.Ip, insService.Port), grpc.WithTransportCredentials(insecure.NewCredentials()))
|
conn, err := grpc.DialContext(ctx, fmt.Sprintf("%s:%d", insService.Ip, insService.Port), grpc.WithTransportCredentials(insecure.NewCredentials()))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -68,9 +61,6 @@ func Auto{{.ClientName}}Client(ctx context.Context) {{.ClientName}}Client {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
return New{{.ClientName}}Client(conn)
|
return New{{.ClientName}}Client(conn)
|
||||||
}
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -85,21 +75,16 @@ func Auto{{.ClientName}}ClientEx(ctx context.Context, opts ...grpc.DialOption) (
|
|||||||
GroupName: groupName,
|
GroupName: groupName,
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := 0; i < 10; i++ {
|
|
||||||
insService, err := namingClient.SelectOneHealthyInstance(sel)
|
insService, err := namingClient.SelectOneHealthyInstance(sel)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if insService.Enable && insService.Healthy {
|
|
||||||
conn, err := grpc.DialContext(ctx, fmt.Sprintf("%s:%d", insService.Ip, insService.Port), opts...)
|
conn, err := grpc.DialContext(ctx, fmt.Sprintf("%s:%d", insService.Ip, insService.Port), opts...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
return New{{.ClientName}}Client(conn), nil
|
return New{{.ClientName}}Client(conn), nil
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil, fmt.Errorf("no healthy with times 10")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
{{end}}
|
{{end}}
|
||||||
@ -11,6 +11,14 @@ func init() {
|
|||||||
{{.RequestVar}} = &service.{{.RequestStruct}}{}
|
{{.RequestVar}} = &service.{{.RequestStruct}}{}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func Test{{.MethodName}}HTTP(t *testing.T) {
|
||||||
|
// 构建请求体
|
||||||
|
resp, err := {{.MethodName}}Http(nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Error(err)
|
||||||
|
}
|
||||||
|
log.Println(resp)
|
||||||
|
}
|
||||||
|
|
||||||
func Test{{.MethodName}}RPC(t *testing.T) {
|
func Test{{.MethodName}}RPC(t *testing.T) {
|
||||||
resp, err := {{.MethodName}}RPC()
|
resp, err := {{.MethodName}}RPC()
|
||||||
|
|||||||
@ -2,19 +2,31 @@ package test
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"net/http"
|
||||||
"{{.ProjectName}}/gen/go/service"
|
"{{.ProjectName}}/gen/go/service"
|
||||||
"{{.ProjectName}}/server/config"
|
"{{.ProjectName}}/server/config"
|
||||||
"fusen-basic/env"
|
"fusen-basic/env"
|
||||||
)
|
)
|
||||||
|
|
||||||
{{range .GrpcTestStructs}}
|
{{range .HttpGrpcTestStructs}}
|
||||||
|
|
||||||
var {{.RequestVar}} *service.{{.RequestStruct}}
|
var {{.RequestVar}} *service.{{.RequestStruct}}
|
||||||
|
|
||||||
|
|
||||||
|
func {{.MethodName}}Http(reqHandler func(*http.Request) error) (any, error) {
|
||||||
|
resp, err := HttpRequest({{.HttpMethod}}, gatewayAddrress+{{.UrlPath}}, {{.RequestVar}}, reqHandler)
|
||||||
|
if err != nil {
|
||||||
|
// t.Error(err)
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return resp, nil
|
||||||
|
}
|
||||||
|
|
||||||
func {{.MethodName}}RPC() (any, error) {
|
func {{.MethodName}}RPC() (any, error) {
|
||||||
if fusen == nil {
|
if fusen == nil {
|
||||||
fusen := env.NewFusenTest[config.Config]()
|
fusen := env.NewFusenTest[config.Config]()
|
||||||
fusen.StartNacos(nil)
|
fusen.StartNacos(nil)
|
||||||
|
service.AutoGrpcInit(fusen)
|
||||||
}
|
}
|
||||||
|
|
||||||
resp, err := service.Auto{{.ServiceName}}Client(context.TODO()).{{.MethodName}}(context.TODO(), {{.RequestVar}})
|
resp, err := service.Auto{{.ServiceName}}Client(context.TODO()).{{.MethodName}}(context.TODO(), {{.RequestVar}})
|
||||||
|
|||||||
@ -1,9 +1,103 @@
|
|||||||
package test
|
package test
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
"{{.ProjectName}}/server/config"
|
"{{.ProjectName}}/server/config"
|
||||||
"fusen-basic/env"
|
"fusen-basic/env"
|
||||||
|
"fusen-basic/utils/log"
|
||||||
|
"net/http"
|
||||||
|
"net/url"
|
||||||
|
"reflect"
|
||||||
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
var fusen *env.Fusen[config.Config]
|
var fusen *env.Fusen[config.Config]
|
||||||
var gatewayAddrress = "http://localhost:9900"
|
var gatewayAddrress = "http://localhost:9900"
|
||||||
|
|
||||||
|
|
||||||
|
func HttpRequest(method, urlStr string, body interface{}, reqHandler func(*http.Request) error) (map[string]interface{}, error) {
|
||||||
|
var jsonBody *bytes.Buffer
|
||||||
|
var queryParams url.Values
|
||||||
|
if method == "GET" {
|
||||||
|
queryParams = JsonTagToURLValues(body)
|
||||||
|
jsonBody = bytes.NewBuffer(nil)
|
||||||
|
} else {
|
||||||
|
// 将请求体转换为JSON格式
|
||||||
|
jsonData, err := json.Marshal(body)
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("Failed to marshal request body: %s\n", err.Error())
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
jsonBody = bytes.NewBuffer(jsonData)
|
||||||
|
log.Println(string(jsonData))
|
||||||
|
}
|
||||||
|
|
||||||
|
// 创建URL对象并添加查询参数
|
||||||
|
u, err := url.Parse(urlStr)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("Failed to parse URL: %s\n", err.Error())
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
u.RawQuery = queryParams.Encode()
|
||||||
|
// 创建HTTP请求
|
||||||
|
req, err := http.NewRequest(method, u.String(), jsonBody)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("Failed to create HTTP request: %s\n", err.Error())
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// 设置请求头
|
||||||
|
req.Header.Set("Content-Type", "application/json")
|
||||||
|
|
||||||
|
if reqHandler != nil {
|
||||||
|
reqHandler(req)
|
||||||
|
}
|
||||||
|
|
||||||
|
// 发送HTTP请求
|
||||||
|
client := http.DefaultClient
|
||||||
|
client.Timeout = time.Second * 60
|
||||||
|
resp, err := client.Do(req)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("HTTP request failed: %s\n", err.Error())
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if resp.StatusCode != 200 {
|
||||||
|
return nil, fmt.Errorf("%s", resp.Status)
|
||||||
|
}
|
||||||
|
|
||||||
|
defer resp.Body.Close()
|
||||||
|
|
||||||
|
// 解析响应体
|
||||||
|
var response map[string]interface{}
|
||||||
|
err = json.NewDecoder(resp.Body).Decode(&response)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("Failed to decode response body: %s\n", err.Error())
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return response, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func JsonTagToURLValues(body interface{}) url.Values {
|
||||||
|
values := url.Values{}
|
||||||
|
|
||||||
|
v := reflect.ValueOf(body)
|
||||||
|
if v.Kind() == reflect.Ptr {
|
||||||
|
v = v.Elem()
|
||||||
|
}
|
||||||
|
t := v.Type()
|
||||||
|
|
||||||
|
for i := 0; i < t.NumField(); i++ {
|
||||||
|
field := t.Field(i)
|
||||||
|
if field.IsExported() {
|
||||||
|
if jsonTag, ok := field.Tag.Lookup("json"); ok {
|
||||||
|
jtag := strings.Split(jsonTag, ",")[0]
|
||||||
|
value := v.Field(i).String()
|
||||||
|
values.Set(jtag, value)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return values
|
||||||
|
}
|
||||||
@ -1,24 +1,16 @@
|
|||||||
package {{.PackageName}}
|
package {{.PackageName}}
|
||||||
|
|
||||||
import (
|
import (
|
||||||
{{if eq .MethodType "rpc"}}
|
"fusen-basic/basic"
|
||||||
"context"
|
|
||||||
{{end}}
|
|
||||||
"{{.ProjectName}}/gen/go/service"
|
"{{.ProjectName}}/gen/go/service"
|
||||||
)
|
)
|
||||||
|
|
||||||
{{if eq .MethodType "rpc"}}
|
func (l *{{.StructName}}) {{.MethodName}}Logic(req {{.ParamReq}}, userinfo *basic.UserInfo) (resp *basic.Response[{{.MethodResponse}}]) {
|
||||||
|
return resp.Set(basic.CodeOK)
|
||||||
func (l *{{.StructName}}) {{.MethodName}}Logic({{range $index, $param := .Params}}{{if $index}}, {{end}}{{$param}}{{end}}) (resp {{.MethodReturn}},err error) {
|
|
||||||
resp = &{{.MethodResponse}}{}
|
|
||||||
return resp, nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
{{else if eq .MethodType "stream"}}
|
|
||||||
|
|
||||||
func (l *{{.StructName}}) {{.MethodName}}Logic(stream {{range $index, $param := .Params}}{{if $index}}, {{end}}{{$param}}{{end}}) (err error) {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
{{end}}
|
|
||||||
|
|
||||||
|
// 自定义验证校验方法 VaildUserInfoHandler
|
||||||
|
// func (h *{{.MethodName}}Handler) VaildUserInfoHandler(ctx context.Context) *basic.UserInfo {
|
||||||
|
// return basic.ValidUserInfo(ctx)
|
||||||
|
// }
|
||||||
|
|||||||
@ -3,13 +3,17 @@ package {{.PackageName}}
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
"fmt"
|
|
||||||
|
|
||||||
|
"fusen-basic/basic"
|
||||||
"fusen-basic/env"
|
"fusen-basic/env"
|
||||||
|
"fusen-basic/utils/log"
|
||||||
|
|
||||||
"{{.ProjectName}}/gen/go/service"
|
"{{.ProjectName}}/gen/go/service"
|
||||||
"{{.ProjectName}}/server/config"
|
"{{.ProjectName}}/server/config"
|
||||||
|
|
||||||
|
"google.golang.org/grpc/metadata"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@ -46,30 +50,77 @@ type {{.MethodName}}Handler struct {
|
|||||||
|
|
||||||
type {{.MethodName}}HandlerMust struct{}
|
type {{.MethodName}}HandlerMust struct{}
|
||||||
|
|
||||||
{{if eq .MethodType "rpc"}}
|
func (must *{{.MethodName}}HandlerMust) ValidUserInfoHandler(ctx context.Context) *basic.UserInfo {
|
||||||
|
return defaultValidUserInfoHandler(ctx)
|
||||||
func (lgrpc *{{.StructName}}Grpc) {{.MethodName}}({{range $index, $param := .Params}}{{if $index}}, {{end}}{{$param}}{{end}}) (_resp {{.MethodReturn}},_err error) {
|
|
||||||
defer func() {
|
|
||||||
if _recoverErr := recover(); _recoverErr != nil {
|
|
||||||
_resp = nil
|
|
||||||
_err = fmt.Errorf("%v", _recoverErr)
|
|
||||||
}
|
|
||||||
}()
|
|
||||||
return New{{.StructName}}(ctx).{{.MethodName}}Logic({{range $index, $param := .ParamsName}}{{if $index}}, {{end}}{{$param}}{{end}})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
{{else if eq .MethodType "stream"}}
|
var __hide_handler{{.MethodName}} *{{.MethodName}}Handler = &{{.MethodName}}Handler{}
|
||||||
|
|
||||||
func (lgrpc *{{.StructName}}Grpc) {{.MethodName}}(stream {{range $index, $param := .Params}}{{if $index}}, {{end}}{{$param}}{{end}}) (_err error) {
|
func (lgrpc *{{.StructName}}Grpc) {{.MethodName}}(ctx {{.ParamCtx}}, req {{.ParamReq}}) ({{.MethodReturn}}, error) {
|
||||||
defer func() {
|
return New{{.StructName}}(ctx).{{.MethodName}}Logic(req, __hide_handler{{.MethodName}}.ValidUserInfoHandler(ctx)).PassMetaResponse(ctx)
|
||||||
if _recoverErr := recover(); _recoverErr != nil {
|
|
||||||
_err = fmt.Errorf("%v", _recoverErr)
|
|
||||||
}
|
|
||||||
}()
|
|
||||||
return New{{.StructName}}(stream.Context()).{{.MethodName}}Logic(stream)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
{{end}}
|
{{end}}
|
||||||
|
|
||||||
{{end}}
|
func DefaultValidToken(ctx context.Context) *basic.UserInfo {
|
||||||
|
var (
|
||||||
|
err error
|
||||||
|
ui = &basic.UserInfo{}
|
||||||
|
)
|
||||||
|
// log.Println(ctx)
|
||||||
|
if md, ok := metadata.FromIncomingContext(ctx); ok {
|
||||||
|
var authtoken, debugtoken *string
|
||||||
|
var vresult *service.ValidTokenResponse
|
||||||
|
if a, ok := md["authorization"]; ok {
|
||||||
|
token := a[0]
|
||||||
|
if len(token) > 15 {
|
||||||
|
if strings.HasPrefix(token[1:], "earer ") {
|
||||||
|
token = token[7:]
|
||||||
|
}
|
||||||
|
authtoken = &token
|
||||||
|
|
||||||
|
defer func() {
|
||||||
|
if vresult != nil {
|
||||||
|
userinfo := vresult.UserInfo.AsMap()
|
||||||
|
ui.UserId = int64(userinfo["user_id"].(float64))
|
||||||
|
ui.GuestId = int64(userinfo["guest_id"].(float64))
|
||||||
|
ui.Exp = int64(userinfo["exp"].(float64))
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if a, ok := md["debug-token"]; ok {
|
||||||
|
token := a[0]
|
||||||
|
if len(token) > 15 {
|
||||||
|
if strings.HasPrefix(token[1:], "earer ") {
|
||||||
|
token = token[7:]
|
||||||
|
}
|
||||||
|
debugtoken = &token
|
||||||
|
|
||||||
|
defer func() {
|
||||||
|
if vresult != nil {
|
||||||
|
debug := vresult.DebugInfo.AsMap()
|
||||||
|
ui.Debug = &basic.Debug{}
|
||||||
|
if dexp, ok := debug["exp"]; ok {
|
||||||
|
dexpint64 := int64(dexp.(float64))
|
||||||
|
ui.Debug.Exp = &dexpint64
|
||||||
|
}
|
||||||
|
ui.Debug.IsAllTemplateTag = int64(debug["is_all_template_tag"].(float64))
|
||||||
|
ui.Debug.IsCache = int64(debug["is_cache"].(float64))
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vresult, err = service.AutoAuthClient(ctx).ValidToken(context.TODO(), &service.ValidTokenRequest{
|
||||||
|
UserToken: authtoken,
|
||||||
|
DebugToken: debugtoken,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
log.Println(err.Error())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ui
|
||||||
|
}
|
||||||
@ -3,12 +3,16 @@ package {{.PackageName}}
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"fusen-basic/dbutils"
|
"fusen-basic/basic"
|
||||||
"fusen-basic/gmodel"
|
"fusen-model/dbutils"
|
||||||
|
"fusen-model/gmodel"
|
||||||
|
|
||||||
"{{.ProjectName}}/server/config"
|
"{{.ProjectName}}/server/config"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// 统一的验证入口
|
||||||
|
var defaultValidUserInfoHandler func(context.Context) *basic.UserInfo = DefaultValidToken
|
||||||
|
|
||||||
// 处理共享数据的上下文
|
// 处理共享数据的上下文
|
||||||
type SharedContext struct {
|
type SharedContext struct {
|
||||||
models *gmodel.Models
|
models *gmodel.Models
|
||||||
|
|||||||
@ -6,15 +6,22 @@ import (
|
|||||||
"fusen-basic/env"
|
"fusen-basic/env"
|
||||||
"fusen-basic/utils/log"
|
"fusen-basic/utils/log"
|
||||||
|
|
||||||
|
"{{.ProjectName}}/gen/go/service"
|
||||||
|
|
||||||
"{{.ProjectName}}/server/config"
|
"{{.ProjectName}}/server/config"
|
||||||
|
|
||||||
|
{{range .LogicDirNames}}
|
||||||
|
"{{$.ProjectName}}/{{.}}"
|
||||||
|
{{- end}}
|
||||||
|
|
||||||
"google.golang.org/grpc"
|
"google.golang.org/grpc"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
|
|
||||||
fusen := env.NewFusen[config.Config]()
|
fusen := env.NewFusen[config.Config]()
|
||||||
fusen.StartNacosGRPC(nil)
|
fusen.StartNacos(nil)
|
||||||
|
service.AutoGrpcInit(fusen)
|
||||||
|
|
||||||
sopt := grpc.UnaryInterceptor(fusen.Interceptor())
|
sopt := grpc.UnaryInterceptor(fusen.Interceptor())
|
||||||
|
|
||||||
@ -23,8 +30,9 @@ func main() {
|
|||||||
log.Fatalf("failed to listen: %v", err)
|
log.Fatalf("failed to listen: %v", err)
|
||||||
}
|
}
|
||||||
s := grpc.NewServer(sopt) //新建一个grpc服务
|
s := grpc.NewServer(sopt) //新建一个grpc服务
|
||||||
|
{{range .StructServiceNames}}
|
||||||
MainRegisterServer(s) // 注册所有的service
|
service.Register{{.StructServiceName}}Server(s, &{{.LogicPackageName}}.{{.StructServiceName}}LogicGrpc{}) // {{.LogicPackageName}} 服务注册
|
||||||
|
{{- end}}
|
||||||
|
|
||||||
if err := s.Serve(lis); err != nil {
|
if err := s.Serve(lis); err != nil {
|
||||||
log.Fatalf("failed to serve: %v", err)
|
log.Fatalf("failed to serve: %v", err)
|
||||||
|
|||||||
@ -1,21 +0,0 @@
|
|||||||
package main
|
|
||||||
|
|
||||||
import (
|
|
||||||
"{{.ProjectName}}/gen/go/service"
|
|
||||||
{{range .StructServiceNames}}
|
|
||||||
"{{$.ProjectName}}/server/logics/{{.LogicPackageName}}"
|
|
||||||
{{- end}}
|
|
||||||
|
|
||||||
"time"
|
|
||||||
"google.golang.org/grpc"
|
|
||||||
)
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
time.Local = time.UTC
|
|
||||||
}
|
|
||||||
|
|
||||||
func MainRegisterServer(s *grpc.Server) {
|
|
||||||
{{range .StructServiceNames}}
|
|
||||||
service.Register{{.StructServiceName}}Server(s, &{{.LogicPackageName}}.{{.StructServiceName}}LogicGrpc{}) // {{.LogicPackageName}} 服务注册
|
|
||||||
{{- end}}
|
|
||||||
}
|
|
||||||
@ -27,15 +27,8 @@ echo "service name: $service_name"
|
|||||||
cd $script_dir/proto
|
cd $script_dir/proto
|
||||||
git pull origin master
|
git pull origin master
|
||||||
cd $script_dir
|
cd $script_dir
|
||||||
|
|
||||||
go mod tidy
|
|
||||||
go mod vendor
|
|
||||||
|
|
||||||
go run -gcflags="-N" proto/goutils/proto_build/main.go
|
go run -gcflags="-N" proto/goutils/proto_build/main.go
|
||||||
|
|
||||||
go mod tidy
|
|
||||||
go mod vendor
|
|
||||||
|
|
||||||
run_server() {
|
run_server() {
|
||||||
# 导航到相应的目录
|
# 导航到相应的目录
|
||||||
cd $script_dir/server
|
cd $script_dir/server
|
||||||
|
|||||||
@ -9,9 +9,9 @@ package goutils
|
|||||||
// google.golang.org/protobuf/cmd/protoc-gen-go \
|
// google.golang.org/protobuf/cmd/protoc-gen-go \
|
||||||
// google.golang.org/grpc/cmd/protoc-gen-go-grpc
|
// google.golang.org/grpc/cmd/protoc-gen-go-grpc
|
||||||
|
|
||||||
// import (
|
import (
|
||||||
// _ "github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-grpc-gateway"
|
_ "github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-grpc-gateway"
|
||||||
// _ "github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-openapiv2"
|
_ "github.com/grpc-ecosystem/grpc-gateway/v2/protoc-gen-openapiv2"
|
||||||
// _ "google.golang.org/grpc/cmd/protoc-gen-go-grpc"
|
_ "google.golang.org/grpc/cmd/protoc-gen-go-grpc"
|
||||||
// _ "google.golang.org/protobuf/cmd/protoc-gen-go"
|
_ "google.golang.org/protobuf/cmd/protoc-gen-go"
|
||||||
// )
|
)
|
||||||
|
|||||||
@ -1,37 +1,124 @@
|
|||||||
syntax = "proto3"; //版本声明,使用v3版本
|
syntax = "proto3"; //版本声明,使用v3版本
|
||||||
|
|
||||||
package auth;
|
package auth;
|
||||||
option go_package = "gitlab.fusenpack.com/backend/auth;service";
|
option go_package = "gitee.com/fusenpack/fusen-auth;service";
|
||||||
|
|
||||||
// 导入google/api/annotations.proto 注释依赖
|
// 导入google/api/annotations.proto 注释依赖
|
||||||
|
import "google/api/annotations.proto";
|
||||||
import "service/basic.proto";
|
import "service/basic.proto";
|
||||||
|
import "google/protobuf/struct.proto";
|
||||||
|
import "google/protobuf/any.proto";
|
||||||
|
|
||||||
|
|
||||||
//定义服务
|
//定义服务
|
||||||
service auth {
|
service auth {
|
||||||
|
|
||||||
// 登录接口
|
// 登录接口
|
||||||
rpc ValidToken(ValidTokenRequest) returns (ValidTokenResponse) {}
|
rpc ValidToken(ValidTokenRequest) returns (ValidTokenResponse) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/valid/token"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 登录接口
|
||||||
|
rpc Login(UserLoginRequest) returns (UserLoginResponse) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/login"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 注册接口
|
||||||
|
rpc Register(UserRegisterRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/register"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
// Cookie 接受接口
|
// Cookie 接受接口
|
||||||
rpc CreateAcceptCookie(basic.Request) returns (GuestResponse) {}
|
rpc AcceptCookie(basic.Request) returns (GuestResponse) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/accept-cookie"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
// 调试令牌创建接口
|
// 调试令牌创建接口
|
||||||
rpc CreateDebugToken(UserDebugRequest) returns (DebugTokenResponse) {}
|
rpc CreateDebugToken(UserDebugRequest) returns (DebugTokenResponse) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/debug/token/create"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
}
|
// Google 登录接口
|
||||||
|
rpc GoogleLogin(GoogleLoginRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP GET 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
get: "/api/auth/oauth2/login/google"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
message Debug {
|
// 邮箱确认接口
|
||||||
int64 exp = 1;
|
rpc EmailConfirmation(EmailConfirmationRequest) returns (basic.Response) {
|
||||||
int64 is_cache = 2;
|
// 添加 HTTP GET 网关注解
|
||||||
int64 is_all_template_tag = 3;
|
option (google.api.http) = {
|
||||||
}
|
post: "/api/auth/email/confirmation"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 使用邮箱注册接口
|
||||||
|
rpc EmailRegister(EmailRegisterRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/oauth2/register"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 发送重置令牌到邮箱接口
|
||||||
|
rpc ResetToken(UserResetTokenRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/reset/token"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 重置密码接口
|
||||||
|
rpc ResetPassword(UserResetPasswordRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/reset/password"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取重定向到 HTML 页面接口
|
||||||
|
rpc ResetPasswordHtml(UserResetHtmlRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP GET 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
get: "/api/auth/reset/password/html"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// 调试删除帐号接口
|
||||||
|
rpc DebugDelete(AuthDeleteRequest) returns (basic.Response) {
|
||||||
|
// 添加 HTTP POST 网关注解
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/auth/debug/delete"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
message UserInfo {
|
|
||||||
int64 user_id = 1;
|
|
||||||
int64 guest_id = 2;
|
|
||||||
int64 exp = 3;
|
|
||||||
Debug debug = 4;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 验证token的请求
|
// 验证token的请求
|
||||||
@ -43,7 +130,8 @@ message ValidTokenRequest {
|
|||||||
|
|
||||||
// 验证token的请求
|
// 验证token的请求
|
||||||
message ValidTokenResponse {
|
message ValidTokenResponse {
|
||||||
UserInfo user_info = 1;
|
google.protobuf.Struct user_info = 1;
|
||||||
|
google.protobuf.Struct debug_info = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -3,6 +3,7 @@ syntax = "proto3"; //版本声明,使用v3版本
|
|||||||
package basic;
|
package basic;
|
||||||
|
|
||||||
option go_package = ".;service";
|
option go_package = ".;service";
|
||||||
|
import "google/protobuf/any.proto";
|
||||||
import "google/protobuf/struct.proto";
|
import "google/protobuf/struct.proto";
|
||||||
|
|
||||||
// 定义请求消息类型.
|
// 定义请求消息类型.
|
||||||
@ -16,23 +17,4 @@ message Response {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
message ResourceInfo{
|
|
||||||
string resource_id = 1;
|
|
||||||
int64 guest_id =2;
|
|
||||||
int64 user_id =3;
|
|
||||||
string resource_type = 4;
|
|
||||||
string resource_url = 5;
|
|
||||||
string version = 6;
|
|
||||||
int64 api_type = 7;
|
|
||||||
string bucket_name = 8;
|
|
||||||
string source = 9;
|
|
||||||
string uploaded_at = 10;
|
|
||||||
google.protobuf.Struct metadata = 11;
|
|
||||||
}
|
|
||||||
|
|
||||||
message Meta {
|
|
||||||
int64 total_count =1;
|
|
||||||
int64 page_count=2;
|
|
||||||
int64 current_page=3;
|
|
||||||
int64 per_page=4;
|
|
||||||
}
|
|
||||||
@ -9,6 +9,15 @@ import "service/basic.proto";
|
|||||||
import "google/protobuf/struct.proto";
|
import "google/protobuf/struct.proto";
|
||||||
import "google/protobuf/any.proto";
|
import "google/protobuf/any.proto";
|
||||||
|
|
||||||
|
//定义服务
|
||||||
|
service notify {
|
||||||
|
rpc Hello(basic.Request) returns (basic.Response) {
|
||||||
|
option (google.api.http) = {
|
||||||
|
post: "/api/notify/hello"
|
||||||
|
body: "*"
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//定义服务
|
//定义服务
|
||||||
service info {
|
service info {
|
||||||
@ -212,3 +221,5 @@ message ContactUsRequest {
|
|||||||
string phone = 3; // 电话号码
|
string phone = 3; // 电话号码
|
||||||
string message = 4; // 消息内容
|
string message = 4; // 消息内容
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1,305 +0,0 @@
|
|||||||
syntax = "proto3"; //版本声明,使用v3版本
|
|
||||||
|
|
||||||
package ldap;
|
|
||||||
option go_package = "gitlab.fusenpack.com/backend/ldap;service";
|
|
||||||
|
|
||||||
// 导入google/api/annotations.proto 注释依赖
|
|
||||||
import "service/basic.proto";
|
|
||||||
|
|
||||||
//定义服务
|
|
||||||
service ldap {
|
|
||||||
// 心跳
|
|
||||||
rpc Ping(basic.Request) returns (basic.Response) {}
|
|
||||||
//获取ldap部门列表
|
|
||||||
rpc GetLdapOrganizations(basic.Request) returns(GetLdapOrganizationsRsp){}
|
|
||||||
//添加ldap部门
|
|
||||||
rpc CreateLdapOrganization(CreateLdapOrganizationReq)returns(basic.Response){}
|
|
||||||
//删除ldap部门
|
|
||||||
rpc DeleteLdapOrganization(DeleteLdapOrganizationReq) returns(basic.Response){}
|
|
||||||
//修改ldap部门
|
|
||||||
rpc UpdateLdapOrganization(UpdateLdapOrganizationReq) returns(basic.Response){}
|
|
||||||
//添加ldap用户帐号
|
|
||||||
rpc CreateLdapUser(CreateLdapUserReq) returns(basic.Response){}
|
|
||||||
//修改ldap用户信息
|
|
||||||
rpc UpdateLdapUser(UpdateLdapUserReq) returns(basic.Response){}
|
|
||||||
//修改ldap用户密码
|
|
||||||
rpc UpdateLdapUserPwd(UpdateLdapUserPwdReq) returns(basic.Response){}
|
|
||||||
//禁用ldap用户帐号
|
|
||||||
rpc DisableLdapUser(DisableLdapUserReq) returns(basic.Response){}
|
|
||||||
//获取用户信息
|
|
||||||
rpc GetLdapUserInfo(GetLdapUserInfoReq) returns(GetLdapUserInfoRsp){}
|
|
||||||
//ldap部门添加成员
|
|
||||||
rpc AddLdapOrganizationMember(AddLdapOrganizationMemberReq) returns(basic.Response){}
|
|
||||||
//ldap部门移除成员
|
|
||||||
rpc RemoveLdapOrganizationMember(RemoveLdapOrganizationMemberReq) returns(basic.Response){}
|
|
||||||
//获取ldap组织成员列表
|
|
||||||
rpc GetLdapOrganizationMembers(GetLdapOrganizationMembersReq) returns(GetLdapOrganizationMembersRsp){}
|
|
||||||
//创建用户基础组
|
|
||||||
rpc CreateLdapUserBaseGroup(basic.Request) returns (basic.Response) {}
|
|
||||||
//获取基础用户组中成员列表
|
|
||||||
rpc GetLdapUsers(GetLdapUsersReq) returns (GetLdapUsersRsp) {}
|
|
||||||
//登录
|
|
||||||
rpc LdapUserLogin(LdapUserLoginReq) returns (LdapUserLoginRsp) {}
|
|
||||||
//解析token
|
|
||||||
rpc LdapParseToken(LdapParseTokenReq) returns (LdapParseTokenRsp) {}
|
|
||||||
|
|
||||||
//获取权限组列表
|
|
||||||
rpc GetLdapGroups(GetLdapGroupsReq) returns (GetLdapGroupsRsp);
|
|
||||||
//获取权限组详情
|
|
||||||
rpc GetLdapGroupDetail(GetLdapGroupDetailReq) returns (GetLdapGroupDetailRsp);
|
|
||||||
//保存权限组
|
|
||||||
rpc SaveLdapGroup(SaveLdapGroupReq) returns (SaveLdapGroupRsp);
|
|
||||||
//删除权限组
|
|
||||||
rpc DeleteLdapGroup(DeleteLdapGroupReq) returns (DeleteLdapGroupRsp);
|
|
||||||
//权限组授权--新增
|
|
||||||
rpc SetLdapGroupAuth(SetLdapGroupAuthReq) returns (SetLdapGroupAuthRsp);
|
|
||||||
//权限组授权--移除
|
|
||||||
rpc RemoveLdapGroupAuth(RemoveLdapGroupAuthReq) returns (RemoveLdapGroupAuthRsp);
|
|
||||||
}
|
|
||||||
message GetLdapGroupsReq {
|
|
||||||
LdapGroupFilter filter = 1;
|
|
||||||
|
|
||||||
int64 current_page = 101;
|
|
||||||
int64 per_page = 102;
|
|
||||||
string order_by = 103;
|
|
||||||
}
|
|
||||||
message GetLdapGroupsRsp {
|
|
||||||
repeated LdapGroup list = 1;
|
|
||||||
basic.Meta meta = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetLdapGroupDetailReq {
|
|
||||||
LdapGroupFilter filter = 1;
|
|
||||||
}
|
|
||||||
message GetLdapGroupDetailRsp {
|
|
||||||
LdapGroup info = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message SaveLdapGroupReq {
|
|
||||||
LdapGroupFilter filter = 1;
|
|
||||||
LdapGroupFilter save = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message SaveLdapGroupRsp {
|
|
||||||
LdapGroup info = 1;
|
|
||||||
}
|
|
||||||
message DeleteLdapGroupReq {
|
|
||||||
LdapGroupFilter filter = 1;
|
|
||||||
}
|
|
||||||
message DeleteLdapGroupRsp {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
message SetLdapGroupAuthReq {
|
|
||||||
int64 group_id = 1;
|
|
||||||
GroupAuth group_auth = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message SetLdapGroupAuthRsp {
|
|
||||||
int64 group_id = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message RemoveLdapGroupAuthReq {
|
|
||||||
int64 group_id = 1;
|
|
||||||
GroupAuth group_auth = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message RemoveLdapGroupAuthRsp {
|
|
||||||
int64 group_id = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GroupAuth {
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
string type = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message LdapGroup {
|
|
||||||
int64 id = 1;
|
|
||||||
string type = 2;
|
|
||||||
string name = 3;
|
|
||||||
string keyword = 4;
|
|
||||||
string remark = 5;
|
|
||||||
int64 status = 6;
|
|
||||||
int64 sort = 7;
|
|
||||||
|
|
||||||
bytes metadata = 101;
|
|
||||||
string ctime = 102;
|
|
||||||
string utime = 103;
|
|
||||||
}
|
|
||||||
|
|
||||||
message LdapGroupFilter {
|
|
||||||
optional int64 id = 1;
|
|
||||||
optional string type = 2;
|
|
||||||
optional string name = 3;
|
|
||||||
optional string keyword = 4;
|
|
||||||
optional string remark = 5;
|
|
||||||
optional int64 status = 6;
|
|
||||||
optional int64 sort = 7;
|
|
||||||
|
|
||||||
optional bytes other_filter = 101; // 其他过滤条件
|
|
||||||
repeated int64 ldap_grouop_ids = 102; // 资源ID列表
|
|
||||||
optional bytes metadata = 103;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//获取ldap部门列表
|
|
||||||
message GetLdapOrganizationsRsp{
|
|
||||||
repeated LdapOrganization list = 1;
|
|
||||||
}
|
|
||||||
message LdapOrganization {
|
|
||||||
int32 member_count = 1; //成员数
|
|
||||||
string organization_name = 2; //部分名字
|
|
||||||
string organization_dn = 3; //部门dn
|
|
||||||
string owner_name = 4; //负责人名字
|
|
||||||
string owner_dn = 5; //负责人dn
|
|
||||||
int32 level = 6; //层级
|
|
||||||
string parent_organization_dn = 7;//父级部门dn
|
|
||||||
int32 sort = 8; //序号
|
|
||||||
repeated LdapOrganization child = 9;//子部门
|
|
||||||
}
|
|
||||||
//添加ldap部门
|
|
||||||
message CreateLdapOrganizationReq{
|
|
||||||
string organization_name = 1; //部门名
|
|
||||||
string parent_organization_dn = 2; //父级部门dn
|
|
||||||
string owner_dn = 3 ; //负责人dn
|
|
||||||
}
|
|
||||||
//删除ldap部门
|
|
||||||
message DeleteLdapOrganizationReq{
|
|
||||||
repeated string organization_dns = 1;//要删除的部门dn集合
|
|
||||||
}
|
|
||||||
//修改ldap部门
|
|
||||||
message UpdateLdapOrganizationReq{
|
|
||||||
string organization_dn = 1; //组织dn
|
|
||||||
string organization_name = 2; //组织分类名称
|
|
||||||
string organization_owner_dn = 3; //负责人dn
|
|
||||||
}
|
|
||||||
//添加ldap用户帐号
|
|
||||||
message CreateLdapUserReq{
|
|
||||||
string user_name = 1; //用户名
|
|
||||||
string email = 2; //邮箱
|
|
||||||
string password = 3; //密码
|
|
||||||
string mobile = 4; //手机号
|
|
||||||
string avatar = 5; //头像地址
|
|
||||||
int64 employee_type = 6; //1正式 2实习 3外包
|
|
||||||
int64 group_id = 7; //授权分组id
|
|
||||||
int64 gender = 8; //性别 1男 2女 3未知
|
|
||||||
string birthday = 9; //生日
|
|
||||||
int64 status = 10; //状态 1正常0离职
|
|
||||||
}
|
|
||||||
//修改ldap用户信息
|
|
||||||
message UpdateLdapUserReq{
|
|
||||||
string user_dn = 1; //用户dn
|
|
||||||
string user_name = 2; //用户名
|
|
||||||
string mobile = 3; //手机号
|
|
||||||
string avatar = 4; //头像地址
|
|
||||||
int64 status = 5; //状态 1正常0离职
|
|
||||||
int64 employee_type = 6; //1正式 2实习 3外包
|
|
||||||
int64 group_id = 7; //权限分组id
|
|
||||||
int64 gender = 8; //性别 1男 2女 3未知
|
|
||||||
string birthday = 9; //生日
|
|
||||||
}
|
|
||||||
//修改ldap用户密码
|
|
||||||
message UpdateLdapUserPwdReq{
|
|
||||||
string user_dn = 1; //用户dn
|
|
||||||
string new_password = 2;//新密码
|
|
||||||
string old_password = 3;//旧密码
|
|
||||||
}
|
|
||||||
//禁用ldap用户帐号
|
|
||||||
message DisableLdapUserReq{
|
|
||||||
string user_dn = 1;//用户dn
|
|
||||||
}
|
|
||||||
//获取用户信息
|
|
||||||
message GetLdapUserInfoReq{
|
|
||||||
string user_dn = 1;//用户dn
|
|
||||||
}
|
|
||||||
message GetLdapUserInfoRsp{
|
|
||||||
int64 user_id = 1; //用户id
|
|
||||||
string user_dn = 2; //用户dn
|
|
||||||
string user_name = 3; //用户名
|
|
||||||
string email = 4; //邮箱
|
|
||||||
string mobile = 5; //手机号
|
|
||||||
string avatar = 6; //头像地址
|
|
||||||
int64 employee_type = 7;//雇佣类型 1正式 2实习 3外包
|
|
||||||
int64 gender = 8; //性别 1男 2女 3未知
|
|
||||||
string birthday = 9; //生日
|
|
||||||
repeated string belong_organization = 10;//属于哪些部门
|
|
||||||
repeated string manage_organization = 11; //负责哪些部门
|
|
||||||
int64 status = 12 ; //状态 1正常0离职
|
|
||||||
}
|
|
||||||
//ldap部门添加成员
|
|
||||||
message AddLdapOrganizationMemberReq{
|
|
||||||
string organization_dn = 1 ; //目标组织DN
|
|
||||||
string user_dn = 2; //用户DN
|
|
||||||
}
|
|
||||||
//ldap部门移除成员
|
|
||||||
message RemoveLdapOrganizationMemberReq{
|
|
||||||
string organization_dn = 1; //目标组织DN
|
|
||||||
string user_dn = 2; //用户DN
|
|
||||||
}
|
|
||||||
//获取ldap组织成员列表
|
|
||||||
message GetLdapOrganizationMembersReq{
|
|
||||||
string organization_dn = 1; //组织dn
|
|
||||||
string user_name = 2; //用户名(模糊搜索)
|
|
||||||
}
|
|
||||||
message GetLdapOrganizationMembersRsp {
|
|
||||||
repeated GetLdapOrganizationMembersItem list = 1;
|
|
||||||
}
|
|
||||||
message GetLdapOrganizationMembersItem {
|
|
||||||
int64 userId = 1; //用户id
|
|
||||||
string user_dn = 2 ; //用户dn
|
|
||||||
string user_name = 3 ; //用户名
|
|
||||||
string email = 4 ; //邮箱
|
|
||||||
string mobile = 5; //手机号
|
|
||||||
string avatar = 6; //头像地址
|
|
||||||
int64 employee_type = 7 ; //雇佣类型
|
|
||||||
int64 gender = 8 ; //性别 1男 2女 3未知
|
|
||||||
string birthday = 9 ; //生日
|
|
||||||
repeated string belong_organizations = 10; //属于哪些部门
|
|
||||||
repeated string manage_organizations = 11 ;//管理哪些部门
|
|
||||||
int64 status = 12 ; //状态 1正常0离职
|
|
||||||
int64 group_id = 13; //权限分组id
|
|
||||||
}
|
|
||||||
//获取基础用户组中成员列表
|
|
||||||
message GetLdapUsersReq{
|
|
||||||
string page_cookie = 1; //下一页分页游标,传空/不传就是第一页
|
|
||||||
string user_name = 2 ; //用户名用于模糊搜索
|
|
||||||
int64 gender = 3; //性别 0所有 1男 2女 3未知
|
|
||||||
int64 employee_type = 4;//员工类型0所有 1正式 2实习 3外包
|
|
||||||
}
|
|
||||||
message GetLdapUsersRsp{
|
|
||||||
repeated GetLdapUsersItem list = 1;
|
|
||||||
string paging_cookie = 2;
|
|
||||||
}
|
|
||||||
message GetLdapUsersItem {
|
|
||||||
int64 user_id = 1; //用户id
|
|
||||||
string user_dn = 2; //用户dn
|
|
||||||
string user_name = 3; //用户名
|
|
||||||
string email = 4; //邮箱
|
|
||||||
string mobile = 5; //手机号
|
|
||||||
string avatar = 6; //头像地址
|
|
||||||
int64 employee_type = 7; //雇佣类型 1正式 2实习 3外包
|
|
||||||
int64 gender = 8; //性别 1男 2女 3未知
|
|
||||||
string birthday = 9; //生日
|
|
||||||
repeated string belong_organizations = 10 ;//属于哪些部门
|
|
||||||
repeated string manage_organizations = 11 ;//管理哪些部门
|
|
||||||
int64 status = 12 ; //状态 1正常0离职
|
|
||||||
int64 group_id = 13; //权限分组id
|
|
||||||
}
|
|
||||||
//登录
|
|
||||||
message LdapUserLoginReq{
|
|
||||||
string email = 1; //邮箱
|
|
||||||
string password = 2;//密码
|
|
||||||
}
|
|
||||||
message LdapUserLoginRsp{
|
|
||||||
string token = 1;
|
|
||||||
}
|
|
||||||
//解析token
|
|
||||||
message LdapParseTokenReq{
|
|
||||||
string token = 1;
|
|
||||||
}
|
|
||||||
message LdapParseTokenRsp{
|
|
||||||
string UserDn = 1;
|
|
||||||
int64 UserId = 2;
|
|
||||||
string UserEmail = 3;
|
|
||||||
}
|
|
||||||
@ -1,166 +0,0 @@
|
|||||||
syntax = "proto3"; //版本声明,使用v3版本
|
|
||||||
|
|
||||||
package notify;
|
|
||||||
option go_package = "gitlab.fusenpack.com/backend/notify;service";
|
|
||||||
|
|
||||||
// 导入google/api/annotations.proto 注释依赖
|
|
||||||
import "service/basic.proto";
|
|
||||||
import "google/protobuf/struct.proto";
|
|
||||||
import "google/protobuf/timestamp.proto";
|
|
||||||
|
|
||||||
//定义服务
|
|
||||||
service notify {
|
|
||||||
|
|
||||||
// 心跳 必要 用来启动邮件
|
|
||||||
rpc Ping(basic.Request) returns (basic.Response) {}
|
|
||||||
|
|
||||||
// 邮件发送基础版本
|
|
||||||
rpc EmailSend(EmailSendReq) returns (EmailSendRes) {}
|
|
||||||
|
|
||||||
// 通过邮件通知 注册确认
|
|
||||||
rpc EmailRegisterConfirm( EmailRegisterReq) returns ( EmailRegisterResp) {}
|
|
||||||
|
|
||||||
// 通过邮件通知 重置密码的填写页面
|
|
||||||
rpc EmailResetPasswordHtml( EmailResetHtmlReq) returns (EmailResetHtmlResp) {}
|
|
||||||
|
|
||||||
// 通过邮件通知 重置密码的确认
|
|
||||||
rpc EmailResetConfirm( EmailResetConfirmReq) returns (EmailResetConfirmResp) {}
|
|
||||||
|
|
||||||
// 通过邮件通知 订单 支付详情
|
|
||||||
rpc OrderPaymentDetails( OrderPaymentDetailsReq) returns (OrderPaymentDetailsResp) {}
|
|
||||||
|
|
||||||
|
|
||||||
// 通过邮件通知 订单 状态流转
|
|
||||||
rpc OrderStatusTransition( OrderStatusTransitionReq) returns (OrderStatusTransitionResp) {}
|
|
||||||
|
|
||||||
// 通过邮件通知 订单 尾部款通知
|
|
||||||
rpc OrderPayArrears( OrderPayArrearsReq) returns (OrderPayArrearsResp) {}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
message Operator {
|
|
||||||
|
|
||||||
// 操作类型
|
|
||||||
enum Type {
|
|
||||||
immediate_resend = 0; // 马上重发(覆盖当前的发送任务,等于重置)
|
|
||||||
normal_send = 1; // 标准发送(可以设置时间和重发的次数)
|
|
||||||
cancel_send = 2; // 取消发送(取消当前的发送)
|
|
||||||
}
|
|
||||||
|
|
||||||
message Retry {
|
|
||||||
int64 retry_count = 1; // 允许重发次数
|
|
||||||
int64 interval_time = 2; // 执行的时间间隔 sec 用秒为单位
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
Type type = 1; // 操作类型
|
|
||||||
optional Retry retry = 2; //重试
|
|
||||||
|
|
||||||
optional google.protobuf.Timestamp start_time = 3; // 在这个时间开始执行
|
|
||||||
optional google.protobuf.Timestamp last_send_time = 4; // 上次发送的时间
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailNotifyBasic {
|
|
||||||
optional string notify_id = 1; // 用于处理唯一的任务,重发都会被利用到 256字节, 如果不写自动生成一个uuid
|
|
||||||
string sender = 2; // 发送者
|
|
||||||
string target_email = 3; // 发送的目标email
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// 默认是 type email
|
|
||||||
message EmailSendReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string title = 2; // 邮件标题
|
|
||||||
string content = 3; // 邮件内容
|
|
||||||
Operator operator = 4; // 操作类型
|
|
||||||
optional google.protobuf.Struct metadata = 5; // 扩展参数
|
|
||||||
}
|
|
||||||
|
|
||||||
// 消息类型
|
|
||||||
enum NotifyType {
|
|
||||||
email = 0; // email
|
|
||||||
feishu = 1; // 飞书
|
|
||||||
wechat = 2; // 微信
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// 操作类型
|
|
||||||
enum EmailStatus {
|
|
||||||
ok = 0; // 成功
|
|
||||||
running = 1; // 进行中
|
|
||||||
error = 2; // 处理错误
|
|
||||||
cancel = 3; // 已经被取消
|
|
||||||
finish = 4; // 结束
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
message EmailSendRes {
|
|
||||||
EmailStatus status = 1;
|
|
||||||
string msg = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailRegisterReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string confirmation_link = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailRegisterResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
string notify_id = 2; // 通知id
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
message EmailResetHtmlReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string confirmation_link = 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailResetHtmlResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
string notify_id = 2; // 通知id
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailResetConfirmReq {
|
|
||||||
string reset_password_link = 1;
|
|
||||||
string reset_token = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmailResetConfirmResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
bytes content = 2; // 返回页面内容
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
message OrderPaymentDetailsReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string payment_details_link = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message OrderPaymentDetailsResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
string notify_id = 2; // 通知id
|
|
||||||
}
|
|
||||||
|
|
||||||
message OrderStatusTransitionReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string last_status = 2; // 上个状态
|
|
||||||
string current_status = 3; // 当前状态
|
|
||||||
string check_status_link = 4; // 检查状态
|
|
||||||
}
|
|
||||||
|
|
||||||
message OrderStatusTransitionResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
string notify_id = 2; // 通知id
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
message OrderPayArrearsReq {
|
|
||||||
EmailNotifyBasic basic_email = 1;
|
|
||||||
string pay_arrears_link = 2; // 检查状态
|
|
||||||
}
|
|
||||||
|
|
||||||
message OrderPayArrearsResp {
|
|
||||||
int64 code = 1; // 0成功 其他异常
|
|
||||||
string notify_id = 2; // 通知id
|
|
||||||
}
|
|
||||||
@ -1,307 +0,0 @@
|
|||||||
syntax = "proto3"; //版本声明,使用v3版本
|
|
||||||
|
|
||||||
package resource;
|
|
||||||
option go_package = "gitlab.fusenpack.com/backend/resource;service";
|
|
||||||
|
|
||||||
// 导入google/api/annotations.proto 注释依赖
|
|
||||||
import "service/basic.proto";
|
|
||||||
import "service/auth.proto";
|
|
||||||
|
|
||||||
//定义服务
|
|
||||||
service resource {
|
|
||||||
// 删除资源详情
|
|
||||||
rpc ResourceDelete(ResourceDeleteReq) returns (ResourceDeleteRes) {}
|
|
||||||
|
|
||||||
// 更新资源详情
|
|
||||||
rpc ResourceSave(ResourceSaveReq) returns (ResourceSaveRes) {}
|
|
||||||
|
|
||||||
// 获取资源详情
|
|
||||||
rpc ResourceInfo(ResourceInfoReq) returns (ResourceInfoRes) {}
|
|
||||||
|
|
||||||
// 获取资源列表
|
|
||||||
rpc ResourceList(ResourceListReq) returns (ResourceListRes) {}
|
|
||||||
|
|
||||||
// 后端上传--单文件
|
|
||||||
rpc UploadFileBackend(UploadFileBackendReq) returns (UploadFileBackendRes) {}
|
|
||||||
|
|
||||||
// 后端上传--分片上传
|
|
||||||
rpc UploadFileBackendFragment(UploadFileBackendFragmentReq) returns (UploadFileBackendFragmentRes) {}
|
|
||||||
|
|
||||||
// logo合图
|
|
||||||
rpc LogoAiCombine(LogoAiCombineReq) returns (LogoAiCombineRes) {}
|
|
||||||
|
|
||||||
// logo基础信息
|
|
||||||
rpc LogoInfoSet(LogoInfoSetReq) returns (LogoInfoSetRes) {}
|
|
||||||
|
|
||||||
// logo裁剪处理
|
|
||||||
rpc LogoAiCropping(LogoAiCroppingReq) returns (LogoAiCroppingRes) {}
|
|
||||||
|
|
||||||
// logo缩略处理
|
|
||||||
rpc LogoResize(LogoResizeReq) returns (LogoResizeRes) {}
|
|
||||||
|
|
||||||
// logo算法信息提取
|
|
||||||
rpc LogoAiInfoGet(LogoAiInfoGetReq) returns (LogoAiInfoGetRes) {}
|
|
||||||
|
|
||||||
// 设置示例logo
|
|
||||||
rpc SetExampleLogo(SetExampleLogoReq) returns (SetExampleLogoRes) {}
|
|
||||||
|
|
||||||
}
|
|
||||||
/* 设置示例logo */
|
|
||||||
message SetExampleLogoReq {
|
|
||||||
int64 is_example = 1;
|
|
||||||
int64 logo_id = 2;
|
|
||||||
}
|
|
||||||
message SetExampleLogoRes {
|
|
||||||
|
|
||||||
}
|
|
||||||
/* 设置示例logo */
|
|
||||||
|
|
||||||
/* logo算法信息提取 */
|
|
||||||
message LogoAiInfoGetReq {
|
|
||||||
string logo_url = 1;// logo地址
|
|
||||||
optional int64 logo_id = 2;// logoID
|
|
||||||
optional string version = 3;// 算法版本
|
|
||||||
optional string is_reverse = 4; // 是否反白
|
|
||||||
optional string logo_crop_type = 5; // 可拆类型
|
|
||||||
optional int64 is_all_template = 7; // 是否全部模版
|
|
||||||
|
|
||||||
repeated string recommend_templates = 6; // 推荐模版
|
|
||||||
bytes preprocess_logo_metadata = 8; // logo数据库额外参数
|
|
||||||
|
|
||||||
optional int64 user_id = 101; // 用户ID
|
|
||||||
optional int64 guest_id = 102; // 访客ID
|
|
||||||
optional string get_type = 103; // 获取类型:user_material=用户素材 temporary =临时
|
|
||||||
}
|
|
||||||
message LogoAiInfoGetRes {
|
|
||||||
bytes metadata =1; // AI返回基础信息--logo
|
|
||||||
bytes metadata_preprocess_logo =2; // AI返回基础信息--logo数据库
|
|
||||||
}
|
|
||||||
/* logo算法信息提取 */
|
|
||||||
|
|
||||||
/* logo缩略处理 */
|
|
||||||
message LogoResizeReq{
|
|
||||||
string resource_id=1; // 资源ID
|
|
||||||
int64 width=2; // 宽
|
|
||||||
int64 height=3;// 高
|
|
||||||
|
|
||||||
int64 handle_type = 100; // 类型:1=缓存 2=重新 3=临时
|
|
||||||
int64 user_id = 101; // 用户ID
|
|
||||||
int64 guest_id = 102; // 访客ID
|
|
||||||
}
|
|
||||||
message LogoResizeRes{
|
|
||||||
string resource_id=1;// 资源ID
|
|
||||||
string resource_url=2;// 资源链接
|
|
||||||
}
|
|
||||||
/* logo缩略处理 */
|
|
||||||
|
|
||||||
/* 更新资源详情 */
|
|
||||||
message ResourceSaveReq {
|
|
||||||
ResourceFilter filter=1;// 过滤条件
|
|
||||||
ResourceFilter save=2;// 更新数据
|
|
||||||
}
|
|
||||||
message ResourceSaveRes {}
|
|
||||||
/* 更新资源详情 */
|
|
||||||
|
|
||||||
/* 删除资源详情 */
|
|
||||||
message ResourceDeleteReq {
|
|
||||||
ResourceFilter filter=1;//过滤条件
|
|
||||||
|
|
||||||
int64 delete_type = 12; // 删除类型:1=删除数据库 2=删除s3 3=删除数据库+s3
|
|
||||||
int64 delete_limit = 13; // 删除数量
|
|
||||||
}
|
|
||||||
|
|
||||||
message ResourceDeleteRes {}
|
|
||||||
/* 删除资源详情 */
|
|
||||||
|
|
||||||
/* logo裁剪处理 */
|
|
||||||
message LogoAiCroppingReq {
|
|
||||||
string is_remove_bg=1; //是否去背景
|
|
||||||
string logo_file=2; // 资源
|
|
||||||
string width=3; // 宽
|
|
||||||
string height=4; // 高
|
|
||||||
string proportion=5; // 分辨率
|
|
||||||
|
|
||||||
int64 handle_type = 100; // 类型:1=缓存 2=重新 3=临时
|
|
||||||
int64 user_id = 101; // 用户ID
|
|
||||||
int64 guest_id = 102; // 访客ID
|
|
||||||
}
|
|
||||||
message LogoAiCroppingRes {
|
|
||||||
string resource_id=1;// 资源ID
|
|
||||||
string resource_url=2;// 资源链接
|
|
||||||
bool ismax_proportion=3; // 最大
|
|
||||||
repeated string img_color=4; // 图片颜色
|
|
||||||
}
|
|
||||||
/* logo裁剪处理 */
|
|
||||||
|
|
||||||
/* logo基础信息 */
|
|
||||||
message LogoInfoSetReq {
|
|
||||||
string logo_url=1;// logo链接
|
|
||||||
string version=2; // 算法版本
|
|
||||||
int64 is_all_template=3; // 是否全部模版
|
|
||||||
}
|
|
||||||
message LogoInfoSetRes {
|
|
||||||
string info =1; // 详情
|
|
||||||
}
|
|
||||||
/* logo基础信息 */
|
|
||||||
|
|
||||||
/* logo合图 */
|
|
||||||
message LogoAiCombineReq {
|
|
||||||
optional string logo_url = 1; // logo资源链接
|
|
||||||
optional int64 logo_material_id = 2; // logo素材ID
|
|
||||||
optional bytes logo_material_metadata = 3; // logo素材额外参数
|
|
||||||
optional int64 preprocess_logo_id = 4; // logo数据库ID
|
|
||||||
|
|
||||||
optional string template_tag = 5; // 模版标签
|
|
||||||
optional bytes template_tag_color = 6; // 模版标签颜色
|
|
||||||
|
|
||||||
optional bytes product_template_v2_info = 7; // 商品模版详情
|
|
||||||
optional bytes product_template_tag_groups = 8; // 商品模版标签组信息
|
|
||||||
|
|
||||||
optional string resolution = 9; // 合图分辨率
|
|
||||||
optional string slogan = 10; // 合图Slogan
|
|
||||||
optional string website = 11; // 合图网站
|
|
||||||
optional string address = 12; // 合图地址
|
|
||||||
optional string phone = 13; // 合图电话号码
|
|
||||||
optional string qrcode = 14; // 合图二维码
|
|
||||||
|
|
||||||
auth.Debug debug = 100; // 调试模式
|
|
||||||
int64 handle_type = 101; // 类型:1=缓存 2=重新 3=临时
|
|
||||||
int64 user_id = 102; // 用户ID
|
|
||||||
int64 guest_id = 103; // 访客ID
|
|
||||||
string trace_id = 104; // 业务链路
|
|
||||||
string resource_source = 105; // 资源来源
|
|
||||||
}
|
|
||||||
|
|
||||||
message TemplateTagColor {
|
|
||||||
repeated Color color =1;
|
|
||||||
int64 index = 2;
|
|
||||||
}
|
|
||||||
message Color {
|
|
||||||
repeated string names = 1;
|
|
||||||
}
|
|
||||||
message TemplateTagGroups {
|
|
||||||
string tag =1;
|
|
||||||
string name =2;
|
|
||||||
string value =3;
|
|
||||||
int64 fixed =4;
|
|
||||||
}
|
|
||||||
message LogoAiCombineRes {
|
|
||||||
string resource_id = 4; // 资源ID
|
|
||||||
string resource_url = 6; // 资源链接
|
|
||||||
int64 diff_time_logo_combine=15; // 合图算法时间
|
|
||||||
int64 diff_time_upload_file=16; // 合图上传时间
|
|
||||||
}
|
|
||||||
/* logo合图 */
|
|
||||||
|
|
||||||
|
|
||||||
/* 后端上传--分片上传 */
|
|
||||||
message UploadFileBackendFragmentReq {
|
|
||||||
string file_name = 1; // 文件名
|
|
||||||
string file_type = 2; // 文件类型
|
|
||||||
bytes file_content = 3; // 文件流
|
|
||||||
bytes file_header = 4; // 文件头
|
|
||||||
string file_data = 5; // base64
|
|
||||||
string file_key = 6; // 哈希
|
|
||||||
|
|
||||||
int64 chunk_number = 7; // 当前分片号:1、2、3
|
|
||||||
int64 total_chunks = 8; // 总分片数:3
|
|
||||||
|
|
||||||
|
|
||||||
int64 upload_bucket = 10; // 上传桶类型:1=持久,2=缓存
|
|
||||||
string upload_type = 11; // 上传方式:s3
|
|
||||||
string upload_id = 12; // 分片上传id
|
|
||||||
int64 api_type = 13; // 请求类型:1=对外,2=对内
|
|
||||||
string source = 14;// 来源
|
|
||||||
int64 refresh = 15; // 是否覆盖
|
|
||||||
string resource_id = 16; // 资源ID
|
|
||||||
string backup_type = 17; // 资源备份:oss
|
|
||||||
bytes metadata = 18; // json格式
|
|
||||||
int64 content_length = 19; // json格式
|
|
||||||
|
|
||||||
int64 cache_type = 100; // 缓存类型:0=不缓存 1=存储数据库
|
|
||||||
int64 user_id = 101;
|
|
||||||
int64 guest_id = 102;
|
|
||||||
}
|
|
||||||
message UploadFileBackendFragmentRes {
|
|
||||||
string upload_id = 1; // 分片上传id
|
|
||||||
string resource_type = 2; // 资源类型
|
|
||||||
string resource_id = 3;// 资源ID
|
|
||||||
string resource_url = 4;// 资源链接
|
|
||||||
}
|
|
||||||
/* 后端上传--分片上传 */
|
|
||||||
|
|
||||||
/* 后端上传--单文件 */
|
|
||||||
message UploadFileBackendReq {
|
|
||||||
string file_name = 1; // 文件名
|
|
||||||
string file_type = 2; // 文件类型
|
|
||||||
bytes file_content = 3; // 文件流
|
|
||||||
bytes file_header = 4; // 文件头
|
|
||||||
string file_data = 6; // base64
|
|
||||||
|
|
||||||
int64 api_type = 10; // 请求类型:1=对外,2=对内
|
|
||||||
int64 upload_bucket = 11; // 上传桶类型:1=持久,2=缓存
|
|
||||||
string file_key = 12; // 哈希
|
|
||||||
string source = 13;// 来源
|
|
||||||
bytes metadata = 14; // json格式
|
|
||||||
int64 refresh = 15; // 是否覆盖
|
|
||||||
string resource_id = 16; // 资源ID
|
|
||||||
string backup_type = 17; // 资源备份:oss
|
|
||||||
string upload_type = 18; // 上传方式:s3
|
|
||||||
|
|
||||||
int64 cache_type = 100; // 缓存类型:0=不缓存 1=存储数据库
|
|
||||||
int64 user_id = 101; // 用户ID
|
|
||||||
int64 guest_id = 102;// 访客ID
|
|
||||||
}
|
|
||||||
|
|
||||||
message UploadFileBackendRes{
|
|
||||||
string resource_type = 5;// 资源类型
|
|
||||||
string resource_id = 4;// 资源ID
|
|
||||||
string resource_url = 6;// 资源链接
|
|
||||||
}
|
|
||||||
/* 后端上传--文件流--单文件 */
|
|
||||||
|
|
||||||
/* 获取资源列表 */
|
|
||||||
message ResourceListReq{
|
|
||||||
ResourceFilter filter=1;// 筛选条件
|
|
||||||
|
|
||||||
int64 current_page =101; // 当前页码
|
|
||||||
int64 per_page =102; // 每页数量
|
|
||||||
string order_by = 103; // 排序
|
|
||||||
}
|
|
||||||
message ResourceListRes{
|
|
||||||
repeated basic.ResourceInfo list=1; // 列表数据
|
|
||||||
basic.Meta meta =2; // 列表参数
|
|
||||||
}
|
|
||||||
/* 获取资源列表 */
|
|
||||||
|
|
||||||
/* 获取资源详情 */
|
|
||||||
message ResourceInfoReq{
|
|
||||||
ResourceFilter filter=1; // 筛选条件
|
|
||||||
}
|
|
||||||
message ResourceInfoRes{
|
|
||||||
basic.ResourceInfo info =1;// 详情数据
|
|
||||||
}
|
|
||||||
|
|
||||||
message ResourceFilter {
|
|
||||||
optional string resource_id = 1; // 资源ID
|
|
||||||
optional int64 guest_id =2; // 用户ID
|
|
||||||
optional int64 user_id =3; // 访客ID
|
|
||||||
optional string resource_type = 4; // 资源类型
|
|
||||||
optional string resource_url = 5; // 资源链接
|
|
||||||
optional string version = 6; // 版本
|
|
||||||
optional int64 api_type = 7; // 请求类型
|
|
||||||
optional string bucket_name = 8; // 资源桶名称
|
|
||||||
optional string source = 9; // 渠道
|
|
||||||
optional bytes metadata = 10; // 额外参数
|
|
||||||
optional string trace_id = 11; // 链路ID
|
|
||||||
|
|
||||||
optional bytes other_filter = 101; // 其他筛选条件
|
|
||||||
repeated string resource_ids = 102; // 资源IDs
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
message ResourceIds {
|
|
||||||
repeated string resource_ids = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 获取资源详情 */
|
|
||||||
Loading…
x
Reference in New Issue
Block a user