added support for *ast.ArrayType, *ast.MapType

This commit is contained in:
Jan Halfar 2018-09-02 18:09:04 +02:00
parent 4815f1a92a
commit 082639676f
7 changed files with 72 additions and 27 deletions

View File

@ -110,7 +110,7 @@ func Build(conf *config.Config, goPath string) {
os.Exit(2)
}
ts, err := RenderTypeScriptServices(conf.ModuleKind, conf.TSClientFlavor, services, conf.Mappings, scalarTypes, target)
ts, err := RenderTypeScriptServices(conf.ModuleKind, conf.TSClientFlavor, services, conf.Mappings, scalarTypes, structs, target)
if err != nil {
fmt.Fprintln(os.Stderr, " could not generate ts code", err)
os.Exit(3)

View File

@ -93,6 +93,8 @@ type Struct struct {
Package string
Name string
Fields []*Field
Map *Map
Array *Array
}
type Scalar struct {

View File

@ -410,6 +410,15 @@ func (s *Struct) DepsSatisfied(missingTypes map[string]bool, structs map[string]
}
}
}
if s.Array != nil {
if s.Array.Value != nil {
if s.Array.Value.StructType != nil {
if needsWork(s.Array.Value.StructType.FullName()) {
return false
}
}
}
}
return !needsWork(s.FullName())
}

View File

@ -362,11 +362,22 @@ func extractTypes(file *ast.File, packageName string, structs map[string]*Struct
Package: packageName,
Type: getScalarFromAstIdent(scalarIdent),
}
// case "*ast.ArrayType":
// arrayType := obj.Decl.(*ast.ArrayType)
// case "*ast.MapType":
// mapType := obj.decl.(*ast.MapType)
case "*ast.ArrayType":
arrayValue := &Value{}
arrayValue.loadExpr(typeSpec.Type, fileImports)
structs[structName] = &Struct{
Name: name,
Package: packageName,
Array: arrayValue.Array,
}
case "*ast.MapType":
mapValue := &Value{}
mapValue.loadExpr(typeSpec.Type, fileImports)
structs[structName] = &Struct{
Name: name,
Package: packageName,
Map: mapValue.Map,
}
default:
fmt.Println(" ignoring", obj.Name, typeSpecRefl.Type().String())
}

View File

@ -23,15 +23,15 @@ func (f *Field) tsName() string {
return n
}
func (v *Value) tsType(mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, ts *code) {
func (v *Value) tsType(mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, ts *code) {
switch true {
case v.Map != nil:
ts.app("{[index:" + v.Map.KeyType + "]:")
v.Map.Value.tsType(mappings, scalarTypes, ts)
v.Map.Value.tsType(mappings, scalarTypes, structs, ts)
ts.app("}")
case v.Array != nil:
v.Array.Value.tsType(mappings, scalarTypes, ts)
v.Array.Value.tsType(mappings, scalarTypes, structs, ts)
if v.Array.Value.ScalarType != ScalarTypeByte {
ts.app("[]")
}
@ -45,12 +45,24 @@ func (v *Value) tsType(mappings config.TypeScriptMappings, scalarTypes map[strin
tsModule = mapping.TypeScriptModule
}
scalarName := v.StructType.FullName()
// is it a hdden scalar ?!
// is it a hidden scalar ?!
hiddenScalar, ok := scalarTypes[scalarName]
if ok {
ts.app(tsTypeFromScalarType(hiddenScalar.Type))
return
}
hiddenStruct, okHiddenStruct := structs[scalarName]
if okHiddenStruct && hiddenStruct.Array != nil {
hiddenMapping, hiddenMappingOK := mappings[hiddenStruct.Array.Value.StructType.Package]
var tsModule string
if hiddenMappingOK {
tsModule = hiddenMapping.TypeScriptModule
}
ts.app(tsModule + "." + hiddenStruct.Array.Value.StructType.Name + "[]")
return
}
ts.app(tsModule + "." + v.StructType.Name)
return
}
@ -58,7 +70,7 @@ func (v *Value) tsType(mappings config.TypeScriptMappings, scalarTypes map[strin
case v.Struct != nil:
//v.Struct.Value.tsType(mappings, ts)
ts.l("{").ind(1)
renderStructFields(v.Struct.Fields, mappings, scalarTypes, ts)
renderStructFields(v.Struct.Fields, mappings, scalarTypes, structs, ts)
ts.ind(-1).app("}")
case len(v.ScalarType) > 0:
ts.app(tsTypeFromScalarType(v.ScalarType))
@ -78,7 +90,7 @@ func tsTypeFromScalarType(scalarType ScalarType) string {
return string(scalarType)
}
func renderStructFields(fields []*Field, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, ts *code) {
func renderStructFields(fields []*Field, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, ts *code) {
for _, f := range fields {
if f.JSONInfo != nil && f.JSONInfo.Ignore {
continue
@ -88,17 +100,28 @@ func renderStructFields(fields []*Field, mappings config.TypeScriptMappings, sca
ts.app("?")
}
ts.app(":")
f.Value.tsType(mappings, scalarTypes, ts)
f.Value.tsType(mappings, scalarTypes, structs, ts)
ts.app(";")
ts.nl()
}
}
func renderTypescriptStruct(str *Struct, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, ts *code) error {
func renderTypescriptStruct(str *Struct, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, ts *code) error {
if str.Array != nil {
// skipping array type
return nil
}
ts.l("// " + str.FullName())
ts.l("export interface " + str.Name + " {").ind(1)
renderStructFields(str.Fields, mappings, scalarTypes, ts)
if str.Map != nil {
ts.app("[index:" + str.Map.KeyType + "]:")
str.Map.Value.tsType(mappings, scalarTypes, structs, ts)
ts.app(";")
ts.nl()
} else {
renderStructFields(str.Fields, mappings, scalarTypes, structs, ts)
}
ts.ind(-1).l("}")
return nil
}
@ -131,7 +154,7 @@ func renderTypescriptStructsToPackages(
if !(moduleKind == config.ModuleKindCommonJS) {
packageCodeMap[str.Name].ind(1)
}
err = renderTypescriptStruct(str, mappings, scalarTypes, packageCodeMap[str.Name])
err = renderTypescriptStruct(str, mappings, scalarTypes, structs, packageCodeMap[str.Name])
if err != nil {
return
}
@ -219,7 +242,7 @@ func ucFirst(str string) string {
return constPrefix
}
func RenderTypeScriptServices(moduleKind config.ModuleKind, tsClientFlavor config.TSClientFlavor, services ServiceList, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, target *config.Target) (typeScript string, err error) {
func RenderTypeScriptServices(moduleKind config.ModuleKind, tsClientFlavor config.TSClientFlavor, services ServiceList, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, target *config.Target) (typeScript string, err error) {
ts := newCode(" ")
if !SkipGoTSRPC && tsClientFlavor == "" {
@ -269,9 +292,9 @@ func RenderTypeScriptServices(moduleKind config.ModuleKind, tsClientFlavor confi
}
switch tsClientFlavor {
case config.TSClientFlavorAsync:
err = renderTypescriptClientAsync(service, mappings, scalarTypes, ts)
err = renderTypescriptClientAsync(service, mappings, scalarTypes, structs, ts)
default:
err = renderTypescriptClient(SkipGoTSRPC, moduleKind, service, mappings, scalarTypes, ts)
err = renderTypescriptClient(SkipGoTSRPC, moduleKind, service, mappings, scalarTypes, structs, ts)
}
if err != nil {
return

View File

@ -7,7 +7,7 @@ import (
"github.com/foomo/gotsrpc/config"
)
func renderTypescriptClient(skipGoTSRPC bool, moduleKind config.ModuleKind, service *Service, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, ts *code) error {
func renderTypescriptClient(skipGoTSRPC bool, moduleKind config.ModuleKind, service *Service, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, ts *code) error {
clientName := service.Name + "Client"
ts.l("export class " + clientName + " {").ind(1)
@ -54,7 +54,7 @@ func renderTypescriptClient(skipGoTSRPC bool, moduleKind config.ModuleKind, serv
ts.app(", ")
}
ts.app(arg.tsName() + ":")
arg.Value.tsType(mappings, scalarTypes, ts)
arg.Value.tsType(mappings, scalarTypes, structs, ts)
callArgs = append(callArgs, arg.Name)
argCount++
}
@ -76,7 +76,7 @@ func renderTypescriptClient(skipGoTSRPC bool, moduleKind config.ModuleKind, serv
ts.app(", ")
}
ts.app(retArgName + ":")
retField.Value.tsType(mappings, scalarTypes, ts)
retField.Value.tsType(mappings, scalarTypes, structs, ts)
}
ts.app(") => void")

View File

@ -8,7 +8,7 @@ import (
"github.com/foomo/gotsrpc/config"
)
func renderTypescriptClientAsync(service *Service, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, ts *code) error {
func renderTypescriptClientAsync(service *Service, mappings config.TypeScriptMappings, scalarTypes map[string]*Scalar, structs map[string]*Struct, ts *code) error {
clientName := service.Name + "Client"
ts.l("export class " + clientName + " {")
@ -48,7 +48,7 @@ func renderTypescriptClientAsync(service *Service, mappings config.TypeScriptMap
ts.app(", ")
}
ts.app(arg.tsName() + ":")
arg.Value.tsType(mappings, scalarTypes, ts)
arg.Value.tsType(mappings, scalarTypes, structs, ts)
callArgs = append(callArgs, arg.Name)
argCount++
}
@ -85,7 +85,7 @@ func renderTypescriptClientAsync(service *Service, mappings config.TypeScriptMap
}
innerReturnTypeTS.app(strconv.Itoa(index) + ":")
retField.Value.tsType(mappings, scalarTypes, innerReturnTypeTS)
retField.Value.tsType(mappings, scalarTypes, structs, innerReturnTypeTS)
if index == len(method.Return)-1 && retField.Value.IsError {
throwLastError = true
@ -94,14 +94,14 @@ func renderTypescriptClientAsync(service *Service, mappings config.TypeScriptMap
} else {
if index == 0 {
firstReturnTypeTS := newCode(" ")
retField.Value.tsType(mappings, scalarTypes, firstReturnTypeTS)
retField.Value.tsType(mappings, scalarTypes, structs, firstReturnTypeTS)
firstReturnType = firstReturnTypeTS.string()
//firstReturnFieldName = retArgName
}
countReturns++
returnTypeTS.app(retArgName + ":")
responseObject += responseObjectPrefix + retArgName + " : response[" + strconv.Itoa(index) + "]"
retField.Value.tsType(mappings, scalarTypes, returnTypeTS)
retField.Value.tsType(mappings, scalarTypes, structs, returnTypeTS)
}
responseObjectPrefix = ", "
}