【重构】【cfg】 略微重构 typescript语言生成代码,多态类的构造函数名由 deserialize改为 constructorFrom,语义更清楚
【修复】【cfg】 修复 typescript 生成代码能编译但未能正确导出定义类的bug 【特性】【proto】 对于使用puerts框架的unity项目,支持生成 typescript的消息代码。测试通过。main
parent
5868f9bd0a
commit
ca8104aa33
|
|
@ -57,6 +57,11 @@ namespace Luban.Common.Utils
|
||||||
return string.Join("", module.Split('.').Select(n => $"{n}_")) + ueName;
|
return string.Join("", module.Split('.').Select(n => $"{n}_")) + ueName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static string MakeTypescriptNamespaceBegin(string module)
|
||||||
|
{
|
||||||
|
return string.Join("", module.Split('.').Select(n => $"export namespace {n} {{"));
|
||||||
|
}
|
||||||
|
|
||||||
public static string MakeFullName(string module, string name)
|
public static string MakeFullName(string module, string name)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrEmpty(module))
|
if (string.IsNullOrEmpty(module))
|
||||||
|
|
|
||||||
|
|
@ -98,9 +98,14 @@ namespace Luban.Job.Cfg.Defs
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static string TsDeserialize(string fieldName, string jsonFieldName, TType type)
|
public static string TsJsonConstructor(string fieldName, string jsonFieldName, TType type)
|
||||||
{
|
{
|
||||||
return type.Apply(TypescriptDeserializeVisitor.Ins, $"{jsonFieldName}", fieldName);
|
return type.Apply(TypescriptJsonConstructorVisitor.Ins, $"{jsonFieldName}", fieldName);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static string TsBinConstructor(string fieldName, string byteBufName, TType type)
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinConstructorVisitor.Ins, $"{byteBufName}", fieldName);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static string TsRecursiveResolve(DefField field, string tables)
|
public static string TsRecursiveResolve(DefField field, string tables)
|
||||||
|
|
@ -124,11 +129,6 @@ namespace Luban.Job.Cfg.Defs
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static string TsDeserializeBin(string fieldName, string byteBufName, TType type)
|
|
||||||
{
|
|
||||||
return type.Apply(TypescriptDeserializeBinVisitor.Ins, byteBufName, fieldName);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static string Py3Deserialize(string fieldName, string jsonFieldName, TType type)
|
public static string Py3Deserialize(string fieldName, string jsonFieldName, TType type)
|
||||||
{
|
{
|
||||||
return type.Apply(PyDeserializeVisitor.Py3Ins, $"{jsonFieldName}", fieldName);
|
return type.Apply(PyDeserializeVisitor.Py3Ins, $"{jsonFieldName}", fieldName);
|
||||||
|
|
|
||||||
|
|
@ -1,14 +1,23 @@
|
||||||
using Luban.Job.Cfg.Defs;
|
using Luban.Job.Cfg.Defs;
|
||||||
using Luban.Job.Common.Defs;
|
using Luban.Job.Common.Defs;
|
||||||
|
using Luban.Job.Common.Utils;
|
||||||
using Scriban;
|
using Scriban;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.Generate
|
namespace Luban.Job.Cfg.Generate
|
||||||
{
|
{
|
||||||
class TypeScriptBinCodeRender : TypescriptCodeRenderBase
|
class TypeScriptBinCodeRender : CodeRenderBase
|
||||||
{
|
{
|
||||||
|
public override string Render(DefConst c)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptConstClass(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Render(DefEnum e)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptEnumClass(e);
|
||||||
|
}
|
||||||
|
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
private static Template t_beanRender;
|
private static Template t_beanRender;
|
||||||
|
|
@ -23,11 +32,11 @@ namespace Luban.Job.Cfg.Generate
|
||||||
hierarchy_export_fields = x.hierarchy_export_fields
|
hierarchy_export_fields = x.hierarchy_export_fields
|
||||||
}}
|
}}
|
||||||
|
|
||||||
namespace {{x.namespace}} {
|
{{x.typescript_namespace_begin}}
|
||||||
|
|
||||||
export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def_type}} extends {{x.parent}}{{end}} {
|
export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def_type}} extends {{x.parent}}{{end}} {
|
||||||
{{~if x.is_abstract_type~}}
|
{{~if x.is_abstract_type~}}
|
||||||
static deserialize(_buf_ : Bright.Serialization.ByteBuf) : {{name}} {
|
static constructorFrom(_buf_ : Bright.Serialization.ByteBuf) : {{name}} {
|
||||||
switch (_buf_.ReadInt())
|
switch (_buf_.ReadInt())
|
||||||
{
|
{
|
||||||
case 0 : return null;
|
case 0 : return null;
|
||||||
|
|
@ -44,7 +53,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
super(_buf_);
|
super(_buf_);
|
||||||
{{~end~}}
|
{{~end~}}
|
||||||
{{~ for field in export_fields ~}}
|
{{~ for field in export_fields ~}}
|
||||||
{{ts_deserialize_bin ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
{{ts_bin_constructor ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
||||||
{{~end~}}
|
{{~end~}}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -69,7 +78,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
{{x.typescript_namespace_end}}
|
||||||
");
|
");
|
||||||
var result = template.RenderCode(b);
|
var result = template.RenderCode(b);
|
||||||
|
|
||||||
|
|
@ -88,7 +97,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
key_type2 = x.key_ttype2
|
key_type2 = x.key_ttype2
|
||||||
value_type = x.value_ttype
|
value_type = x.value_ttype
|
||||||
}}
|
}}
|
||||||
namespace {{x.namespace}} {
|
{{x.typescript_namespace_begin}}
|
||||||
export class {{name}}{
|
export class {{name}}{
|
||||||
{{~ if x.is_two_key_map_table ~}}
|
{{~ if x.is_two_key_map_table ~}}
|
||||||
private _dataListMap : Map<{{ts_define_type key_type1}}, {{ts_define_type value_type}}[]>;
|
private _dataListMap : Map<{{ts_define_type key_type1}}, {{ts_define_type value_type}}[]>;
|
||||||
|
|
@ -102,7 +111,7 @@ export class {{name}}{
|
||||||
|
|
||||||
for(let n = _buf_.ReadInt(); n > 0 ; n--) {
|
for(let n = _buf_.ReadInt(); n > 0 ; n--) {
|
||||||
let _v : {{ts_define_type value_type}};
|
let _v : {{ts_define_type value_type}};
|
||||||
{{ts_deserialize_bin '_v' '_buf_' value_type}}
|
{{ts_bin_constructor '_v' '_buf_' value_type}}
|
||||||
this._dataList.push(_v);
|
this._dataList.push(_v);
|
||||||
var _key = _v.{{x.index_field1.ts_style_name}};
|
var _key = _v.{{x.index_field1.ts_style_name}};
|
||||||
let list : {{ts_define_type value_type}}[] = this._dataListMap.get(_key);
|
let list : {{ts_define_type value_type}}[] = this._dataListMap.get(_key);
|
||||||
|
|
@ -142,7 +151,7 @@ export class {{name}}{
|
||||||
|
|
||||||
for(let n = _buf_.ReadInt() ; n > 0 ; n--) {
|
for(let n = _buf_.ReadInt() ; n > 0 ; n--) {
|
||||||
let _v : {{ts_define_type value_type}};
|
let _v : {{ts_define_type value_type}};
|
||||||
{{ts_deserialize_bin '_v' '_buf_' value_type}}
|
{{ts_bin_constructor '_v' '_buf_' value_type}}
|
||||||
this._dataList.push(_v);
|
this._dataList.push(_v);
|
||||||
this._dataMap.set(_v.{{x.index_field.ts_style_name}}, _v);
|
this._dataMap.set(_v.{{x.index_field.ts_style_name}}, _v);
|
||||||
}
|
}
|
||||||
|
|
@ -165,7 +174,7 @@ export class {{name}}{
|
||||||
|
|
||||||
constructor(_buf_ : Bright.Serialization.ByteBuf) {
|
constructor(_buf_ : Bright.Serialization.ByteBuf) {
|
||||||
if (_buf_.ReadInt() != 1) throw new Error('table mode=one, but size != 1');
|
if (_buf_.ReadInt() != 1) throw new Error('table mode=one, but size != 1');
|
||||||
{{ts_deserialize_bin 'this._data' '_buf_' value_type}}
|
{{ts_bin_constructor 'this._data' '_buf_' value_type}}
|
||||||
}
|
}
|
||||||
|
|
||||||
getData() : {{ts_define_type value_type}} { return this._data; }
|
getData() : {{ts_define_type value_type}} { return this._data; }
|
||||||
|
|
@ -180,7 +189,7 @@ export class {{name}}{
|
||||||
|
|
||||||
{{end}}
|
{{end}}
|
||||||
}
|
}
|
||||||
}
|
{{x.typescript_namespace_end}}
|
||||||
");
|
");
|
||||||
var result = template.RenderCode(p);
|
var result = template.RenderCode(p);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,13 +1,24 @@
|
||||||
using Luban.Job.Cfg.Defs;
|
using Luban.Job.Cfg.Defs;
|
||||||
using Luban.Job.Common.Defs;
|
using Luban.Job.Common.Defs;
|
||||||
|
using Luban.Job.Common.Utils;
|
||||||
using Scriban;
|
using Scriban;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.Generate
|
namespace Luban.Job.Cfg.Generate
|
||||||
{
|
{
|
||||||
class TypeScriptJsonCodeRender : TypescriptCodeRenderBase
|
class TypeScriptJsonCodeRender : CodeRenderBase
|
||||||
{
|
{
|
||||||
|
public override string Render(DefConst c)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptConstClass(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Render(DefEnum e)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptEnumClass(e);
|
||||||
|
}
|
||||||
|
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
private static Template t_beanRender;
|
private static Template t_beanRender;
|
||||||
public override string Render(DefBean b)
|
public override string Render(DefBean b)
|
||||||
|
|
@ -21,11 +32,11 @@ namespace Luban.Job.Cfg.Generate
|
||||||
hierarchy_export_fields = x.hierarchy_export_fields
|
hierarchy_export_fields = x.hierarchy_export_fields
|
||||||
}}
|
}}
|
||||||
|
|
||||||
namespace {{x.namespace}} {
|
{{x.typescript_namespace_begin}}
|
||||||
|
|
||||||
export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def_type}} extends {{x.parent}}{{end}} {
|
export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def_type}} extends {{x.parent}}{{end}} {
|
||||||
{{~if x.is_abstract_type~}}
|
{{~if x.is_abstract_type~}}
|
||||||
static deserialize(_json_ : any) : {{name}} {
|
static constructorFrom(_json_ : any) : {{name}} {
|
||||||
switch (_json_.__type__) {
|
switch (_json_.__type__) {
|
||||||
case null : return null;
|
case null : return null;
|
||||||
{{~ for child in x.hierarchy_not_abstract_children~}}
|
{{~ for child in x.hierarchy_not_abstract_children~}}
|
||||||
|
|
@ -44,7 +55,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
{{~if !field.ctype.is_nullable~}}
|
{{~if !field.ctype.is_nullable~}}
|
||||||
if (_json_.{{field.name}} == null) { throw new Error(); }
|
if (_json_.{{field.name}} == null) { throw new Error(); }
|
||||||
{{~end~}}
|
{{~end~}}
|
||||||
{{ts_deserialize ('this.' + field.ts_style_name) ( '_json_.' + field.name) field.ctype}}
|
{{ts_json_constructor ('this.' + field.ts_style_name) ( '_json_.' + field.name) field.ctype}}
|
||||||
{{~end~}}
|
{{~end~}}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -69,7 +80,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
{{x.typescript_namespace_end}}
|
||||||
");
|
");
|
||||||
var result = template.RenderCode(b);
|
var result = template.RenderCode(b);
|
||||||
|
|
||||||
|
|
@ -88,7 +99,7 @@ export {{if x.is_abstract_type}} abstract {{end}} class {{name}} {{if parent_def
|
||||||
key_type2 = x.key_ttype2
|
key_type2 = x.key_ttype2
|
||||||
value_type = x.value_ttype
|
value_type = x.value_ttype
|
||||||
}}
|
}}
|
||||||
namespace {{x.namespace}} {
|
{{x.typescript_namespace_begin}}
|
||||||
export class {{name}}{
|
export class {{name}}{
|
||||||
{{~ if x.is_two_key_map_table ~}}
|
{{~ if x.is_two_key_map_table ~}}
|
||||||
private _dataListMap : Map<{{ts_define_type key_type1}}, {{ts_define_type value_type}}[]>;
|
private _dataListMap : Map<{{ts_define_type key_type1}}, {{ts_define_type value_type}}[]>;
|
||||||
|
|
@ -102,7 +113,7 @@ export class {{name}}{
|
||||||
|
|
||||||
for(var _json2_ of _json_) {
|
for(var _json2_ of _json_) {
|
||||||
let _v : {{ts_define_type value_type}};
|
let _v : {{ts_define_type value_type}};
|
||||||
{{ts_deserialize '_v' '_json2_' value_type}}
|
{{ts_json_constructor '_v' '_json2_' value_type}}
|
||||||
this._dataList.push(_v);
|
this._dataList.push(_v);
|
||||||
var _key = _v.{{x.index_field1.ts_style_name}};
|
var _key = _v.{{x.index_field1.ts_style_name}};
|
||||||
let list : {{ts_define_type value_type}}[] = this._dataListMap.get(_key);
|
let list : {{ts_define_type value_type}}[] = this._dataListMap.get(_key);
|
||||||
|
|
@ -142,7 +153,7 @@ export class {{name}}{
|
||||||
|
|
||||||
for(var _json2_ of _json_) {
|
for(var _json2_ of _json_) {
|
||||||
let _v : {{ts_define_type value_type}};
|
let _v : {{ts_define_type value_type}};
|
||||||
{{ts_deserialize '_v' '_json2_' value_type}}
|
{{ts_json_constructor '_v' '_json2_' value_type}}
|
||||||
this._dataList.push(_v);
|
this._dataList.push(_v);
|
||||||
this._dataMap.set(_v.{{x.index_field.ts_style_name}}, _v);
|
this._dataMap.set(_v.{{x.index_field.ts_style_name}}, _v);
|
||||||
}
|
}
|
||||||
|
|
@ -165,7 +176,7 @@ export class {{name}}{
|
||||||
|
|
||||||
constructor(_json_ : any) {
|
constructor(_json_ : any) {
|
||||||
if (_json_.length != 1) throw new Error('table mode=one, but size != 1');
|
if (_json_.length != 1) throw new Error('table mode=one, but size != 1');
|
||||||
{{ts_deserialize 'this._data' '_json_[0]' value_type}}
|
{{ts_json_constructor 'this._data' '_json_[0]' value_type}}
|
||||||
}
|
}
|
||||||
|
|
||||||
getData() : {{ts_define_type value_type}} { return this._data; }
|
getData() : {{ts_define_type value_type}} { return this._data; }
|
||||||
|
|
@ -180,7 +191,7 @@ export class {{name}}{
|
||||||
|
|
||||||
{{end}}
|
{{end}}
|
||||||
}
|
}
|
||||||
}
|
{{x.typescript_namespace_end}}
|
||||||
");
|
");
|
||||||
var result = template.RenderCode(p);
|
var result = template.RenderCode(p);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,59 +0,0 @@
|
||||||
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 TypescriptCodeRenderBase : CodeRenderBase
|
|
||||||
{
|
|
||||||
[ThreadStatic]
|
|
||||||
private static Template t_tsConstRender;
|
|
||||||
public override string Render(DefConst c)
|
|
||||||
{
|
|
||||||
var ctx = new TemplateContext();
|
|
||||||
var env = new TTypeTemplateCommonExtends
|
|
||||||
{
|
|
||||||
["x"] = c
|
|
||||||
};
|
|
||||||
ctx.PushGlobal(env);
|
|
||||||
|
|
||||||
|
|
||||||
var template = t_tsConstRender ??= Template.Parse(@"
|
|
||||||
namespace {{x.namespace}} {
|
|
||||||
export class {{x.name}} {
|
|
||||||
{{~ for item in x.items ~}}
|
|
||||||
static {{item.name}} = {{ts_const_value item.ctype item.value}};
|
|
||||||
{{~end~}}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
");
|
|
||||||
var result = template.Render(ctx);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
[ThreadStatic]
|
|
||||||
private static Template t_tsEnumRender;
|
|
||||||
public override string Render(DefEnum e)
|
|
||||||
{
|
|
||||||
var template = t_tsEnumRender ??= Template.Parse(@"
|
|
||||||
namespace {{namespace}} {
|
|
||||||
export enum {{name}} {
|
|
||||||
{{- for item in items }}
|
|
||||||
{{item.name}} = {{item.value}},
|
|
||||||
{{-end}}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
");
|
|
||||||
var result = template.Render(e);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
using Luban.Job.Common.Types;
|
||||||
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
|
{
|
||||||
|
class TypescriptBinConstructorVisitor : DecoratorFuncVisitor<string, string, string>
|
||||||
|
{
|
||||||
|
public static TypescriptBinConstructorVisitor Ins { get; } = new TypescriptBinConstructorVisitor();
|
||||||
|
|
||||||
|
public override string DoAccept(TType type, string byteBufName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.IsNullable)
|
||||||
|
{
|
||||||
|
return $"if({byteBufName}.ReadBool()) {{ {type.Apply(TypescriptBinUnderingConstructorVisitor.Ins, byteBufName, fieldName)} }} else {{ {fieldName} = null; }}";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinUnderingConstructorVisitor.Ins, byteBufName, fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO 设计需要简化,现在造成多态bean的可空与其他字段类型不一样,而需要单独处理
|
||||||
|
// 多态bean不浪费一个字段,直接用typeid==0表示空
|
||||||
|
// 因此不跟普通字段一样,需要 ReadBool()来区别是否为空
|
||||||
|
public override string Accept(TBean type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinUnderingConstructorVisitor.Ins, bufName, fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,22 @@
|
||||||
|
using Luban.Job.Common.Types;
|
||||||
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
|
{
|
||||||
|
class TypescriptBinUnderingConstructorVisitor : TypescriptBinUnderingDeserializeVisitorBase
|
||||||
|
{
|
||||||
|
public static TypescriptBinUnderingConstructorVisitor Ins { get; } = new TypescriptBinUnderingConstructorVisitor();
|
||||||
|
|
||||||
|
public override string Accept(TBean type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.Bean.IsAbstractType)
|
||||||
|
{
|
||||||
|
return $"{fieldName} = {type.Bean.FullName}.constructorFrom({bufVarName});";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return $"{fieldName} = new {type.Bean.FullName}({bufVarName});";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,27 +0,0 @@
|
||||||
using Luban.Job.Common.Types;
|
|
||||||
using Luban.Job.Common.TypeVisitors;
|
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.TypeVisitors
|
|
||||||
{
|
|
||||||
class TypescriptDeserializeVisitor : DecoratorFuncVisitor<string, string, string>
|
|
||||||
{
|
|
||||||
public static TypescriptDeserializeVisitor Ins { get; } = new TypescriptDeserializeVisitor();
|
|
||||||
|
|
||||||
public override string DoAccept(TType type, string jsonFieldName, string fieldName)
|
|
||||||
{
|
|
||||||
if (type.IsNullable)
|
|
||||||
{
|
|
||||||
return $"if({jsonFieldName} != null) {{ {type.Apply(TypescriptUnderingDeserializeVisitor.Ins, jsonFieldName, fieldName)} }} else {{ {fieldName} = null; }}";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return type.Apply(TypescriptUnderingDeserializeVisitor.Ins, jsonFieldName, fieldName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public override string Accept(TBean type, string bufName, string fieldName)
|
|
||||||
{
|
|
||||||
return type.Apply(TypescriptUnderingDeserializeVisitor.Ins, bufName, fieldName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -0,0 +1,27 @@
|
||||||
|
using Luban.Job.Common.Types;
|
||||||
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
|
namespace Luban.Job.Cfg.TypeVisitors
|
||||||
|
{
|
||||||
|
class TypescriptJsonConstructorVisitor : DecoratorFuncVisitor<string, string, string>
|
||||||
|
{
|
||||||
|
public static TypescriptJsonConstructorVisitor Ins { get; } = new TypescriptJsonConstructorVisitor();
|
||||||
|
|
||||||
|
public override string DoAccept(TType type, string jsonFieldName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.IsNullable)
|
||||||
|
{
|
||||||
|
return $"if({jsonFieldName} != null) {{ {type.Apply(TypescriptJsonUnderingConstructorVisitor.Ins, jsonFieldName, fieldName)} }} else {{ {fieldName} = null; }}";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptJsonUnderingConstructorVisitor.Ins, jsonFieldName, fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//public override string Accept(TBean type, string bytebufName, string fieldName)
|
||||||
|
//{
|
||||||
|
// return type.Apply(TypescriptJsonUnderingConstructorVisitor.Ins, bytebufName, fieldName);
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -3,9 +3,9 @@ using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.TypeVisitors
|
namespace Luban.Job.Cfg.TypeVisitors
|
||||||
{
|
{
|
||||||
class TypescriptUnderingDeserializeVisitor : ITypeFuncVisitor<string, string, string>
|
class TypescriptJsonUnderingConstructorVisitor : ITypeFuncVisitor<string, string, string>
|
||||||
{
|
{
|
||||||
public static TypescriptUnderingDeserializeVisitor Ins { get; } = new TypescriptUnderingDeserializeVisitor();
|
public static TypescriptJsonUnderingConstructorVisitor Ins { get; } = new TypescriptJsonUnderingConstructorVisitor();
|
||||||
|
|
||||||
public string Accept(TBool type, string jsonVarName, string fieldName)
|
public string Accept(TBool type, string jsonVarName, string fieldName)
|
||||||
{
|
{
|
||||||
|
|
@ -81,7 +81,7 @@ namespace Luban.Job.Cfg.TypeVisitors
|
||||||
{
|
{
|
||||||
if (type.Bean.IsAbstractType)
|
if (type.Bean.IsAbstractType)
|
||||||
{
|
{
|
||||||
return $"{fieldName} = {type.Bean.FullName}.deserialize({jsonVarName});";
|
return $"{fieldName} = {type.Bean.FullName}.constructorFrom({jsonVarName});";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
@ -33,6 +33,9 @@ namespace Luban.Job.Common.Defs
|
||||||
|
|
||||||
public string CppFullNameWithTopModule => TypeUtil.MakeCppFullName(AssemblyBase.TopModule, FullName);
|
public string CppFullNameWithTopModule => TypeUtil.MakeCppFullName(AssemblyBase.TopModule, FullName);
|
||||||
|
|
||||||
|
public string TypescriptNamespaceBegin => TypeUtil.MakeTypescriptNamespaceBegin(Namespace);
|
||||||
|
|
||||||
|
public string TypescriptNamespaceEnd => TypeUtil.MakeCppNamespaceEnd(Namespace);
|
||||||
|
|
||||||
public string CppFullName => TypeUtil.MakeCppFullName(Namespace, Name);
|
public string CppFullName => TypeUtil.MakeCppFullName(Namespace, Name);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -138,6 +138,16 @@ namespace Luban.Job.Common.Defs
|
||||||
return type.Apply(LuaConstValueVisitor.Ins, value);
|
return type.Apply(LuaConstValueVisitor.Ins, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static string TsBinSerialize(string fieldName, string byteBufName, TType type)
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinSerializeVisitor.Ins, byteBufName, fieldName);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static string TsBinDeserialize(string fieldName, string byteBufName, TType type)
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinDeserializeVisitor.Ins, byteBufName, fieldName);
|
||||||
|
}
|
||||||
|
|
||||||
public static string PyDefineType(TType type)
|
public static string PyDefineType(TType type)
|
||||||
{
|
{
|
||||||
return type.Apply(PyDefineTypeName.Ins);
|
return type.Apply(PyDefineTypeName.Ins);
|
||||||
|
|
|
||||||
|
|
@ -1,27 +1,27 @@
|
||||||
using Luban.Job.Common.Types;
|
using Luban.Job.Common.Types;
|
||||||
using Luban.Job.Common.TypeVisitors;
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.TypeVisitors
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
{
|
{
|
||||||
class TypescriptDeserializeBinVisitor : DecoratorFuncVisitor<string, string, string>
|
class TypescriptBinDeserializeVisitor : DecoratorFuncVisitor<string, string, string>
|
||||||
{
|
{
|
||||||
public static TypescriptDeserializeBinVisitor Ins { get; } = new TypescriptDeserializeBinVisitor();
|
public static TypescriptBinDeserializeVisitor Ins { get; } = new TypescriptBinDeserializeVisitor();
|
||||||
|
|
||||||
public override string DoAccept(TType type, string byteBufName, string fieldName)
|
public override string DoAccept(TType type, string byteBufName, string fieldName)
|
||||||
{
|
{
|
||||||
if (type.IsNullable)
|
if (type.IsNullable)
|
||||||
{
|
{
|
||||||
return $"if({byteBufName}.ReadBool()) {{ {type.Apply(TypescriptUnderingDeserializeBinVisitor.Ins, byteBufName, fieldName)} }} else {{ {fieldName} = null; }}";
|
return $"if({byteBufName}.ReadBool()) {{ {type.Apply(TypescriptBinUnderingDeserializeVisitor.Ins, byteBufName, fieldName)} }} else {{ {fieldName} = null; }}";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
return type.Apply(TypescriptUnderingDeserializeBinVisitor.Ins, byteBufName, fieldName);
|
return type.Apply(TypescriptBinUnderingDeserializeVisitor.Ins, byteBufName, fieldName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public override string Accept(TBean type, string bufName, string fieldName)
|
public override string Accept(TBean type, string bufName, string fieldName)
|
||||||
{
|
{
|
||||||
return type.Apply(TypescriptUnderingDeserializeBinVisitor.Ins, bufName, fieldName);
|
return type.Apply(TypescriptBinUnderingDeserializeVisitor.Ins, bufName, fieldName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -0,0 +1,31 @@
|
||||||
|
using Luban.Job.Common.Types;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
|
{
|
||||||
|
class TypescriptBinSerializeVisitor : DecoratorFuncVisitor<string, string, string>
|
||||||
|
{
|
||||||
|
public static TypescriptBinSerializeVisitor Ins { get; } = new TypescriptBinSerializeVisitor();
|
||||||
|
|
||||||
|
public override string DoAccept(TType type, string bytebufName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.IsNullable)
|
||||||
|
{
|
||||||
|
return $"if({bytebufName}.ReadBool()) {{{type.Apply(TypescriptBinUnderingSerializeVisitor.Ins, bytebufName, fieldName)} }} else {{ {fieldName} = null; }}";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinUnderingSerializeVisitor.Ins, bytebufName, fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Accept(TBean type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return type.Apply(TypescriptBinUnderingSerializeVisitor.Ins, bufName, fieldName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,22 @@
|
||||||
|
using Luban.Job.Common.Types;
|
||||||
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
|
{
|
||||||
|
public class TypescriptBinUnderingDeserializeVisitor : TypescriptBinUnderingDeserializeVisitorBase
|
||||||
|
{
|
||||||
|
public static TypescriptBinUnderingDeserializeVisitor Ins { get; } = new TypescriptBinUnderingDeserializeVisitor();
|
||||||
|
|
||||||
|
public override string Accept(TBean type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.Bean.IsAbstractType)
|
||||||
|
{
|
||||||
|
return $"{fieldName} = {type.Bean.FullName}.deserializeFrom({bufVarName});";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return $"{fieldName} = new {type.Bean.FullName}(); {fieldName}.deserialize({bufVarName});";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,12 +1,10 @@
|
||||||
using Luban.Job.Common.Types;
|
using Luban.Job.Common.Types;
|
||||||
using Luban.Job.Common.TypeVisitors;
|
using Luban.Job.Common.TypeVisitors;
|
||||||
|
|
||||||
namespace Luban.Job.Cfg.TypeVisitors
|
namespace Luban.Job.Common.TypeVisitors
|
||||||
{
|
{
|
||||||
class TypescriptUnderingDeserializeBinVisitor : ITypeFuncVisitor<string, string, string>
|
public abstract class TypescriptBinUnderingDeserializeVisitorBase : ITypeFuncVisitor<string, string, string>
|
||||||
{
|
{
|
||||||
public static TypescriptUnderingDeserializeBinVisitor Ins { get; } = new TypescriptUnderingDeserializeBinVisitor();
|
|
||||||
|
|
||||||
public string Accept(TBool type, string bufName, string fieldName)
|
public string Accept(TBool type, string bufName, string fieldName)
|
||||||
{
|
{
|
||||||
return $"{fieldName} = {bufName}.ReadBool();";
|
return $"{fieldName} = {bufName}.ReadBool();";
|
||||||
|
|
@ -69,7 +67,7 @@ namespace Luban.Job.Cfg.TypeVisitors
|
||||||
|
|
||||||
public string Accept(TBytes type, string bufName, string fieldName)
|
public string Accept(TBytes type, string bufName, string fieldName)
|
||||||
{
|
{
|
||||||
return $"{fieldName} = {bufName}.ReadArrayBuf();";
|
return $"{fieldName} = new Uint8Array({bufName}.ReadArrayBuffer());";
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Accept(TText type, string bufName, string fieldName)
|
public string Accept(TText type, string bufName, string fieldName)
|
||||||
|
|
@ -77,17 +75,17 @@ namespace Luban.Job.Cfg.TypeVisitors
|
||||||
return $"{fieldName} = {bufName}.ReadString();";
|
return $"{fieldName} = {bufName}.ReadString();";
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Accept(TBean type, string bufVarName, string fieldName)
|
public abstract string Accept(TBean type, string bufVarName, string fieldName);
|
||||||
{
|
//{
|
||||||
if (type.Bean.IsAbstractType)
|
// if (type.Bean.IsAbstractType)
|
||||||
{
|
// {
|
||||||
return $"{fieldName} = {type.Bean.FullName}.deserialize({bufVarName});";
|
// return $"{fieldName} = {type.Bean.FullName}.deserialize({bufVarName});";
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
return $"{fieldName} = new {type.Bean.FullName}({bufVarName});";
|
// return $"{fieldName} = new {type.Bean.FullName}({bufVarName});";
|
||||||
}
|
// }
|
||||||
}
|
//}
|
||||||
|
|
||||||
private string GetNewArray(TArray arrayType, string size)
|
private string GetNewArray(TArray arrayType, string size)
|
||||||
{
|
{
|
||||||
|
|
@ -0,0 +1,171 @@
|
||||||
|
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.Common.TypeVisitors
|
||||||
|
{
|
||||||
|
class TypescriptBinUnderingSerializeVisitor : ITypeFuncVisitor<string, string, string>
|
||||||
|
{
|
||||||
|
public static TypescriptBinUnderingSerializeVisitor Ins { get; } = new TypescriptBinUnderingSerializeVisitor();
|
||||||
|
|
||||||
|
public string Accept(TBool type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteBool({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TByte type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteByte({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TShort type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteShort({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TFshort type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteFshort({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TInt type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteInt({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TFint type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteFint({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TLong type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteLong({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TFlong type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteFlong({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TFloat type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteFloat({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TDouble type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteDouble({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TEnum type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteInt({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TString type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteString({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TBytes type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteArrayBuffer({fieldName}.buffer);";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TText type, string bufName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufName}.WriteString({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TVector2 type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{fieldName}.to({bufVarName})";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TVector3 type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{fieldName}.to({bufVarName})";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TVector4 type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{fieldName}.to({bufVarName})";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TDateTime type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{bufVarName}.WriteInt({fieldName});";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TBean type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
if (type.Bean.IsAbstractType)
|
||||||
|
{
|
||||||
|
return $"{type.Bean.FullName}.serializeTo({bufVarName}, {fieldName});";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return $"{fieldName}.serialize({bufVarName});";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string GetNewArray(TArray arrayType, string size)
|
||||||
|
{
|
||||||
|
switch (arrayType.ElementType)
|
||||||
|
{
|
||||||
|
case TByte _: return $"new Uint8Array({size})";
|
||||||
|
case TShort _:
|
||||||
|
case TFshort _: return $"new Int16Array({size})";
|
||||||
|
case TInt _:
|
||||||
|
case TFint _: return $"new Int32Array({size})";
|
||||||
|
case TLong _:
|
||||||
|
case TFlong _: return $"new Int64Array({size})";
|
||||||
|
case TFloat _: return $"new Float32Array({size})";
|
||||||
|
case TDouble _: return $"new Float64Array({size})";
|
||||||
|
default: return "[]";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static bool IsRawArrayElementType(TType elementType)
|
||||||
|
{
|
||||||
|
switch (elementType)
|
||||||
|
{
|
||||||
|
case TByte _:
|
||||||
|
case TShort _:
|
||||||
|
case TFshort _:
|
||||||
|
case TInt _:
|
||||||
|
case TFint _:
|
||||||
|
case TLong _:
|
||||||
|
case TFlong _:
|
||||||
|
case TFloat _:
|
||||||
|
case TDouble _: return true;
|
||||||
|
default: return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TArray type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{{ {bufVarName}.WriteSize({fieldName}.length); for(let _e of {fieldName}) {{ {type.ElementType.Apply(this, bufVarName, "_e")} }} }}";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TList type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{{ {bufVarName}.WriteSize({fieldName}.length); for(let _e of {fieldName}) {{ {type.ElementType.Apply(this, bufVarName, "_e")} }} }}";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TSet type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{{ {bufVarName}.WriteSize({fieldName}.size); for(let _e of {fieldName}) {{ {type.ElementType.Apply(this, bufVarName, "_e")} }} }}";
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Accept(TMap type, string bufVarName, string fieldName)
|
||||||
|
{
|
||||||
|
return $"{{ {bufVarName}.WriteSize({fieldName}.size); for(let [_k, _v] of {fieldName}) {{ {type.KeyType.Apply(this, bufVarName, "_k")} {type.ValueType.Apply(this, bufVarName, "_v")} }} }}";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -177,11 +177,9 @@ enum class {{name}}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
private static Template t_tsConstRender;
|
private static Template t_tsConstRender;
|
||||||
public static string RenderTsConstClass(DefConst c)
|
public static string RenderTypescriptConstClass(DefConst c)
|
||||||
{
|
{
|
||||||
var ctx = new TemplateContext();
|
var ctx = new TemplateContext();
|
||||||
var env = new TTypeTemplateCommonExtends
|
var env = new TTypeTemplateCommonExtends
|
||||||
|
|
@ -192,15 +190,14 @@ enum class {{name}}
|
||||||
|
|
||||||
|
|
||||||
var template = t_tsConstRender ??= Template.Parse(@"
|
var template = t_tsConstRender ??= Template.Parse(@"
|
||||||
namespace {{x.namespace_with_top_module}}
|
{{typescript_namespace_begin}}
|
||||||
{
|
|
||||||
export class {{x.name}}
|
export class {{x.name}} {
|
||||||
{
|
|
||||||
{{~ for item in x.items ~}}
|
{{~ for item in x.items ~}}
|
||||||
static {{item.name}} : {{ts_define_type item.ctype}} = {{ts_const_value item.ctype item.value}};
|
static {{item.name}} = {{ts_const_value item.ctype item.value}};
|
||||||
{{~end~}}
|
{{~end~}}
|
||||||
}
|
}
|
||||||
}
|
{{typescript_namespace_end}}
|
||||||
|
|
||||||
");
|
");
|
||||||
var result = template.Render(ctx);
|
var result = template.Render(ctx);
|
||||||
|
|
@ -210,20 +207,17 @@ namespace {{x.namespace_with_top_module}}
|
||||||
|
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
private static Template t_tsEnumRender;
|
private static Template t_tsEnumRender;
|
||||||
public static string RenderTsEnumClass(DefEnum e)
|
public static string RenderTypescriptEnumClass(DefEnum e)
|
||||||
{
|
{
|
||||||
var template = t_tsEnumRender ??= Template.Parse(@"
|
var template = t_tsEnumRender ??= Template.Parse(@"
|
||||||
namespace {{namespace_with_top_module}}
|
{{typescript_namespace_begin}}
|
||||||
{
|
|
||||||
export enum {{name}}
|
export enum {{name}} {
|
||||||
{
|
|
||||||
{{- for item in items }}
|
{{- for item in items }}
|
||||||
{{item.name}} = {{item.value}},
|
{{item.name}} = {{item.value}},
|
||||||
{{-end}}
|
{{-end}}
|
||||||
}
|
}
|
||||||
}
|
{{typescript_namespace_end}}
|
||||||
|
|
||||||
|
|
||||||
");
|
");
|
||||||
var result = template.Render(e);
|
var result = template.Render(e);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,231 @@
|
||||||
|
using Luban.Job.Common.Defs;
|
||||||
|
using Luban.Job.Common.Utils;
|
||||||
|
using Luban.Job.Proto.Defs;
|
||||||
|
using Scriban;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace Luban.Job.Proto.Generate
|
||||||
|
{
|
||||||
|
class TypescriptRender
|
||||||
|
{
|
||||||
|
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 DefProto p: return Render(p);
|
||||||
|
case DefRpc r: return Render(r);
|
||||||
|
|
||||||
|
default: throw new Exception($"unknown render type:{o}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private string Render(DefConst c)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptConstClass(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
private string Render(DefEnum e)
|
||||||
|
{
|
||||||
|
return RenderUtil.RenderTypescriptEnumClass(e);
|
||||||
|
}
|
||||||
|
|
||||||
|
[ThreadStatic]
|
||||||
|
private static Template t_beanRender;
|
||||||
|
private string Render(DefBean b)
|
||||||
|
{
|
||||||
|
var template = t_beanRender ??= Template.Parse(@"
|
||||||
|
{{
|
||||||
|
is_value_type = x.is_value_type
|
||||||
|
is_abstract_type = x.is_abstract_type
|
||||||
|
name = x.name
|
||||||
|
full_name = x.full_name
|
||||||
|
parent_def_type = x.parent_def_type
|
||||||
|
parent = x.parent
|
||||||
|
fields = x.fields
|
||||||
|
hierarchy_fields = x.hierarchy_fields
|
||||||
|
}}
|
||||||
|
|
||||||
|
|
||||||
|
{{x.typescript_namespace_begin}}
|
||||||
|
|
||||||
|
export {{if x.is_abstract_type}} abstract {{end}} class {{name}} extends {{if parent_def_type}}{{x.parent}}{{else}}BeanBase{{end}} {
|
||||||
|
{{~if x.is_abstract_type~}}
|
||||||
|
static serializeTo(_buf_ : Bright.Serialization.ByteBuf, _bean_ : {{name}}) : void {
|
||||||
|
if (_bean_ == null) {
|
||||||
|
_buf_.WriteInt(0)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
_buf_.WriteInt(_bean_.getTypeId())
|
||||||
|
_bean_.serialize(_buf_)
|
||||||
|
}
|
||||||
|
|
||||||
|
static deserializeFrom(_buf_ : Bright.Serialization.ByteBuf) : {{name}} {
|
||||||
|
let _bean_ :{{name}}
|
||||||
|
switch (_buf_.ReadInt()) {
|
||||||
|
case 0 : return null;
|
||||||
|
{{~ for child in x.hierarchy_not_abstract_children~}}
|
||||||
|
case {{child.id}}: _bean_ = new {{child.full_name}}(_buf_); break;
|
||||||
|
{{~end~}}
|
||||||
|
default: throw new Error();
|
||||||
|
}
|
||||||
|
_bean_.deserialize(_buf_)
|
||||||
|
return _bean_
|
||||||
|
}
|
||||||
|
{{else}}
|
||||||
|
static readonly ID = {{x.id}}
|
||||||
|
getTypeId() { return {{name}}.ID }
|
||||||
|
{{~end~}}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{field.ts_style_name}}{{if field.is_nullable}}?{{end}} : {{ts_define_type field.ctype}};
|
||||||
|
{{~end~}}
|
||||||
|
|
||||||
|
serialize(_buf_ : Bright.Serialization.ByteBuf) {
|
||||||
|
{{~if parent_def_type~}}
|
||||||
|
super.serialize(_buf_);
|
||||||
|
{{~end~}}
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{ts_bin_serialize ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
||||||
|
{{~end~}}
|
||||||
|
}
|
||||||
|
|
||||||
|
deserialize(_buf_ : Bright.Serialization.ByteBuf) {
|
||||||
|
{{~if parent_def_type~}}
|
||||||
|
super.deserialize(_buf_);
|
||||||
|
{{~end~}}
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{ts_bin_deserialize ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
||||||
|
{{~end~}}
|
||||||
|
}
|
||||||
|
|
||||||
|
toString(): string {
|
||||||
|
return ""{{full_name}}{ ""
|
||||||
|
{{~ for field in hierarchy_fields ~}}
|
||||||
|
+ ""{{field.ts_style_name}}:"" + this.{{field.ts_style_name}} + "",""
|
||||||
|
{{~end~}}
|
||||||
|
+ ""}"";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
{{x.typescript_namespace_end}}
|
||||||
|
");
|
||||||
|
var result = template.RenderCode(b);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
[ThreadStatic]
|
||||||
|
private static Template t_protoRender;
|
||||||
|
private string Render(DefProto p)
|
||||||
|
{
|
||||||
|
var template = t_protoRender ??= Template.Parse(@"
|
||||||
|
{{
|
||||||
|
name = x.name
|
||||||
|
full_name = x.full_name
|
||||||
|
parent = x.parent
|
||||||
|
fields = x.fields
|
||||||
|
}}
|
||||||
|
{{x.typescript_namespace_begin}}
|
||||||
|
|
||||||
|
export class {{name}} extends Protocol {
|
||||||
|
static readonly ID = {{x.id}}
|
||||||
|
getTypeId() { return {{name}}.ID }
|
||||||
|
|
||||||
|
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{field.ts_style_name}}{{if field.is_nullable}}?{{end}} : {{ts_define_type field.ctype}};
|
||||||
|
{{~end~}}
|
||||||
|
|
||||||
|
serialize(_buf_ : Bright.Serialization.ByteBuf) {
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{ts_bin_serialize ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
||||||
|
{{~end~}}
|
||||||
|
}
|
||||||
|
|
||||||
|
deserialize(_buf_ : Bright.Serialization.ByteBuf) {
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
{{ts_bin_deserialize ('this.' + field.ts_style_name) '_buf_' field.ctype}}
|
||||||
|
{{~end~}}
|
||||||
|
}
|
||||||
|
|
||||||
|
toString(): string {
|
||||||
|
return ""{{full_name}}{ ""
|
||||||
|
{{~ for field in fields ~}}
|
||||||
|
+ ""{{field.ts_style_name}}:"" + this.{{field.ts_style_name}} + "",""
|
||||||
|
{{~end~}}
|
||||||
|
+ ""}"";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
{{x.typescript_namespace_end}}
|
||||||
|
");
|
||||||
|
var result = template.RenderCode(p);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
[ThreadStatic]
|
||||||
|
private static Template t_rpcRender;
|
||||||
|
private string Render(DefRpc r)
|
||||||
|
{
|
||||||
|
var template = t_rpcRender ??= Template.Parse(@"
|
||||||
|
{{
|
||||||
|
name = x.name
|
||||||
|
full_name = x.full_name
|
||||||
|
parent = x.parent
|
||||||
|
fields = x.fields
|
||||||
|
targ_type = x.targ_type
|
||||||
|
tres_type = x.tres_type
|
||||||
|
}}
|
||||||
|
|
||||||
|
// TODO {{full_name}}
|
||||||
|
|
||||||
|
");
|
||||||
|
var result = template.RenderCode(r);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
[ThreadStatic]
|
||||||
|
private static Template t_stubRender;
|
||||||
|
public string RenderStubs(string name, string module, List<DefTypeBase> protos, List<DefTypeBase> rpcs)
|
||||||
|
{
|
||||||
|
var template = t_stubRender ??= Template.Parse(@"
|
||||||
|
|
||||||
|
type ProtocolFactory = () => Protocol
|
||||||
|
|
||||||
|
export class {{name}} {
|
||||||
|
static readonly Factories = new Map<number, ProtocolFactory>([
|
||||||
|
|
||||||
|
{{~ for proto in protos ~}}
|
||||||
|
[{{proto.full_name}}.ID, () => new {{proto.full_name}}()],
|
||||||
|
{{~end~}}
|
||||||
|
|
||||||
|
{{~ for rpc in rpcs ~}}
|
||||||
|
// TODO RPC .. [{{rpc.full_name}}.ID] = () => new {{rpc.full_name}}(),
|
||||||
|
{{~end~}}
|
||||||
|
])
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
");
|
||||||
|
var result = template.Render(new
|
||||||
|
{
|
||||||
|
Name = name,
|
||||||
|
Namespace = module,
|
||||||
|
Protos = protos,
|
||||||
|
Rpcs = rpcs,
|
||||||
|
});
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
using CommandLine;
|
using CommandLine;
|
||||||
using Luban.Common.Protos;
|
using Luban.Common.Protos;
|
||||||
using Luban.Common.Utils;
|
using Luban.Common.Utils;
|
||||||
|
using Luban.Job.Common;
|
||||||
using Luban.Job.Common.Defs;
|
using Luban.Job.Common.Defs;
|
||||||
using Luban.Job.Common.Utils;
|
using Luban.Job.Common.Utils;
|
||||||
using Luban.Job.Proto.Defs;
|
using Luban.Job.Proto.Defs;
|
||||||
|
|
@ -30,7 +31,7 @@ namespace Luban.Job.Proto
|
||||||
[Option('c', "output_code_dir", Required = true, HelpText = "output code directory")]
|
[Option('c', "output_code_dir", Required = true, HelpText = "output code directory")]
|
||||||
public string OutputCodeDir { get; set; }
|
public string OutputCodeDir { get; set; }
|
||||||
|
|
||||||
[Option('g', "gen_type", Required = true, HelpText = "cs,lua,java,cpp")]
|
[Option('g', "gen_type", Required = true, HelpText = "cs,lua,java,cpp,ts")]
|
||||||
public string GenType { get; set; }
|
public string GenType { get; set; }
|
||||||
|
|
||||||
[Option('s', "service", Required = true, HelpText = "service")]
|
[Option('s', "service", Required = true, HelpText = "service")]
|
||||||
|
|
@ -145,6 +146,132 @@ namespace Luban.Job.Proto
|
||||||
}));
|
}));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case "ts":
|
||||||
|
{
|
||||||
|
var render = new TypescriptRender();
|
||||||
|
|
||||||
|
tasks.Add(Task.Run(() =>
|
||||||
|
{
|
||||||
|
var fileContent = new List<string>
|
||||||
|
{
|
||||||
|
@$"
|
||||||
|
import {{Bright}} from 'csharp'
|
||||||
|
|
||||||
|
export namespace {ass.TopModule} {{
|
||||||
|
",
|
||||||
|
|
||||||
|
@"
|
||||||
|
export interface ISerializable {
|
||||||
|
serialize(_buf_: Bright.Serialization.ByteBuf) : void
|
||||||
|
deserialize(_buf_: Bright.Serialization.ByteBuf) : void
|
||||||
|
}
|
||||||
|
|
||||||
|
export abstract class BeanBase implements ISerializable {
|
||||||
|
abstract getTypeId() : number
|
||||||
|
abstract serialize(_buf_: Bright.Serialization.ByteBuf): void
|
||||||
|
abstract deserialize(_buf_: Bright.Serialization.ByteBuf): void
|
||||||
|
}
|
||||||
|
|
||||||
|
export abstract class Protocol implements ISerializable {
|
||||||
|
abstract getTypeId() : number
|
||||||
|
abstract serialize(_buf_: Bright.Serialization.ByteBuf): void
|
||||||
|
abstract deserialize(_buf_: Bright.Serialization.ByteBuf): void
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Vector2 {
|
||||||
|
x: number;
|
||||||
|
y: number;
|
||||||
|
constructor(x: number, y: number) {
|
||||||
|
this.x = x;
|
||||||
|
this.y = y;
|
||||||
|
}
|
||||||
|
|
||||||
|
to(_buf_: Bright.Serialization.ByteBuf) {
|
||||||
|
_buf_.WriteFloat(this.x)
|
||||||
|
_buf_.WriteFloat(this.y)
|
||||||
|
}
|
||||||
|
|
||||||
|
static from(_buf_: Bright.Serialization.ByteBuf): Vector2 {
|
||||||
|
let x = _buf_.ReadFloat();
|
||||||
|
let y = _buf_.ReadFloat();
|
||||||
|
return new Vector2(x, y);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
export class Vector3 {
|
||||||
|
x: number;
|
||||||
|
y: number;
|
||||||
|
z: number;
|
||||||
|
constructor(x: number, y: number, z: number) {
|
||||||
|
this.x = x;
|
||||||
|
this.y = y;
|
||||||
|
this.z = z;
|
||||||
|
}
|
||||||
|
|
||||||
|
to(_buf_: Bright.Serialization.ByteBuf) {
|
||||||
|
_buf_.WriteFloat(this.x)
|
||||||
|
_buf_.WriteFloat(this.y)
|
||||||
|
_buf_.WriteFloat(this.z)
|
||||||
|
}
|
||||||
|
|
||||||
|
static from(_buf_: Bright.Serialization.ByteBuf): Vector3 {
|
||||||
|
let x = _buf_.ReadFloat();
|
||||||
|
let y = _buf_.ReadFloat();
|
||||||
|
let z = _buf_.ReadFloat();
|
||||||
|
return new Vector3(x, y, z);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Vector4 {
|
||||||
|
x: number;
|
||||||
|
y: number;
|
||||||
|
z: number;
|
||||||
|
w: number;
|
||||||
|
constructor(x: number, y: number, z: number, w: number) {
|
||||||
|
this.x = x;
|
||||||
|
this.y = y;
|
||||||
|
this.z = z;
|
||||||
|
this.w = w;
|
||||||
|
}
|
||||||
|
|
||||||
|
to(_buf_: Bright.Serialization.ByteBuf) {
|
||||||
|
_buf_.WriteFloat(this.x)
|
||||||
|
_buf_.WriteFloat(this.y)
|
||||||
|
_buf_.WriteFloat(this.z)
|
||||||
|
_buf_.WriteFloat(this.w)
|
||||||
|
}
|
||||||
|
|
||||||
|
static from(_buf_: Bright.Serialization.ByteBuf): Vector4 {
|
||||||
|
let x = _buf_.ReadFloat();
|
||||||
|
let y = _buf_.ReadFloat();
|
||||||
|
let z = _buf_.ReadFloat();
|
||||||
|
let w = _buf_.ReadFloat();
|
||||||
|
return new Vector4(x, y, z, w);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
"
|
||||||
|
};
|
||||||
|
|
||||||
|
foreach (var type in exportTypes)
|
||||||
|
{
|
||||||
|
fileContent.Add(render.RenderAny(type));
|
||||||
|
}
|
||||||
|
|
||||||
|
fileContent.Add(render.RenderStubs("ProtocolStub", ass.TopModule, ass.Types.Values.Where(t => t is DefProto).ToList(),
|
||||||
|
ass.Types.Values.Where(t => t is DefRpc).ToList()));
|
||||||
|
|
||||||
|
fileContent.Add("}"); // end of topmodule
|
||||||
|
|
||||||
|
var content = FileHeaderUtil.ConcatAutoGenerationHeader(string.Join('\n', fileContent), ELanguage.TYPESCRIPT);
|
||||||
|
var file = "Types.ts";
|
||||||
|
var md5 = CacheFileUtil.GenMd5AndAddCache(file, content);
|
||||||
|
genCodeFiles.Add(new FileInfo() { FilePath = file, MD5 = md5 });
|
||||||
|
}));
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
{
|
{
|
||||||
throw new NotSupportedException($"not support gen type:{genType}");
|
throw new NotSupportedException($"not support gen type:{genType}");
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue