1 Star 0 Fork 0

rainman/goboot

加入 Gitee
与超过 1400万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
文件
克隆/下载
src_scanner.go 6.56 KB
一键复制 编辑 原始数据 按行查看 历史
rainman 提交于 2025-11-21 17:25 +08:00 . 调整结构
package goboot
import (
"go/ast"
"go/parser"
"go/token"
"log"
"os"
"strings"
)
// OriStruct 原始结构体
type OriStruct struct {
StructName string `json:"structName"` //结构体名称
PackageName string `json:"packageName"` //包名称
FullPackageName string `json:"fullPackageName"` //包名称
CommentStr string `json:"commentStr"` //注释
PackageImports []string `json:"packageImports"` //导入的包
FiledList []OriStructFiled `json:"filedList"` //字段列表
}
// OriStructFiled 原始结构体字段
type OriStructFiled struct {
CommentStr string `json:"commentStr"` //注释
Name string `json:"name"` //参数名称
TypeName string `json:"typeName"` //参数类型名称
TagStr string `json:"tagStr"` //标签
}
// OriStructMethod 原始结构体方法
type OriStructMethod struct {
PackageName string `json:"packageName"` //包名称
Name string `json:"name"` //方法名称
CommentStr string `json:"commentStr"` //注释
BelongStructName string `json:"belongStructName"` //所属结构体名称
BelongStructFullPackageName string `json:"belongStructFullPackageName"` //所属结构体名称
ParamList []oriStructMethodParam `json:"paramList"` //参数列表
PackageImports []string `json:"packageImports"` //导入的包
}
type oriStructMethodParam struct {
Name string `json:"name"` //参数名称
TypeName string `json:"typeName"` //参数类型名称
}
var fileFullPaths []string
var oriMethodList []OriStructMethod //原始的方法列表
var oriStructList []OriStruct //原始的结构体列表
func scanOriCode(moduleName string) {
listAllFiles(".")
for _, filePath := range fileFullPaths {
scanOriCodeOne(filePath, moduleName)
}
}
func scanOriCodeOne(scanFilePath string, moduleName string) {
//fmt.Println(scanFilePath)
//读取文件内容
fileContent, err := os.ReadFile(scanFilePath)
if err != nil {
panic(err)
}
fileAst, err := parser.ParseFile(token.NewFileSet(), scanFilePath, nil, parser.ParseComments)
if err != nil {
panic(err)
}
fullPackageName := ""
packageName := fileAst.Name.Name
if packageName != "main" {
fullPackageName = moduleName + "/" + scanFilePath[2:strings.LastIndex(scanFilePath, "/")]
}
packageImports := []string{}
//获得导包信息
for _, importItem := range fileAst.Imports {
packageImports = append(packageImports, importItem.Path.Value)
}
//fmt.Println(packageImports)
//读取结构体信息
for _, decl := range fileAst.Decls {
if stc, ok := decl.(*ast.GenDecl); ok { //处理结构体
for _, spec := range stc.Specs {
if tp, ok := spec.(*ast.TypeSpec); ok {
filedList := []OriStructFiled{}
if stp, ok := tp.Type.(*ast.StructType); ok {
for _, field := range stp.Fields.List {
//字段名称
fieldName := ""
for _, name := range field.Names {
fieldName = name.Name
}
//字段类型名称
typeName := ""
if starExpr, ok := field.Type.(*ast.StarExpr); ok {
if ident, ok := starExpr.X.(*ast.Ident); ok { //地址
typeName = "*" + ident.Name
}
if selectorExpr, ok := starExpr.X.(*ast.SelectorExpr); ok { //列表
typeName = "*" + selectorExpr.Sel.Name
}
}
if ident, ok := field.Type.(*ast.Ident); ok { //非地址
typeName = ident.Name
}
tagStr := ""
if field.Tag != nil {
tagStr = field.Tag.Value
}
filedList = append(filedList, OriStructFiled{
Name: fieldName,
TypeName: typeName,
TagStr: tagStr,
CommentStr: field.Comment.Text(),
})
}
}
oriStructList = append(oriStructList, OriStruct{
StructName: tp.Name.Name,
PackageName: packageName,
FullPackageName: fullPackageName,
CommentStr: stc.Doc.Text(),
//PackageImports: packageImports,
FiledList: filedList,
})
}
}
} else { //处理函数
funcDecl := decl.(*ast.FuncDecl)
fullStr := string(fileContent[funcDecl.Type.Pos()-1 : funcDecl.Type.End()-1])
fullStr = fullStr[0:strings.Index(fullStr, funcDecl.Name.Name+"(")]
if !strings.Contains(fullStr, "(") {
fullStr = ""
} else {
fullStr = fullStr[strings.Index(fullStr, "(")+1 : strings.Index(fullStr, ")")]
fullStr = strings.Trim(fullStr, " ")
fullStr = fullStr[strings.LastIndex(fullStr, " ")+1:]
if fullStr[0] == '*' {
fullStr = fullStr[1:]
}
}
paramList := []oriStructMethodParam{}
for _, param := range funcDecl.Type.Params.List { //参数列表
for _, name := range param.Names {
//参数类型名称
typeName := ""
if starExpr, ok := param.Type.(*ast.StarExpr); ok {
//typeName = "*" + starExpr.X.(*ast.Ident).Name
if ident, ok := starExpr.X.(*ast.Ident); ok {
typeName = "*" + ident.Name
}
if selectorExpr, ok := starExpr.X.(*ast.SelectorExpr); ok {
typeName = "*" + string(fileContent[selectorExpr.Pos()-1:selectorExpr.End()-1])
}
}
if ident, ok := param.Type.(*ast.Ident); ok {
typeName = ident.Name
}
if selectorExpr, ok := param.Type.(*ast.SelectorExpr); ok {
typeName = string(fileContent[selectorExpr.Pos()-1 : selectorExpr.End()-1])
}
paramList = append(paramList, oriStructMethodParam{
Name: name.Name,
TypeName: typeName,
})
}
}
oriMethodList = append(oriMethodList, OriStructMethod{
PackageName: packageName,
Name: funcDecl.Name.Name,
BelongStructName: fullStr,
BelongStructFullPackageName: fullPackageName,
ParamList: paramList,
PackageImports: packageImports,
CommentStr: funcDecl.Doc.Text(),
})
}
}
}
func listAllFiles(dirPath string) {
dir, direrr := os.Open(dirPath)
if direrr != nil {
log.Fatalf("文件不存在: %v", direrr)
}
defer dir.Close()
files, _ := dir.ReadDir(-1)
for _, dirsOrFile := range files {
if dirsOrFile.IsDir() {
listAllFiles(dirPath + "/" + dirsOrFile.Name())
} else {
if !strings.HasSuffix(dirsOrFile.Name(), ".go") {
continue
}
fileFullPaths = append(fileFullPaths, dirPath+"/"+dirsOrFile.Name())
}
}
}
Loading...
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
1
https://gitee.com/rainsuperman/goboot.git
git@gitee.com:rainsuperman/goboot.git
rainsuperman
goboot
goboot
v1.0.5

搜索帮助