【重构】validator重构

main
walon 2021-10-25 20:41:41 +08:00
parent 79d684dca4
commit 60bbcbbbf8
18 changed files with 316 additions and 482 deletions

View File

@ -1,13 +1,15 @@
using Luban.Common.Utils; using Luban.Common.Utils;
using Luban.Job.Cfg.Datas; using Luban.Job.Cfg.Datas;
using Luban.Job.Cfg.Defs; using Luban.Job.Cfg.Defs;
using Luban.Job.Cfg.Validators;
using Luban.Job.Common.Types; using Luban.Job.Common.Types;
using Luban.Job.Common.TypeVisitors;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
namespace Luban.Job.Cfg.DataVisitors namespace Luban.Job.Cfg.DataVisitors
{ {
public class ValidatorVisitor : IDataActionVisitor<DefAssembly> public class ValidatorVisitor : ITypeActionVisitor<DType>
{ {
private readonly Stack<object> _path = new Stack<object>(); private readonly Stack<object> _path = new Stack<object>();
@ -24,7 +26,6 @@ namespace Luban.Job.Cfg.DataVisitors
public void ValidateTable(DefTable table, List<Record> records) public void ValidateTable(DefTable table, List<Record> records)
{ {
DefAssembly ass = table.Assembly;
var keyIndex = table.IndexFieldIdIndex; var keyIndex = table.IndexFieldIdIndex;
foreach (Record r in records) foreach (Record r in records)
@ -37,285 +38,212 @@ namespace Luban.Job.Cfg.DataVisitors
{ {
_path.Push(data.Fields[keyIndex]); _path.Push(data.Fields[keyIndex]);
} }
Accept(data, ass); if (table.ValueTType.Processors.Count > 0)
{
foreach (var p in table.ValueTType.Processors)
{
if (p is IValidator v)
{
v.Validate(Ctx, table.ValueTType, data);
}
}
}
table.ValueTType.Apply(this, data);
} }
} }
public void Accept(DBool type, DefAssembly x) private void AcceptListLike(TType elementType, List<DType> eles)
{ {
throw new NotImplementedException(); if (elementType.Processors.Count > 0)
{
int index = 0;
foreach (var value in eles)
{
_path.Push(index++);
foreach (var v in elementType.Processors)
{
if (v is IValidator eleVal)
{
eleVal.Validate(Ctx, elementType, value);
if (value != null)
{
elementType.Apply(this, value);
}
}
}
_path.Pop();
}
}
} }
public void Accept(DByte type, DefAssembly x) public void Accept(TBool type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DShort type, DefAssembly x) public void Accept(TByte type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DFshort type, DefAssembly x) public void Accept(TShort type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DInt type, DefAssembly x) public void Accept(TFshort type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DFint type, DefAssembly x) public void Accept(TInt type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DLong type, DefAssembly x) public void Accept(TFint type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DFlong type, DefAssembly x) public void Accept(TLong type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DFloat type, DefAssembly x) public void Accept(TFlong type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DDouble type, DefAssembly x) public void Accept(TFloat type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DEnum type, DefAssembly x) public void Accept(TDouble type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DString type, DefAssembly x) public void Accept(TEnum type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DBytes type, DefAssembly x) public void Accept(TString type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DText type, DefAssembly x) public void Accept(TBytes type, DType x)
{ {
throw new NotImplementedException();
} }
public void Accept(DBean record, DefAssembly assembly) public void Accept(TText type, DType x)
{ {
if (record == null)
{
return;
} }
var defFields = record.ImplType.HierarchyFields;
public void Accept(TBean type, DType x)
{
var beanData = (DBean)x;
var defFields = ((DefBean)type.Bean.AssemblyBase.GetDefType(beanData.ImplType.FullName)).HierarchyFields;// beanData.ImplType.HierarchyFields;
int i = 0; int i = 0;
foreach (var fieldValue in record.Fields) foreach (var fieldValue in beanData.Fields)
{ {
var defField = (DefField)defFields[i++]; var defField = (DefField)defFields[i++];
_path.Push(defField.Name); _path.Push(defField.Name);
switch (defField.CType)
var fieldType = defField.CType;
if (fieldType.Processors.Count > 0)
{ {
case TArray a: foreach (var p in fieldType.Processors)
{ {
if (defField.ValueValidators.Count > 0) if (p is IValidator val)
{ {
var arr = (DArray)fieldValue; val.Validate(Ctx, fieldType, fieldValue);
int index = 0; }
foreach (var value in arr.Datas) }
{ }
_path.Push(index++); if (fieldValue != null)
foreach (var v in defField.ValueValidators) {
{ fieldType.Apply(this, fieldValue);
v.Validate(Ctx, value, defField.IsNullable); }
} }
_path.Pop();
} }
} public void Accept(TArray type, DType x)
if (a.ElementType is TBean)
{ {
var arr = (DArray)fieldValue; AcceptListLike(type.ElementType, ((DArray)x).Datas);
int index = 0;
foreach (var value in arr.Datas)
{
_path.Push(index++);
Accept((DBean)value, assembly);
_path.Pop();
} }
} public void Accept(TList type, DType x)
break;
}
case TList b:
{ {
if (defField.ValueValidators.Count > 0) AcceptListLike(type.ElementType, ((DList)x).Datas);
{
var arr = (DList)fieldValue;
int index = 0;
foreach (var value in arr.Datas)
{
_path.Push(index++);
foreach (var v in defField.ValueValidators)
{
v.Validate(Ctx, value, false);
}
_path.Pop();
} }
} public void Accept(TSet type, DType x)
if (b.ElementType is TBean tb)
{ {
var arr = (DList)fieldValue; AcceptListLike(type.ElementType, ((DSet)x).Datas);
int index = 0;
foreach (var value in arr.Datas)
{
_path.Push(index++);
Accept((DBean)value, assembly);
_path.Pop();
} }
public void Accept(TMap type, DType x)
if (defField.IndexField != null)
{ {
var indexSet = new HashSet<DType>(); var keyType = type.KeyType;
if (!tb.GetBeanAs<DefBean>().TryGetField(defField.Index, out var _, out var indexOfIndexField)) var valueType = type.ValueType;
if (keyType.Processors.Count > 0 || valueType.Processors.Count > 0)
{ {
throw new Exception("impossible"); foreach (var e in ((DMap)x).Datas)
{
_path.Push(e.Key);
if (keyType.Processors.Count > 0)
{
foreach (var v in keyType.Processors)
{
if (v is IValidator eleVal)
{
eleVal.Validate(Ctx, keyType, e.Key);
keyType.Apply(this, e.Key);
} }
foreach (var value in arr.Datas) }
}
if (valueType.Processors.Count > 0)
{ {
_path.Push(index++); foreach (var v in valueType.Processors)
DType indexValue = ((DBean)value).Fields[indexOfIndexField];
if (!indexSet.Add(indexValue))
{ {
throw new Exception($"'{TypeUtil.MakeFullName(_path)}' index:'{indexValue}' 重复"); if (v is IValidator eleVal)
{
eleVal.Validate(Ctx, valueType, e.Value);
valueType.Apply(this, e.Value);
}
}
} }
_path.Pop(); _path.Pop();
} }
} }
} }
break;
} public void Accept(TVector2 type, DType x)
case TSet c:
{ {
if (defField.ValueValidators.Count > 0)
{
var arr = (DSet)fieldValue;
foreach (var value in arr.Datas)
{
foreach (var v in defField.ValueValidators)
{
v.Validate(Ctx, value, false);
}
}
} }
break;
public void Accept(TVector3 type, DType x)
{
} }
case TMap m: public void Accept(TVector4 type, DType x)
{ {
DMap map = (DMap)fieldValue;
if (defField.KeyValidators.Count > 0)
{
foreach (var key in map.Datas.Keys)
{
_path.Push(key);
foreach (var v in defField.KeyValidators)
{
v.Validate(Ctx, key, false);
}
_path.Pop();
}
}
if (defField.ValueValidators.Count > 0)
{
foreach (var value in map.Datas.Values)
{
_path.Push(value);
foreach (var v in defField.ValueValidators)
{
v.Validate(Ctx, value, false);
} }
if (value is DBean dv) public void Accept(TDateTime type, DType x)
{ {
Accept(dv, assembly);
}
_path.Pop();
}
}
break;
}
case TBean n:
{
Accept((DBean)fieldValue, assembly);
break;
}
default:
{
if (defField.Validators.Count > 0)
{
foreach (var v in defField.Validators)
{
v.Validate(Ctx, fieldValue, defField.IsNullable);
}
}
break;
}
}
_path.Pop();
}
}
public void Accept(DArray type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DList type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DSet type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DMap type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DVector2 type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DVector3 type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DVector4 type, DefAssembly x)
{
throw new NotImplementedException();
}
public void Accept(DDateTime type, DefAssembly x)
{
throw new NotImplementedException();
} }
} }
} }

View File

@ -70,49 +70,14 @@ namespace Luban.Job.Cfg.Defs
{ {
get get
{ {
//var imports = new HashSet<CfgDefTypeBase>();
//if (ParentDefType != null)
//{
// imports.Add(ParentDefType);
//}
//foreach (var f in Fields)
//{
// f.CType.Apply(CollectEditorCppHeaderIncludeVisitor.Ins, imports);
//}
//imports.Remove(this);
//return string.Join('\n', imports.Select(im => $"#include \"{im.UeBpHeaderFileName}\""));
throw new NotImplementedException(); throw new NotImplementedException();
} }
} }
//public string UeForwards
//{
// get
// {
// var imports = new HashSet<IDefType>();
// foreach (var f in Fields)
// {
// f.CType.Apply(CollectUeCppForwardDefineVisitor.Ins, imports);
// }
// return string.Join('\n', imports.Select(im => $"{im.CppNamespaceBegin} class {im.UeBpName}; {im.CppNamespaceEnd}"));
// }
//}
public string EditorCppIncludes public string EditorCppIncludes
{ {
get get
{ {
//var imports = new HashSet<CfgDefTypeBase>();
//if (ParentDefType != null)
//{
// imports.Add(ParentDefType);
//}
//foreach (var f in Fields)
//{
// f.CType.Apply(CollectEditorCppHeaderIncludeVisitor.Ins, imports);
//}
//imports.Remove(this);
//return string.Join('\n', imports.Select(im => $"#include \"{im.UeEditorHeaderFileName}\""));
throw new NotImplementedException(); throw new NotImplementedException();
} }
} }
@ -126,7 +91,6 @@ namespace Luban.Job.Cfg.Defs
{ {
f.CType.Apply(CollectEditorCppForwardDefineVisitor.Ins, imports); f.CType.Apply(CollectEditorCppForwardDefineVisitor.Ins, imports);
} }
//return string.Join('\n', imports.Select(im => $"{im.CppNamespaceBegin} struct {im.UeFname}; {im.CppNamespaceEnd}"));
throw new NotImplementedException(); throw new NotImplementedException();
} }
} }

View File

@ -24,15 +24,15 @@ namespace Luban.Job.Cfg.Defs
public RefValidator Ref { get; private set; } public RefValidator Ref { get; private set; }
public RefValidator KeyRef { get; private set; } //public RefValidator KeyRef { get; private set; }
public RefValidator ValueRef { get; private set; } //public RefValidator ValueRef { get; private set; }
public List<IValidator> Validators { get; } = new List<IValidator>(); //public List<IValidator> Validators { get; } = new List<IValidator>();
public List<IValidator> KeyValidators { get; } = new List<IValidator>(); //public List<IValidator> KeyValidators { get; } = new List<IValidator>();
public List<IValidator> ValueValidators { get; } = new List<IValidator>(); //public List<IValidator> ValueValidators { get; } = new List<IValidator>();
// 如果ref了多个表不再生成 xxx_ref之类的字段也不会resolve // 如果ref了多个表不再生成 xxx_ref之类的字段也不会resolve
public bool GenRef => Ref != null && Ref.Tables.Count == 1; public bool GenRef => Ref != null && Ref.Tables.Count == 1;
@ -126,102 +126,71 @@ namespace Luban.Job.Cfg.Defs
this.RawDefine = f; this.RawDefine = f;
} }
private void CompileValidatorsForType(TType type)
{
foreach (var valName in ValidatorFactory.ValidatorNames)
{
if (type.Tags != null && type.Tags.TryGetValue(valName, out var valValue))
{
type.Processors.Add(ValidatorFactory.Create(valName, valValue));
}
}
}
private void CompileValidatorsForArrayLink(TType elementType)
{
CompileValidatorsForType(elementType);
var valueRef = this.CType.Processors.Find(v => v is RefValidator);
if (valueRef != null)
{
this.CType.Processors.Remove(valueRef);
elementType.Processors.Add(valueRef);
}
var valuePath = this.CType.Processors.Find(v => v is PathValidator);
if (valuePath != null)
{
this.CType.Processors.Remove(valuePath);
elementType.Processors.Add(valuePath);
}
}
public override void Compile() public override void Compile()
{ {
base.Compile(); base.Compile();
CompileValidatorsForType(CType);
switch (this.CType) switch (this.CType)
{ {
case TArray ta: case TArray ta:
{ {
if (ta.ElementType.Tags.TryGetValue("ref", out string refStr)) CompileValidatorsForArrayLink(ta.ElementType);
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr));
}
if (CType.Tags.TryGetValue("ref", out string refStr2))
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr2));
}
if (ta.ElementType.Tags.TryGetValue("path", out string PathStr))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", PathStr));
}
if (CType.Tags.TryGetValue("path", out string pathStr2))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", pathStr2));
}
break; break;
} }
case TList ta: case TList ta:
{ {
if (ta.ElementType.Tags.TryGetValue("ref", out string refStr)) CompileValidatorsForArrayLink(ta.ElementType);
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr));
}
if (CType.Tags.TryGetValue("ref", out string refStr2))
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr2));
}
if (ta.ElementType.Tags.TryGetValue("path", out string PathStr))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", PathStr));
}
if (CType.Tags.TryGetValue("path", out string pathStr2))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", pathStr2));
}
break; break;
} }
case TSet ta: case TSet ta:
{ {
if (ta.ElementType.Tags.TryGetValue("ref", out string refStr)) CompileValidatorsForArrayLink(ta.ElementType);
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr));
}
if (CType.Tags.TryGetValue("ref", out string refStr2))
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", refStr2));
}
if (ta.ElementType.Tags.TryGetValue("path", out string PathStr))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", PathStr));
}
if (CType.Tags.TryGetValue("path", out string pathStr2))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", pathStr2));
}
break; break;
} }
case TMap ta: case TMap ta:
{ {
if (ta.KeyType.Tags.TryGetValue("ref", out string keyRefStr)) CompileValidatorsForType(ta.KeyType);
{ CompileValidatorsForType(ta.ValueType);
this.KeyValidators.Add(this.KeyRef = (RefValidator)ValidatorFactory.Create("ref", keyRefStr));
}
if (ta.ValueType.Tags.TryGetValue("ref", out string valueRefStr))
{
this.ValueValidators.Add(this.ValueRef = (RefValidator)ValidatorFactory.Create("ref", valueRefStr));
}
if (ta.KeyType.Tags.TryGetValue("path", out string PathStr))
{
this.KeyValidators.Add(ValidatorFactory.Create("path", PathStr));
}
if (ta.ValueType.Tags.TryGetValue("path", out string pathStr2))
{
this.ValueValidators.Add(ValidatorFactory.Create("path", pathStr2));
}
break; break;
} }
default: default:
{ {
if (CType.Tags.TryGetValue("ref", out string refStr2)) var selfRef = this.CType.Processors.Find(v => v is RefValidator);
if (selfRef != null)
{ {
this.Validators.Add(this.Ref = (RefValidator)ValidatorFactory.Create("ref", refStr2)); this.Ref = (RefValidator)selfRef;
}
if (CType.Tags.TryGetValue("path", out string pathStr2))
{
this.Validators.Add(ValidatorFactory.Create("path", pathStr2));
} }
break; break;
} }
@ -301,49 +270,52 @@ namespace Luban.Job.Cfg.Defs
} }
} }
private void CompileValidator(TType type)
{
foreach (var p in CType.Processors)
{
if (p is IValidator val)
{
val.Compile(this);
if (val is RefValidator refVal)
{
ValidateRef(refVal, type);
}
}
}
}
public override void PostCompile() public override void PostCompile()
{ {
base.PostCompile(); base.PostCompile();
foreach (var val in KeyValidators.Concat(ValueValidators).Concat(Validators)) CompileValidator(CType);
{
val.Compile(this);
}
if (Ref != null)
{
ValidateRef(Ref, CType);
}
if (KeyRef != null)
{
ValidateRef(KeyRef, (CType as TMap).KeyType);
}
if (ValueRef != null)
{
switch (this.CType) switch (this.CType)
{ {
case TArray ta: case TArray ta:
{ {
ValidateRef(ValueRef, ta.ElementType); CompileValidator(ta.ElementType);
break; break;
} }
case TList ta: case TList ta:
{ {
ValidateRef(ValueRef, ta.ElementType); CompileValidator(ta.ElementType);
break; break;
} }
case TSet ta: case TSet ta:
{ {
ValidateRef(ValueRef, ta.ElementType); CompileValidator(ta.ElementType);
break; break;
} }
case TMap ta: case TMap ta:
{ {
ValidateRef(ValueRef, ta.ValueType); CompileValidator(ta.KeyType);
CompileValidator(ta.ValueType);
break; break;
} }
} }
}
Index = CType.GetTag("index"); Index = CType.GetTag("index");

View File

@ -55,24 +55,6 @@ namespace Luban.Job.Cfg.TypeVisitors
return false; return false;
} }
//bool IsValidatorEquals(List<Validator> vs1, List<Validator> vs2)
//{
// if (vs1.Count != vs2.Count)
// {
// return false;
// }
// for (int i = 0; i < vs1.Count; i++)
// {
// var v1 = vs1[i];
// var v2 = vs2[i];
// if (v1.Type != v2.Type || v1.Rule != v2.Rule)
// {
// return false;
// }
// }
// return true;
//}
if (ctx.TryGetValue(a, out var e)) if (ctx.TryGetValue(a, out var e))
{ {
return e; return e;
@ -103,15 +85,9 @@ namespace Luban.Job.Cfg.TypeVisitors
if (f1.Name != f2.Name if (f1.Name != f2.Name
|| f1.NeedExport != f2.NeedExport || f1.NeedExport != f2.NeedExport
|| f1.Index != f2.Index || f1.Index != f2.Index
// || f1.Sep != f2.Sep
//#if !LUBAN_LITE
// || f1.ResourceTag != f2.ResourceTag
//#endif
|| f1.CType.IsNullable != f2.CType.IsNullable || f1.CType.IsNullable != f2.CType.IsNullable
|| f1.CType.GetType() != f2.CType.GetType() || f1.CType.GetType() != f2.CType.GetType()
//|| !IsValidatorEquals(f1.RawDefine.Validators, f2.RawDefine.Validators) //|| !IsProcessorEqual(f1.CType, f2.CType)
//|| !IsValidatorEquals(f1.RawDefine.KeyValidators, f2.RawDefine.KeyValidators)
//|| !IsValidatorEquals(f1.RawDefine.ValueValidators, f2.RawDefine.ValueValidators)
) )
{ {
return setupNotEqual(); return setupNotEqual();

View File

@ -64,13 +64,6 @@ namespace Luban.Job.Cfg.Utils
return allFiles; return allFiles;
} }
//private async Task<List<InputFileInfo>> CollectInputFilesAsync(RemoteAgent agent, DefTable table, string dataDir)
//{
// var collectTasks = new List<Task<List<InputFileInfo>>>();
// foreach (var file in table.InputFiles)
// return CollectInputFilesAsync(agent, table.InputFiles, dataDir)
//}
public static async Task GenerateLoadRecordFromFileTasksAsync(IAgent agent, DefTable table, string dataDir, List<string> inputFiles2, List<Task<List<Record>>> tasks) public static async Task GenerateLoadRecordFromFileTasksAsync(IAgent agent, DefTable table, string dataDir, List<string> inputFiles2, List<Task<List<Record>>> tasks)
{ {
var inputFileInfos = await CollectInputFilesAsync(agent, inputFiles2, dataDir); var inputFileInfos = await CollectInputFilesAsync(agent, inputFiles2, dataDir);

View File

@ -1,12 +1,14 @@
using Luban.Job.Cfg.Datas; using Luban.Job.Cfg.Datas;
using Luban.Job.Cfg.Defs; using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Defs;
using Luban.Job.Common.Types;
namespace Luban.Job.Cfg.Validators namespace Luban.Job.Cfg.Validators
{ {
public interface IValidator public interface IValidator : IProcessor
{ {
void Compile(DefField def); void Compile(DefField def);
void Validate(ValidatorContext ctx, DType data, bool nullable); void Validate(ValidatorContext ctx, TType type, DType data);
} }
} }

View File

@ -1,5 +1,6 @@
using Luban.Job.Cfg.Datas; using Luban.Job.Cfg.Datas;
using Luban.Job.Cfg.Defs; using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Types;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
@ -162,11 +163,11 @@ namespace Luban.Job.Cfg.Validators
this.RawPattern = pathPattern; this.RawPattern = pathPattern;
} }
public void Validate(ValidatorContext ctx, DType data, bool nullable) public void Validate(ValidatorContext ctx, TType type, DType data)
{ {
var assembly = ctx.Assembly; var assembly = ctx.Assembly;
if (nullable && data == null) if (type.IsNullable && data == null)
{ {
return; return;
} }

View File

@ -1,5 +1,6 @@
using Luban.Job.Cfg.Datas; using Luban.Job.Cfg.Datas;
using Luban.Job.Cfg.Defs; using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Types;
using System; using System;
namespace Luban.Job.Cfg.Validators namespace Luban.Job.Cfg.Validators
@ -143,7 +144,7 @@ namespace Luban.Job.Cfg.Validators
public string Source => ValidatorContext.CurrentVisitor.CurrentValidateRecord.Source; public string Source => ValidatorContext.CurrentVisitor.CurrentValidateRecord.Source;
public void Validate(ValidatorContext ctx, DType data, bool nullable) public void Validate(ValidatorContext ctx, TType type, DType data)
{ {
var assembly = ctx.Assembly; var assembly = ctx.Assembly;
void LogError() void LogError()
@ -151,7 +152,7 @@ namespace Luban.Job.Cfg.Validators
assembly.Agent.Error("记录 {0}:{1} (来自文件:{2}) 不在范围:{3}内", ValidatorContext.CurrentRecordPath, data, Source, _str); assembly.Agent.Error("记录 {0}:{1} (来自文件:{2}) 不在范围:{3}内", ValidatorContext.CurrentRecordPath, data, Source, _str);
} }
if (nullable && data == null) if (type.IsNullable && data == null)
{ {
return; return;
} }

View File

@ -1,8 +1,10 @@
using Luban.Job.Cfg.Datas; using Luban.Job.Cfg.Datas;
using Luban.Job.Cfg.DataVisitors; using Luban.Job.Cfg.DataVisitors;
using Luban.Job.Cfg.Defs; using Luban.Job.Cfg.Defs;
using Luban.Job.Common.Types;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
namespace Luban.Job.Cfg.Validators namespace Luban.Job.Cfg.Validators
{ {
@ -28,10 +30,10 @@ namespace Luban.Job.Cfg.Validators
this.Tables = new List<string>(tables); this.Tables = new List<string>(tables);
} }
public void Validate(ValidatorContext ctx, DType key, bool nullable) public void Validate(ValidatorContext ctx, TType type, DType key)
{ {
// 对于可空字段,跳过检查 // 对于可空字段,跳过检查
if (nullable && key == null) if (type.IsNullable && key == null)
{ {
return; return;
} }

View File

@ -1,5 +1,6 @@
using Luban.Job.Cfg.RawDefs; using Luban.Job.Cfg.RawDefs;
using System; using System;
using System.Collections.Generic;
using System.Linq; using System.Linq;
namespace Luban.Job.Cfg.Validators namespace Luban.Job.Cfg.Validators
@ -7,6 +8,11 @@ namespace Luban.Job.Cfg.Validators
static class ValidatorFactory static class ValidatorFactory
{ {
private static readonly NLog.Logger s_logger = NLog.LogManager.GetCurrentClassLogger(); private static readonly NLog.Logger s_logger = NLog.LogManager.GetCurrentClassLogger();
private readonly static List<string> s_validatorNames = new List<string>() { RefValidator.NAME, PathValidator.NAME, RangeValidator.NAME };
public static List<string> ValidatorNames => s_validatorNames;
public static IValidator Create(string type, string rule) public static IValidator Create(string type, string rule)
{ {
s_logger.Debug("== create validator {type}:{rule}", type, rule); s_logger.Debug("== create validator {type}:{rule}", type, rule);

View File

@ -38,7 +38,6 @@ namespace Luban.Job.Cfg.l10n
Fields = new List<Common.RawDefs.Field> Fields = new List<Common.RawDefs.Field>
{ {
new CfgField() { Name = "key", Type = "string" }, new CfgField() { Name = "key", Type = "string" },
//new Common.RawDefs.Field() { Id = 1, Name = "origin_text", Type = "string" },
new CfgField() { Name = textValueFieldName, Type = "string" }, new CfgField() { Name = textValueFieldName, Type = "string" },
} }
}) })

View File

@ -129,11 +129,7 @@ namespace Luban.Job.Common.Defs
public TType CreateType(string module, string type) public TType CreateType(string module, string type)
{ {
#if LUBAN_LITE int sepIndex = DefUtil.IndexOfIncludeBrace(type, ',');
int sepIndex = type.IndexOf(',');
#else
int sepIndex = type.IndexOf(',', System.StringComparison.Ordinal);
#endif
if (sepIndex > 0) if (sepIndex > 0)
{ {
var (containerAndElementType, tags) = DefUtil.ParseType(type); var (containerAndElementType, tags) = DefUtil.ParseType(type);

View File

@ -61,53 +61,6 @@ namespace Luban.Job.Common.Defs
} }
} }
//private string _lanStyleName;
//public string CsStyleName
//{
// get
// {
// if (_lanStyleName == null)
// {
// _lanStyleName = TypeUtil.ToCsStyleName(Name);
// }
// return _lanStyleName;
// }
//}
//public string JavaStyleName
//{
// get
// {
// if (_lanStyleName == null)
// {
// _lanStyleName = TypeUtil.ToJavaStyleName(Name);
// }
// return _lanStyleName;
// }
//}
//public string CppStyleName => JavaStyleName;
//public string TsStyleName
//{
// get
// {
// if (_lanStyleName == null)
// {
// _lanStyleName = TypeUtil.ToJavaStyleName(Name);
// }
// return _lanStyleName;
// }
//}
//public string PyStyleName => Name;
//public string GoStyleName => CsStyleName;
//public string RustStyleName => Name != "type" ? Name : "r#" + Name;
//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; }

View File

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace Luban.Job.Common.Defs
{
public interface IProcessor
{
}
}

View File

@ -11,7 +11,7 @@ namespace Luban.Job.Common.Types
public static TBool Create(bool isNullable, Dictionary<string, string> tags) public static TBool Create(bool isNullable, Dictionary<string, string> tags)
{ {
if (tags == null) if (tags == null || tags.Count == 0)
{ {
return isNullable ? NullableIns : Ins; return isNullable ? NullableIns : Ins;
} }

View File

@ -1,3 +1,4 @@
using Luban.Job.Common.Defs;
using Luban.Job.Common.TypeVisitors; using Luban.Job.Common.TypeVisitors;
using System.Collections.Generic; using System.Collections.Generic;
@ -9,6 +10,8 @@ namespace Luban.Job.Common.Types
public Dictionary<string, string> Tags { get; } public Dictionary<string, string> Tags { get; }
public List<IProcessor> Processors { get; } = new List<IProcessor>();
protected TType(bool isNullable, Dictionary<string, string> tags) protected TType(bool isNullable, Dictionary<string, string> tags)
{ {
IsNullable = isNullable; IsNullable = isNullable;

View File

@ -35,6 +35,29 @@ namespace Luban.Job.Common.Utils
return am; return am;
} }
public static int IndexOfIncludeBrace(string s, char sep)
{
int braceDepth = 0;
for (int i = 0; i < s.Length; i++)
{
var c = s[i];
if (c == '(' || c == '[' || c == '{')
{
++braceDepth;
}
else if (c == ')' || c == ')' || c == '}')
{
--braceDepth;
}
if (braceDepth == 0 && (c == sep))
{
return i;
}
}
return -1;
}
public static (string, Dictionary<string, string>) ParseType(string s) public static (string, Dictionary<string, string>) ParseType(string s)
{ {
int sepIndex = s.IndexOfAny(s_attrSep); int sepIndex = s.IndexOfAny(s_attrSep);
@ -48,11 +71,11 @@ namespace Luban.Job.Common.Utils
for (int i = 0; i < s.Length; i++) for (int i = 0; i < s.Length; i++)
{ {
var c = s[i]; var c = s[i];
if (c == '(') if (c == '(' || c == '[' || c == '{')
{ {
++braceDepth; ++braceDepth;
} }
else if (c == ')') else if (c == ')' || c == ')' || c == '}')
{ {
--braceDepth; --braceDepth;
} }

View File

@ -17,8 +17,11 @@
<ItemGroup> <ItemGroup>
<Compile Remove="Datas\**" /> <Compile Remove="Datas\**" />
<Compile Remove="Scripts\**" />
<EmbeddedResource Remove="Datas\**" /> <EmbeddedResource Remove="Datas\**" />
<EmbeddedResource Remove="Scripts\**" />
<None Remove="Datas\**" /> <None Remove="Datas\**" />
<None Remove="Scripts\**" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>