【修复】修复 go对可空变量的支持

main
walon 2021-07-08 14:01:21 +08:00
parent 36645bd6f8
commit 1aeeca2e08
13 changed files with 669 additions and 342 deletions

View File

@ -25,8 +25,6 @@ Luban适合有以下需求的开发者
2. 希望针对项目需求方便地定制配置、消息等生成,满足更严苛的内存和性能的要求 2. 希望针对项目需求方便地定制配置、消息等生成,满足更严苛的内存和性能的要求
3. 希望做其他自定义生成或者缓存 3. 希望做其他自定义生成或者缓存
====**如果觉得不错烦请点个star你的支持会给予我们巨大动力 ^_^**==== ====**如果觉得不错烦请点个star你的支持会给予我们巨大动力 ^_^**====
## 文档 ## 文档

View File

@ -40,12 +40,10 @@
可以直接从 [示例配置](https://github.com/focus-creative-games/luban_examples/tree/main/DesignerConfigs/Defines) 拷贝这个文件。 可以直接从 [示例配置](https://github.com/focus-creative-games/luban_examples/tree/main/DesignerConfigs/Defines) 拷贝这个文件。
这个 root 文件描述了: 这个 root 文件描述了:
3. 生成代码的默认顶层命名空间为 cfg - 生成代码的默认顶层命名空间为 cfg
4. 有 3 个分组 c,s,e 对应 clientservereditor 分组。 分组用于配置选择性导出。后面再介绍。 - 有 3 个分组 c,s,e 对应 clientservereditor 分组。 分组用于配置选择性导出。后面再介绍。
5. import name=”.” 表明从当前目录导入所有子模块定义文件。我们会把所有子模块定义文件也放到 Defines 目录下。 - import name=”.” 表明从当前目录导入所有子模块定义文件。我们会把所有子模块定义文件也放到 Defines 目录下。
6. server 表示最终输出的目标。当前定义了 4 个目标。service 的 group 属性指明了这个目标会包含哪些分组。 - server 表示最终输出的目标。当前定义了 4 个目标。service 的 group 属性指明了这个目标会包含哪些分组。例如: server 目标就只包含 s 分组,而 all 目标包含了所有分组。我们先不细究这些定义的含义。
例如: server 目标就只包含 s 分组,而 all 目标包含了所有分组。
我们先不细究这些定义的含义。
7. 创建第一个配置表 物品表 7. 创建第一个配置表 物品表
@ -166,7 +164,7 @@
加载完 cfg.Tables 后,只需要用 tables.<表名> 就能获得那个表实例,接着可以做各种操作。 加载完 cfg.Tables 后,只需要用 tables.<表名> 就能获得那个表实例,接着可以做各种操作。
例如我们要访问 id = 1 的那个记录。代码如下 例如我们要访问 id = 1 的那个记录。代码如下
``` ```c#
cfg.item.Item itemInfo = tables.TbItem.Get(1); cfg.item.Item itemInfo = tables.TbItem.Get(1);
Console.WriteLine(“{0} {1} {2} {3}”, Console.WriteLine(“{0} {1} {2} {3}”,
itemInfo.Id, itemInfo.Name, itemInfo.Desc,itemInfo.Price) itemInfo.Id, itemInfo.Name, itemInfo.Desc,itemInfo.Price)

View File

@ -78,24 +78,14 @@ namespace Luban.Job.Cfg.Defs
return type.Apply(GoTypeNameVisitor.Ins); return type.Apply(GoTypeNameVisitor.Ins);
} }
public static string GoDeserializeType(TType type, string bufName) public static string GoDeserializeType(TBean type, string bufName)
{ {
return type.Apply(GoDeserializeVisitor.Ins, bufName); return type.Bean.IsAbstractType ? $"NewChild{type.Bean.GoFullName}({bufName})" : $"New{ type.Bean.GoFullName} ({ bufName})";
} }
public static string GoDeserializeField(DefField field, string bufName) public static string GoDeserializeField(TType type, string name, string bufName)
{ {
var name = field.CsStyleName; return type.Apply(GoDeserializeVisitor.Ins, name, bufName);
TType type = field.CType;
if (field.CType.IsNullable)
{
return $"{{ var _exists bool; if _exists, err = {bufName}.ReadBool(); err != nil {{ return }}; if _exists {{ if _v.{name}, err = {type.Apply(GoDeserializeVisitor.Ins, bufName)}; err != nil {{ return }} }} }}";
}
else
{
return $"if _v.{name}, err = {type.Apply(GoDeserializeVisitor.Ins, bufName)}; err != nil {{ return }} ";
}
} }
public static string TsJsonConstructor(string fieldName, string jsonFieldName, TType type) public static string TsJsonConstructor(string fieldName, string jsonFieldName, TType type)

View File

@ -6,67 +6,11 @@ using System.Collections.Generic;
namespace Luban.Job.Cfg.Generate namespace Luban.Job.Cfg.Generate
{ {
class GoCodeRender class GoBinCodeRender : GoCodeRenderBase
{ {
public string RenderAny(object o)
{
switch (o)
{
case DefConst c: return Render(c);
case DefEnum e: return Render(e);
case DefBean b: return Render(b);
case DefTable r: return Render(r);
default: throw new Exception($"unknown render type:{o}");
}
}
[ThreadStatic]
private static Template t_constRender;
public string Render(DefConst c)
{
string package = "cfg";
var template = t_constRender ??= Template.Parse(@"
package {{package}}
const (
{{~for item in x.items ~}}
{{x.go_full_name}}_{{item.name}} = {{go_const_value item.ctype item.value}}
{{~end~}}
)
");
var result = template.RenderCode(c, new Dictionary<string, object>() { ["package"] = package });
return result;
}
[ThreadStatic]
private static Template t_enumRender;
public string Render(DefEnum e)
{
string package = "cfg";
var template = t_enumRender ??= Template.Parse(@"
package {{package}}
const (
{{~for item in x.items ~}}
{{x.go_full_name}}_{{item.name}} = {{item.value}}
{{~end~}}
)
");
var result = template.RenderCode(e, new Dictionary<string, object>() { ["package"] = package });
return result;
}
[ThreadStatic] [ThreadStatic]
private static Template t_beanRender; private static Template t_beanRender;
protected override string Render(DefBean b)
public string Render(DefBean b)
{ {
string package = "cfg"; string package = "cfg";
@ -78,9 +22,15 @@ const (
export_fields = x.export_fields export_fields = x.export_fields
hierarchy_not_abstract_children = x.hierarchy_not_abstract_children hierarchy_not_abstract_children = x.hierarchy_not_abstract_children
-}} -}}
package {{package}} package {{package}}
import ""bright/serialization"" import (
""bright/serialization""
{{~if is_abstract_type~}}
""errors""
{{~end~}}
)
{{x.go_import}} {{x.go_import}}
@ -107,7 +57,7 @@ func New{{go_full_name}}(_buf *serialization.ByteBuf) (_v *{{go_full_name}}, err
_v.{{parent_def_type.go_full_name}} = *_p _v.{{parent_def_type.go_full_name}} = *_p
{{~end~}} {{~end~}}
{{~for field in export_fields ~}} {{~for field in export_fields ~}}
{{go_deserialize_field field '_buf'}} {{go_deserialize_field field.ctype (""_v."" + field.go_style_name) '_buf'}}
{{~end~}} {{~end~}}
return return
} }
@ -119,8 +69,9 @@ func NewChild{{go_full_name}}(_buf *serialization.ByteBuf) (_v interface{}, err
} }
switch id { switch id {
{{~for child in hierarchy_not_abstract_children~}} {{~for child in hierarchy_not_abstract_children~}}
case {{child.id}}: return New{{child.go_full_name}}(_buf); case {{child.id}}: return New{{child.go_full_name}}(_buf)
{{~end~}} {{~end~}}
default: return nil, errors.New(""unknown type id"")
} }
return return
} }
@ -132,10 +83,9 @@ func NewChild{{go_full_name}}(_buf *serialization.ByteBuf) (_v interface{}, err
return result; return result;
} }
[ThreadStatic] [ThreadStatic]
private static Template t_tableRender; private static Template t_tableRender;
public string Render(DefTable p) protected override string Render(DefTable p)
{ {
// TODO 目前只有普通表支持多态. 单例表和双key表都不支持 // TODO 目前只有普通表支持多态. 单例表和双key表都不支持
string package = "cfg"; string package = "cfg";
@ -150,6 +100,7 @@ func NewChild{{go_full_name}}(_buf *serialization.ByteBuf) (_v interface{}, err
index_field1 = x.index_field1 index_field1 = x.index_field1
index_field2 = x.index_field2 index_field2 = x.index_field2
-}} -}}
package {{package}} package {{package}}
import ""bright/serialization"" import ""bright/serialization""
@ -236,11 +187,12 @@ func (table *{{go_full_name}}) Get() {{go_define_type value_type}} {
[ThreadStatic] [ThreadStatic]
private static Template t_serviceRender; private static Template t_serviceRender;
public string RenderService(string name, string module, List<DefTable> tables) public override string RenderService(string name, string module, List<DefTable> tables)
{ {
string package = "cfg"; string package = "cfg";
var template = t_serviceRender ??= Template.Parse(@" var template = t_serviceRender ??= Template.Parse(@"
package {{package}} package {{package}}
import ""bright/serialization"" import ""bright/serialization""

View File

@ -0,0 +1,78 @@
using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Defs;
using Scriban;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace Luban.Job.Cfg.Generate
{
abstract class GoCodeRenderBase
{
public string RenderAny(object o)
{
switch (o)
{
case DefConst c: return Render(c);
case DefEnum e: return Render(e);
case DefBean b: return Render(b);
case DefTable r: return Render(r);
default: throw new Exception($"unknown render type:{o}");
}
}
[ThreadStatic]
private static Template t_constRender;
private string Render(DefConst c)
{
string package = "cfg";
var template = t_constRender ??= Template.Parse(@"
package {{package}}
const (
{{~for item in x.items ~}}
{{x.go_full_name}}_{{item.name}} = {{go_const_value item.ctype item.value}}
{{~end~}}
)
");
var result = template.RenderCode(c, new Dictionary<string, object>() { ["package"] = package });
return result;
}
[ThreadStatic]
private static Template t_enumRender;
private string Render(DefEnum e)
{
string package = "cfg";
var template = t_enumRender ??= Template.Parse(@"
package {{package}}
const (
{{~for item in x.items ~}}
{{x.go_full_name}}_{{item.name}} = {{item.value}}
{{~end~}}
)
");
var result = template.RenderCode(e, new Dictionary<string, object>() { ["package"] = package });
return result;
}
protected abstract string Render(DefBean b);
protected abstract string Render(DefTable p);
public abstract string RenderService(string name, string module, List<DefTable> tables);
}
}

View File

@ -0,0 +1,218 @@
using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Defs;
using Scriban;
using System;
using System.Collections.Generic;
namespace Luban.Job.Cfg.Generate
{
class GoJsonCodeRender : GoCodeRenderBase
{
[ThreadStatic]
private static Template t_beanRender;
protected override string Render(DefBean b)
{
string package = "cfg";
var template = t_beanRender ??= Template.Parse(@"
{{-
go_full_name = x.go_full_name
parent_def_type = x.parent_def_type
is_abstract_type = x.is_abstract_type
export_fields = x.export_fields
hierarchy_not_abstract_children = x.hierarchy_not_abstract_children
-}}
package {{package}}
{{x.go_import}}
type {{go_full_name}} struct {
{{~if parent_def_type~}}
{{parent_def_type.go_full_name}}
{{~end~}}
{{~for field in export_fields ~}}
{{field.cs_style_name}} {{go_define_type field.ctype}}
{{~end~}}
}
{{~if !is_abstract_type~}}
func ({{go_full_name}}) GetTypeId() int {
return {{x.id}}
}
{{~end~}}
func New{{go_full_name}}(_buf map[string]interface{}) (_v *{{go_full_name}}, err error) {
_v = &{{go_full_name}}{}
{{~if parent_def_type~}}
var _p *{{parent_def_type.go_full_name}}
if _p, err = New{{parent_def_type.go_full_name}}(_buf) ; err != nil { return }
_v.{{parent_def_type.go_full_name}} = *_p
{{~end~}}
{{~for field in export_fields ~}}
{{go_deserialize_field field '_buf'}}
{{~end~}}
return
}
{{~if is_abstract_type~}}
func NewChild{{go_full_name}}(_buf map[string]interface{}) (_v interface{}, err error) {
var id int32
if id, err = _buf.ReadInt() ; err != nil {
return
}
switch id {
{{~for child in hierarchy_not_abstract_children~}}
case {{child.id}}: return New{{child.go_full_name}}(_buf);
{{~end~}}
default: return nil, errors.New(""unknown type id"")
}
return
}
{{~end~}}
");
var result = template.RenderCode(b, new Dictionary<string, object>() { ["package"] = package });
return result;
}
[ThreadStatic]
private static Template t_tableRender;
protected override string Render(DefTable p)
{
// TODO 目前只有普通表支持多态. 单例表和双key表都不支持
string package = "cfg";
var template = t_tableRender ??= Template.Parse(@"
{{-
go_full_name = x.go_full_name
key_type = x.key_ttype
key_type1 = x.key_ttype1
key_type2 = x.key_ttype2
value_type = x.value_ttype
index_field = x.index_field
index_field1 = x.index_field1
index_field2 = x.index_field2
-}}
package {{package}}
{{~if x.is_map_table~}}
type {{go_full_name}} struct {
_dataMap map[{{go_define_type key_type}}]{{go_define_type value_type}}
_dataList []{{go_define_type value_type}}
}
func New{{go_full_name}}(_buf []map[string]interface{}) (*{{go_full_name}}, error) {
_dataList := make([]{{go_define_type value_type}}, 0, len(_buf))
dataMap := make(map[{{go_define_type key_type}}]{{go_define_type value_type}})
for _, _ele_ := range _buf {
if _v, err2 := {{go_deserialize_type value_type '_ele_'}}; err2 != nil {
return nil, err2
} else {
_dataList = append(_dataList, _v)
{{~if value_type.is_dynamic ~}}
{{~for child in value_type.bean.hierarchy_not_abstract_children~}}
if __v, __is := _v.(*{{child.go_full_name}}) ; __is {
dataMap[__v.{{index_field.cs_style_name}}] = _v
continue
}
{{~end~}}
{{~else~}}
dataMap[_v.{{index_field.cs_style_name}}] = _v
{{~end~}}
}
}
return &{{go_full_name}}{_dataList:_dataList, _dataMap:dataMap}, nil
}
func (table *{{go_full_name}}) GetDataMap() map[{{go_define_type key_type}}]{{go_define_type value_type}} {
return table._dataMap
}
func (table *{{go_full_name}}) GetDataList() []{{go_define_type value_type}} {
return table._dataList
}
func (table *{{go_full_name}}) Get(key {{go_define_type key_type}}) {{go_define_type value_type}} {
return table._dataMap[key]
}
{{~else~}}
import ""errors""
type {{go_full_name}} struct {
_data {{go_define_type value_type}}
}
func New{{go_full_name}}(_buf []map[string]interface{}) (*{{go_full_name}}, error) {
if len(_buf) != 1 {
return nil, errors.New("" size != 1 "")
} else {
if _v, err2 := {{go_deserialize_type value_type '_buf'}}; err2 != nil {
return nil, err2
} else {
return &{{go_full_name}}{_data:_v}, nil
}
}
}
func (table *{{go_full_name}}) Get() {{go_define_type value_type}} {
return table._data
}
{{~end~}}
");
var result = template.RenderCode(p, new Dictionary<string, object>() { ["package"] = package });
return result;
}
[ThreadStatic]
private static Template t_serviceRender;
public override string RenderService(string name, string module, List<DefTable> tables)
{
string package = "cfg";
var template = t_serviceRender ??= Template.Parse(@"
package {{package}}
type JsonLoader func(string) ([]map[string]interface{}, error)
type {{name}} struct {
{{~for table in tables ~}}
{{table.name}} *{{table.go_full_name}}
{{~end~}}
}
func NewTables(loader JsonLoader) (*{{name}}, error) {
var err error
var buf []map[string]interface{}
tables := &{{name}}{}
{{~for table in tables ~}}
if buf, err = loader(""{{table.json_output_data_file}}"") ; err != nil {
return nil, err
}
if tables.{{table.name}}, err = New{{table.go_full_name}}(buf) ; err != nil {
return nil, err
}
{{~end~}}
return tables, nil
}
");
var result = template.Render(new
{
Name = name,
Namespace = module,
Tables = tables,
Package = package,
});
return result;
}
}
}

View File

@ -300,8 +300,9 @@ namespace Luban.Job.Cfg
break; break;
} }
case "code_go_bin": case "code_go_bin":
case "code_go_json":
{ {
var render = new GoCodeRender(); GoCodeRenderBase render = genType == "code_go_bin" ? new GoBinCodeRender() : new GoJsonCodeRender();
foreach (var c in exportTypes) foreach (var c in exportTypes)
{ {
tasks.Add(Task.Run(() => tasks.Add(Task.Run(() =>

View File

@ -3,151 +3,20 @@ using Luban.Job.Common.TypeVisitors;
namespace Luban.Job.Cfg.TypeVisitors namespace Luban.Job.Cfg.TypeVisitors
{ {
class GoDeserializeVisitor : ITypeFuncVisitor<string, string> class GoDeserializeVisitor : DecoratorFuncVisitor<string, string, string>
{ {
public static GoDeserializeVisitor Ins { get; } = new GoDeserializeVisitor(); public static GoDeserializeVisitor Ins { get; } = new GoDeserializeVisitor();
public string Accept(TBool type, string bufName) public override string DoAccept(TType type, string fieldName, string bufName)
{ {
return $"{bufName}.ReadBool()"; if (type.IsNullable)
}
public string Accept(TByte type, string bufName)
{ {
return $"{bufName}.ReadByte()"; return $"{{ var __exists__ bool; if __exists__, err = {bufName}.ReadBool(); err != nil {{ return }}; if __exists__ {{ var __x__ {type.Apply(GoTypeUnderingNameVisitor.Ins)}; {type.Apply(GoUnderingDeserializeVisitor.Ins, "__x__", bufName)}; {fieldName} = {(type.Apply(IsGoPointerTypeVisitor.Ins) ? "&" : "")}__x__ }}}}";
} }
else
public string Accept(TShort type, string bufName)
{ {
return $"{bufName}.ReadShort()"; return type.Apply(GoUnderingDeserializeVisitor.Ins, (string)fieldName, bufName);
} }
public string Accept(TFshort type, string bufName)
{
return $"{bufName}.ReadFshort()";
}
public string Accept(TInt type, string bufName)
{
return $"{bufName}.ReadInt()";
}
public string Accept(TFint type, string bufName)
{
return $"{bufName}.ReadFint()";
}
public string Accept(TLong type, string bufName)
{
return $"{bufName}.ReadLong()";
}
public string Accept(TFlong type, string bufName)
{
return $"{bufName}.ReadFlong()";
}
public string Accept(TFloat type, string bufName)
{
return $"{bufName}.ReadFloat()";
}
public string Accept(TDouble type, string bufName)
{
return $"{bufName}.ReadDouble()";
}
public string Accept(TEnum type, string bufName)
{
return $"{bufName}.ReadInt()";
}
public string Accept(TString type, string bufName)
{
return $"{bufName}.ReadString()";
}
public string Accept(TBytes type, string bufName)
{
return $"{bufName}.ReadBytes()";
}
public string Accept(TText type, string bufName)
{
return $"{bufName}.ReadString()";
}
public string Accept(TBean type, string bufName)
{
return type.Bean.IsAbstractType ? $"NewChild{type.Bean.GoFullName}({bufName})" : $"New{ type.Bean.GoFullName} ({ bufName})";
}
private string GenList(TType elementType, string bufName)
{
return $@"func (_buf2 *serialization.ByteBuf) (_v2 []{elementType.Apply(GoTypeNameVisitor.Ins)}, err2 error) {{
_v2 = make([]{elementType.Apply(GoTypeNameVisitor.Ins)}, 0)
var n int
if n, err2 = _buf2.ReadSize(); err2 != nil {{return}}
for i := 0 ; i < n ; i++ {{
var v3 {elementType.Apply(GoTypeNameVisitor.Ins)}
if v3, err2 = {elementType.Apply(this, "_buf2")}; err2 != nil {{return}}
_v2 = append(_v2, v3)
}}
return
}}({bufName})";
}
public string Accept(TArray type, string bufName)
{
return GenList(type.ElementType, bufName);
}
public string Accept(TList type, string bufName)
{
return GenList(type.ElementType, bufName);
}
public string Accept(TSet type, string bufName)
{
return GenList(type.ElementType, bufName);
}
public string Accept(TMap type, string bufName)
{
return $@"func (_buf2 *serialization.ByteBuf) (_v2 {type.Apply(GoTypeNameVisitor.Ins)}, err2 error) {{
_v2 = make({type.Apply(GoTypeNameVisitor.Ins)})
var n int
if n, err2 = _buf2.ReadSize(); err2 != nil {{return}}
for i := 0 ; i < n ; i++ {{
var _key {type.KeyType.Apply(GoTypeNameVisitor.Ins)}
if _key, err2 = {type.KeyType.Apply(this, "_buf2")}; err2 != nil {{return}}
var _value {type.ValueType.Apply(GoTypeNameVisitor.Ins)}
if _value, err2 = {type.ValueType.Apply(this, "_buf2")}; err2 != nil {{return}}
_v2[_key] = _value
}}
return
}}({bufName})";
}
public string Accept(TVector2 type, string bufName)
{
return $"{bufName}.ReadVector2()";
}
public string Accept(TVector3 type, string bufName)
{
return $"{bufName}.ReadVector3()";
}
public string Accept(TVector4 type, string bufName)
{
return $"{bufName}.ReadVector4()";
}
public string Accept(TDateTime type, string bufName)
{
return $"{bufName}.ReadInt()";
} }
} }
} }

View File

@ -3,123 +3,14 @@ using Luban.Job.Common.TypeVisitors;
namespace Luban.Job.Cfg.TypeVisitors namespace Luban.Job.Cfg.TypeVisitors
{ {
class GoTypeNameVisitor : ITypeFuncVisitor<string> class GoTypeNameVisitor : DecoratorFuncVisitor<string>
{ {
public static GoTypeNameVisitor Ins { get; } = new GoTypeNameVisitor(); public static GoTypeNameVisitor Ins { get; } = new GoTypeNameVisitor();
public string Accept(TBool type) public override string DoAccept(TType type)
{ {
return "bool"; var s = type.Apply(GoTypeUnderingNameVisitor.Ins);
} return type.Apply(IsGoPointerTypeVisitor.Ins) ? "*" + s : s;
public string Accept(TByte type)
{
return "byte";
}
public string Accept(TShort type)
{
return "int16";
}
public string Accept(TFshort type)
{
return "int16";
}
public string Accept(TInt type)
{
return "int32";
}
public string Accept(TFint type)
{
return "int32";
}
public string Accept(TLong type)
{
return "int64";
}
public string Accept(TFlong type)
{
return "int64";
}
public string Accept(TFloat type)
{
return "float32";
}
public string Accept(TDouble type)
{
return "float64";
}
public string Accept(TEnum type)
{
return "int32";
}
public string Accept(TString type)
{
return "string";
}
public string Accept(TBytes type)
{
return "[]byte";
}
public string Accept(TText type)
{
return "string";
}
public string Accept(TBean type)
{
return type.Bean.IsAbstractType ? $"interface{{}}" : $"*{type.Bean.GoFullName}";
}
public string Accept(TArray type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TList type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TSet type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TMap type)
{
return $"map[{type.KeyType.Apply(this)}]{type.ValueType.Apply(this)}";
}
public string Accept(TVector2 type)
{
return $"math.Vector2";
}
public string Accept(TVector3 type)
{
return $"math.Vector3";
}
public string Accept(TVector4 type)
{
return $"math.Vector4";
}
public string Accept(TDateTime type)
{
return "int32";
} }
} }
} }

View File

@ -0,0 +1,125 @@
using Luban.Job.Common.Types;
using Luban.Job.Common.TypeVisitors;
namespace Luban.Job.Cfg.TypeVisitors
{
class GoTypeUnderingNameVisitor : ITypeFuncVisitor<string>
{
public static GoTypeUnderingNameVisitor Ins { get; } = new GoTypeUnderingNameVisitor();
public string Accept(TBool type)
{
return "bool";
}
public string Accept(TByte type)
{
return "byte";
}
public string Accept(TShort type)
{
return "int16";
}
public string Accept(TFshort type)
{
return "int16";
}
public string Accept(TInt type)
{
return "int32";
}
public string Accept(TFint type)
{
return "int32";
}
public string Accept(TLong type)
{
return "int64";
}
public string Accept(TFlong type)
{
return "int64";
}
public string Accept(TFloat type)
{
return "float32";
}
public string Accept(TDouble type)
{
return "float64";
}
public string Accept(TEnum type)
{
return "int32";
}
public string Accept(TString type)
{
return "string";
}
public string Accept(TBytes type)
{
return "[]byte";
}
public string Accept(TText type)
{
return "string";
}
public string Accept(TBean type)
{
return type.Bean.IsAbstractType ? $"interface{{}}" : $"*{type.Bean.GoFullName}";
}
public string Accept(TArray type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TList type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TSet type)
{
return $"[]{type.ElementType.Apply(this)}";
}
public string Accept(TMap type)
{
return $"map[{type.KeyType.Apply(this)}]{type.ValueType.Apply(this)}";
}
public string Accept(TVector2 type)
{
return $"math.Vector2";
}
public string Accept(TVector3 type)
{
return $"math.Vector3";
}
public string Accept(TVector4 type)
{
return $"math.Vector4";
}
public string Accept(TDateTime type)
{
return "int32";
}
}
}

View File

@ -0,0 +1,153 @@
using Luban.Job.Common.Types;
using Luban.Job.Common.TypeVisitors;
namespace Luban.Job.Cfg.TypeVisitors
{
class GoUnderingDeserializeVisitor : ITypeFuncVisitor<string, string, string>
{
public static GoUnderingDeserializeVisitor Ins { get; } = new GoUnderingDeserializeVisitor();
public string Accept(TBool type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadBool(); err != nil {{ return }} }}";
}
public string Accept(TByte type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadByte(); err != nil {{ return }} }}";
}
public string Accept(TShort type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadShort(); err != nil {{ return }} }}";
}
public string Accept(TFshort type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadFshort(); err != nil {{ return }} }}";
}
public string Accept(TInt type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadInt(); err != nil {{ return }} }}";
}
public string Accept(TFint type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadFint(); err != nil {{ return }} }}";
}
public string Accept(TLong type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadLong(); err != nil {{ return }} }}";
}
public string Accept(TFlong type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadFlong(); err != nil {{ return }} }}";
}
public string Accept(TFloat type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadFloat(); err != nil {{ return }} }}";
}
public string Accept(TDouble type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadDouble(); err != nil {{ return }} }}";
}
public string Accept(TEnum type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadInt(); err != nil {{ return }} }}";
}
public string Accept(TString type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadString(); err != nil {{ return }} }}";
}
public string Accept(TBytes type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadBytes(); err != nil {{ return }} }}";
}
public string Accept(TText type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadString(); err != nil {{ return }} }}";
}
public string Accept(TBean type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {(type.Bean.IsAbstractType ? $"NewChild{type.Bean.GoFullName}({bufName})" : $"New{ type.Bean.GoFullName} ({ bufName})")}; err != nil {{ return }} }}";
//return type.Bean.IsAbstractType ? $"NewChild{type.Bean.GoFullName}({bufName})" : $"New{ type.Bean.GoFullName} ({ bufName})";
}
private string GenList(TType elementType, string fieldName, string bufName)
{
return $@" {{
{fieldName} = make([]{elementType.Apply(GoTypeNameVisitor.Ins)}, 0)
var _n_ int
if _n_, err = {bufName}.ReadSize(); err != nil {{return}}
for i := 0 ; i < _n_ ; i++ {{
var _e_ {elementType.Apply(GoTypeNameVisitor.Ins)}
{elementType.Apply(GoDeserializeVisitor.Ins, "_e_", bufName)}
{fieldName} = append({fieldName}, _e_)
}}
}}
";
}
public string Accept(TArray type, string fieldName, string bufName)
{
return GenList(type.ElementType, fieldName, bufName);
}
public string Accept(TList type, string fieldName, string bufName)
{
return GenList(type.ElementType, fieldName, bufName);
}
public string Accept(TSet type, string fieldName, string bufName)
{
return GenList(type.ElementType, fieldName, bufName);
}
public string Accept(TMap type, string fieldName, string bufName)
{
return $@"{{
{fieldName} = make({type.Apply(GoTypeNameVisitor.Ins)})
var _n_ int
if _n_, err = {bufName}.ReadSize(); err != nil {{return}}
for i := 0 ; i < _n_ ; i++ {{
var _key_ {type.KeyType.Apply(GoTypeNameVisitor.Ins)}
{type.KeyType.Apply(GoDeserializeVisitor.Ins, "_key_", bufName)}
var _value_ {type.ValueType.Apply(GoTypeNameVisitor.Ins)}
{type.ValueType.Apply(GoDeserializeVisitor.Ins, "_value_", bufName)}
{fieldName}[_key_] = _value_
}}
}}";
}
public string Accept(TVector2 type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadVector2(); err != nil {{ return }} }}";
}
public string Accept(TVector3 type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadVector3(); err != nil {{ return }} }}";
}
public string Accept(TVector4 type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadVector4(); err != nil {{ return }} }}";
}
public string Accept(TDateTime type, string fieldName, string bufName)
{
return $"{{ if {fieldName}, err = {bufName}.ReadInt(); err != nil {{ return }} }}";
}
}
}

View File

@ -0,0 +1,50 @@
using Luban.Job.Common.Types;
using Luban.Job.Common.TypeVisitors;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace Luban.Job.Cfg.TypeVisitors
{
class IsGoPointerTypeVisitor : DecoratorFuncVisitor<bool>
{
public static IsGoPointerTypeVisitor Ins { get; } = new();
public override bool DoAccept(TType type)
{
return type.IsNullable;
}
public override bool Accept(TBytes type)
{
return false;
}
public override bool Accept(TBean type)
{
return false;
}
public override bool Accept(TArray type)
{
return false;
}
public override bool Accept(TList type)
{
return false;
}
public override bool Accept(TSet type)
{
return false;
}
public override bool Accept(TMap type)
{
return false;
}
}
}

View File

@ -57,6 +57,10 @@ namespace Luban.Job.Common.Defs
public string PyStyleName => Name; public string PyStyleName => Name;
public string GoStyleName => CsStyleName;
//public string GoStyleAssignName => CType.IsNullable ? "*" + CsStyleName : CsStyleName;
public string Type { get; } public string Type { get; }
public TType CType { get; protected set; } public TType CType { get; protected set; }