ソースを参照

fix inner type generate error (#377)

* fix point type bug

* optimized

* fix inner type error
kingxt 4 年 前
コミット
9cd2015661

+ 27 - 23
tools/goctl/api/javagen/gencomponents.go

@@ -122,15 +122,6 @@ func (c *componentsContext) createComponent(dir, packetName string, ty spec.Type
 		return err
 	}
 
-	fp, created, err := apiutil.MaybeCreateFile(dir, modelDir, modelFile)
-	if err != nil {
-		return err
-	}
-	if !created {
-		return nil
-	}
-	defer fp.Close()
-
 	propertiesString, err := c.buildProperties(defineStruct)
 	if err != nil {
 		return err
@@ -160,6 +151,15 @@ func (c *componentsContext) createComponent(dir, packetName string, ty spec.Type
 		return err
 	}
 
+	fp, created, err := apiutil.MaybeCreateFile(dir, modelDir, modelFile)
+	if err != nil {
+		return err
+	}
+	if !created {
+		return nil
+	}
+	defer fp.Close()
+
 	buffer := new(bytes.Buffer)
 	t := template.Must(template.New("componentType").Parse(componentTemplate))
 	err = t.Execute(buffer, map[string]interface{}{
@@ -192,7 +192,7 @@ func (c *componentsContext) buildProperties(defineStruct spec.DefineStruct) (str
 
 func (c *componentsContext) buildGetterSetter(defineStruct spec.DefineStruct) (string, error) {
 	var builder strings.Builder
-	if err := c.genGetSet(&builder, defineStruct, 1); err != nil {
+	if err := c.genGetSet(&builder, 1); err != nil {
 		return "", apiutil.WrapErr(err, "Type "+defineStruct.Name()+" get or set generate error")
 	}
 
@@ -209,18 +209,23 @@ func (c *componentsContext) writeType(writer io.Writer, defineStruct spec.Define
 	return nil
 }
 
-func (c *componentsContext) writeMembers(writer io.Writer, defineStruct spec.DefineStruct, indent int) error {
-	for _, member := range defineStruct.Members {
+func (c *componentsContext) writeMembers(writer io.Writer, tp spec.Type, indent int) error {
+	definedType, ok := tp.(spec.DefineStruct)
+	if !ok {
+		pointType, ok := tp.(spec.PointerType)
+		if ok {
+			return c.writeMembers(writer, pointType.Type, indent)
+		}
+		return errors.New(fmt.Sprintf("type %s not supported", tp.Name()))
+	}
+
+	for _, member := range definedType.Members {
 		if member.IsInline {
-			defineStruct, ok := member.Type.(spec.DefineStruct)
-			if ok {
-				err := c.writeMembers(writer, defineStruct, indent)
-				if err != nil {
-					return err
-				}
-				continue
+			err := c.writeMembers(writer, member.Type, indent)
+			if err != nil {
+				return err
 			}
-			return errors.New("unsupported inline type %s" + member.Type.Name())
+			continue
 		}
 
 		if member.IsBodyMember() || member.IsFormMember() {
@@ -263,9 +268,8 @@ func (c *componentsContext) buildConstructor() (string, string, error) {
 	return params.String(), constructorSetter.String(), nil
 }
 
-func (c *componentsContext) genGetSet(writer io.Writer, defineStruct spec.DefineStruct, indent int) error {
-	var members = defineStruct.GetBodyMembers()
-	members = append(members, defineStruct.GetFormMembers()...)
+func (c *componentsContext) genGetSet(writer io.Writer, indent int) error {
+	var members = c.members
 	for _, member := range members {
 		javaType, err := specTypeToJava(member.Type)
 		if err != nil {

+ 16 - 21
tools/goctl/api/javagen/genpacket.go

@@ -1,10 +1,8 @@
 package javagen
 
 import (
-	"bufio"
 	"bytes"
 	"fmt"
-	"os"
 	"strings"
 	"text/template"
 
@@ -20,6 +18,7 @@ import com.xhb.core.packet.HttpPacket;
 import com.xhb.core.network.HttpRequestClient;
 {{.imports}}
 
+{{.doc}}
 public class {{.packetName}} extends HttpPacket<{{.responseType}}> {
 	{{.paramsDeclaration}}
 
@@ -101,14 +100,28 @@ func createWith(dir string, api *spec.ApiSpec, route spec.Route, packetName stri
 		"requestType":       util.Title(route.RequestTypeName()),
 		"HasRequestBody":    hasRequestBody,
 		"imports":           imports,
+		"doc":               doc(route),
 	})
 	if err != nil {
 		return err
 	}
-	formatFile(&tmplBytes, fp)
+
+	_, err = fp.WriteString(formatSource(tmplBytes.String()))
 	return nil
 }
 
+func doc(route spec.Route) string {
+	comment := route.JoinedDoc()
+	if len(comment) > 0 {
+		formatter := `
+/*
+    %s	
+*/`
+		return fmt.Sprintf(formatter, comment)
+	}
+	return ""
+}
+
 func getImports(api *spec.ApiSpec, packetName string) string {
 	var builder strings.Builder
 	allTypes := api.Types
@@ -118,24 +131,6 @@ func getImports(api *spec.ApiSpec, packetName string) string {
 	return builder.String()
 }
 
-func formatFile(tmplBytes *bytes.Buffer, file *os.File) {
-	scanner := bufio.NewScanner(tmplBytes)
-	builder := bufio.NewWriter(file)
-	defer builder.Flush()
-	preIsBreakLine := false
-	for scanner.Scan() {
-		text := strings.TrimSpace(scanner.Text())
-		if text == "" && preIsBreakLine {
-			continue
-		}
-		preIsBreakLine = text == ""
-		builder.WriteString(scanner.Text() + "\n")
-	}
-	if err := scanner.Err(); err != nil {
-		fmt.Println(err)
-	}
-}
-
 func paramsSet(route spec.Route) string {
 	path := route.Path
 	cops := strings.Split(path, "/")

+ 4 - 0
tools/goctl/api/javagen/util.go

@@ -11,6 +11,10 @@ import (
 )
 
 func writeProperty(writer io.Writer, member spec.Member, indent int) error {
+	if len(member.Comment) > 0 {
+		writeIndent(writer, indent)
+		fmt.Fprint(writer, member.Comment+util.NL)
+	}
 	writeIndent(writer, indent)
 	ty, err := specTypeToJava(member.Type)
 	ty = strings.Replace(ty, "*", "", 1)

+ 17 - 0
tools/goctl/api/parser/parser.go

@@ -104,9 +104,11 @@ func (p parser) fillTypes() error {
 		}
 	}
 
+	var types []spec.Type
 	for _, item := range p.spec.Types {
 		switch v := (item).(type) {
 		case spec.DefineStruct:
+			var members []spec.Member
 			for _, member := range v.Members {
 				switch v := member.Type.(type) {
 				case spec.DefineStruct:
@@ -117,11 +119,16 @@ func (p parser) fillTypes() error {
 						member.Type = *tp
 					}
 				}
+				members = append(members, member)
 			}
+			v.Members = members
+			types = append(types, v)
 		default:
 			return errors.New(fmt.Sprintf("unknown type %+v", v))
 		}
 	}
+	p.spec.Types = types
+
 	return nil
 }
 
@@ -243,6 +250,16 @@ func (p parser) fillService() error {
 			if astRoute.Route.Reply != nil {
 				route.ResponseType = p.astTypeToSpec(astRoute.Route.Reply.Name)
 			}
+			if astRoute.AtDoc != nil {
+				var properties = make(map[string]string, 0)
+				for _, kv := range astRoute.AtDoc.Kv {
+					properties[kv.Key.Text()] = kv.Value.Text()
+				}
+				route.AtDoc.Properties = properties
+				if astRoute.AtDoc.LineDoc != nil {
+					route.AtDoc.Text = astRoute.AtDoc.LineDoc.Text()
+				}
+			}
 
 			err := p.fillRouteType(&route)
 			if err != nil {

+ 11 - 3
tools/goctl/api/spec/fn.go

@@ -8,8 +8,11 @@ import (
 	"github.com/tal-tech/go-zero/tools/goctl/util"
 )
 
-const bodyTagKey = "json"
-const formTagKey = "form"
+const (
+	bodyTagKey        = "json"
+	formTagKey        = "form"
+	defaultSummaryKey = "summary"
+)
 
 var definedKeys = []string{bodyTagKey, formTagKey, "path"}
 
@@ -155,7 +158,12 @@ func (t DefineStruct) GetNonBodyMembers() []Member {
 }
 
 func (r Route) JoinedDoc() string {
-	return strings.Join(r.Docs, " ")
+	doc := r.AtDoc.Text
+	if r.AtDoc.Properties != nil {
+		doc += r.AtDoc.Properties[defaultSummaryKey]
+	}
+	doc += strings.Join(r.Docs, " ")
+	return strings.TrimSpace(doc)
 }
 
 func (r Route) GetAnnotation(key string) string {

+ 6 - 0
tools/goctl/api/spec/spec.go

@@ -61,6 +61,7 @@ type (
 		ResponseType Type
 		Docs         Doc
 		Handler      string
+		AtDoc        AtDoc
 	}
 
 	Service struct {
@@ -109,4 +110,9 @@ type (
 		RawName string
 		Type    Type
 	}
+
+	AtDoc struct {
+		Properties map[string]string
+		Text       string
+	}
 )

+ 2 - 2
tools/goctl/api/tsgen/genpacket.go

@@ -46,10 +46,11 @@ func genHandler(dir, webApi, caller string, api *spec.ApiSpec, unwrapApi bool) e
 
 	if len(api.Types) != 0 {
 		if len(imports) > 0 {
-			imports += "\n"
+			imports += util.NL
 		}
 		outputFile := apiutil.ComponentName(api)
 		imports += fmt.Sprintf(`import * as components from "%s"`, "./"+outputFile)
+		imports += fmt.Sprintf(`%sexport * from "%s"`, util.NL, "./"+outputFile)
 	}
 
 	apis, err := genApi(api, caller)
@@ -59,7 +60,6 @@ func genHandler(dir, webApi, caller string, api *spec.ApiSpec, unwrapApi bool) e
 
 	t := template.Must(template.New("handlerTemplate").Parse(handlerTemplate))
 	return t.Execute(fp, map[string]string{
-		"webApi":  webApi,
 		"imports": imports,
 		"apis":    strings.TrimSpace(apis),
 	})

+ 9 - 5
tools/goctl/api/tsgen/util.go

@@ -111,7 +111,7 @@ func primitiveType(tp string) (string, bool) {
 
 func writeType(writer io.Writer, tp spec.Type) error {
 	fmt.Fprintf(writer, "export interface %s {\n", util.Title(tp.Name()))
-	if err := genMembers(writer, tp, false); err != nil {
+	if err := writeMembers(writer, tp, false); err != nil {
 		return err
 	}
 
@@ -131,7 +131,7 @@ func genParamsTypesIfNeed(writer io.Writer, tp spec.Type) error {
 	}
 	fmt.Fprintf(writer, "\n")
 	fmt.Fprintf(writer, "export interface %sParams {\n", util.Title(tp.Name()))
-	if err := genMembers(writer, tp, true); err != nil {
+	if err := writeMembers(writer, tp, true); err != nil {
 		return err
 	}
 
@@ -139,10 +139,14 @@ func genParamsTypesIfNeed(writer io.Writer, tp spec.Type) error {
 	return nil
 }
 
-func genMembers(writer io.Writer, tp spec.Type, isParam bool) error {
+func writeMembers(writer io.Writer, tp spec.Type, isParam bool) error {
 	definedType, ok := tp.(spec.DefineStruct)
 	if !ok {
-		return errors.New("no members of type " + tp.Name())
+		pointType, ok := tp.(spec.PointerType)
+		if ok {
+			return writeMembers(writer, pointType.Type, isParam)
+		}
+		return errors.New(fmt.Sprintf("type %s not supported", tp.Name()))
 	}
 
 	members := definedType.GetBodyMembers()
@@ -151,7 +155,7 @@ func genMembers(writer io.Writer, tp spec.Type, isParam bool) error {
 	}
 	for _, member := range members {
 		if member.IsInline {
-			if err := genMembers(writer, member.Type, isParam); err != nil {
+			if err := writeMembers(writer, member.Type, isParam); err != nil {
 				return err
 			}
 			continue