tons of code

This commit is contained in:
Egor Aristov 2025-10-22 06:52:15 +03:00
parent 12e472c8e5
commit c17f0f7322
Signed by: egor3f
GPG Key ID: 40482A264AAEC85F

View File

@ -10,18 +10,12 @@ import (
var decorComment = regexp.MustCompile(`^//\s?kittenipc:api$`)
type apiStruct struct {
pkgName string
name string
methods []*ast.FuncDecl
}
type GoApiParser struct {
}
func (g *GoApiParser) Parse(sourceFile string) (*Api, error) {
var apiStructs []*apiStruct
var api Api
fileSet := token.NewFileSet()
astFile, err := parser.ParseFile(fileSet, sourceFile, nil, parser.ParseComments|parser.SkipObjectResolution)
@ -29,8 +23,6 @@ func (g *GoApiParser) Parse(sourceFile string) (*Api, error) {
return nil, fmt.Errorf("parse file: %w", err)
}
pkgName := astFile.Name.Name
for _, decl := range astFile.Decls {
genDecl, ok := decl.(*ast.GenDecl)
if !ok {
@ -58,20 +50,15 @@ func (g *GoApiParser) Parse(sourceFile string) (*Api, error) {
}
_ = structType
apiStructs = append(apiStructs, &apiStruct{
name: typeSpec.Name.Name,
pkgName: pkgName,
api.Endpoints = append(api.Endpoints, Endpoint{
Name: typeSpec.Name.Name,
})
}
if len(apiStructs) == 0 {
if len(api.Endpoints) == 0 {
return nil, fmt.Errorf("no api struct found")
}
if len(apiStructs) > 1 {
return nil, fmt.Errorf("multiple api struct found")
}
for _, decl := range astFile.Decls {
funcDecl, ok := decl.(*ast.FuncDecl)
if !ok {
@ -99,12 +86,54 @@ func (g *GoApiParser) Parse(sourceFile string) (*Api, error) {
continue
}
for _, apiStrct := range apiStructs {
if recvIdent.Name == apiStrct.name && pkgName == apiStrct.pkgName {
apiStrct.methods = append(apiStrct.methods, funcDecl)
for i, endpoint := range api.Endpoints {
if recvIdent.Name == endpoint.Name {
var apiMethod Method
apiMethod.Name = funcDecl.Name.Name
for _, param := range funcDecl.Type.Params.List {
var apiPar Val
ident := param.Type.(*ast.Ident)
switch ident.Name {
case "int":
apiPar.Type = TInt
case "string":
apiPar.Type = TString
case "bool":
apiPar.Type = TBool
default:
return nil, fmt.Errorf("parameter type %s is not supported yet", ident.Name)
}
if len(param.Names) != 1 {
return nil, fmt.Errorf("all parameters in method %s should be named", apiMethod.Name)
}
apiPar.Name = param.Names[0].Name
apiMethod.Params = append(apiMethod.Params, apiPar)
}
for _, ret := range funcDecl.Type.Results.List {
var apiRet Val
ident := ret.Type.(*ast.Ident)
switch ident.Name {
case "int":
apiRet.Type = TInt
case "string":
apiRet.Type = TString
case "bool":
apiRet.Type = TBool
case "error":
// errors are processed other way
continue
default:
return nil, fmt.Errorf("return type %s is not supported yet", ident.Name)
}
if len(ret.Names) > 0 {
apiRet.Name = ret.Names[0].Name
}
apiMethod.Ret = append(apiMethod.Ret, apiRet)
}
api.Endpoints[i].Methods = append(api.Endpoints[i].Methods, apiMethod)
}
}
}
return nil, nil
return &api, nil
}