【优化】更加优雅地打印配置加载错误。默认不再显示大段的堆栈信息
parent
54685289af
commit
df722abb4a
|
|
@ -262,6 +262,10 @@ Options:
|
|||
else
|
||||
{
|
||||
s_logger.Error("GenJob fail. err:{err} msg:{msg}", res.ErrCode, res.ErrMsg);
|
||||
if (!string.IsNullOrEmpty(res.StackTrace))
|
||||
{
|
||||
s_logger.Debug("StackTrace: {}", res.StackTrace);
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
|
|
|
|||
|
|
@ -8,5 +8,6 @@ namespace Luban.Common
|
|||
READ_FILE_FAIL,
|
||||
JOB_ARGUMENT_ERROR,
|
||||
JOB_EXCEPTION,
|
||||
DATA_PARSE_ERROR,
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -70,6 +70,8 @@ namespace Luban.Common.Protos
|
|||
|
||||
public List<FileInfo> ScatteredFiles { get; set; } = new List<FileInfo>();
|
||||
|
||||
public string StackTrace { get; set; }
|
||||
|
||||
public override int GetTypeId()
|
||||
{
|
||||
return 0;
|
||||
|
|
@ -81,6 +83,7 @@ namespace Luban.Common.Protos
|
|||
os.WriteString(ErrMsg);
|
||||
Bright.Common.SerializationUtil.Serialize(os, FileGroups);
|
||||
Bright.Common.SerializationUtil.Serialize(os, ScatteredFiles);
|
||||
os.WriteString(StackTrace);
|
||||
}
|
||||
public override void Deserialize(ByteBuf os)
|
||||
{
|
||||
|
|
@ -88,6 +91,7 @@ namespace Luban.Common.Protos
|
|||
ErrMsg = os.ReadString();
|
||||
Bright.Common.SerializationUtil.Deserialize(os, FileGroups);
|
||||
Bright.Common.SerializationUtil.Deserialize(os, ScatteredFiles);
|
||||
StackTrace = os.ReadString();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,44 @@
|
|||
using Luban.Job.Cfg.Defs;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Luban.Job.Cfg.DataCreators
|
||||
{
|
||||
public class DataCreateException : System.Exception
|
||||
{
|
||||
private List<(DefBean, DefField)> VariablePath { get; } = new();
|
||||
|
||||
public string OriginDataLocation { get; set; }
|
||||
|
||||
public string DataLocationInFile { get; }
|
||||
|
||||
public string OriginErrorMsg { get; }
|
||||
|
||||
public string OriginStackTrace { get; }
|
||||
|
||||
public DataCreateException(Exception e, string dataLocation) : base("DataCreateException", e)
|
||||
{
|
||||
this.OriginStackTrace = e.StackTrace;
|
||||
this.OriginErrorMsg = e.Message;
|
||||
this.DataLocationInFile = dataLocation;
|
||||
}
|
||||
|
||||
public void Push(DefBean bean, DefField f)
|
||||
{
|
||||
VariablePath.Add((bean, f));
|
||||
}
|
||||
|
||||
public string VariableFullPathStr
|
||||
{
|
||||
get
|
||||
{
|
||||
var path = new List<(DefBean, DefField)>(VariablePath);
|
||||
path.Reverse();
|
||||
return string.Join(" => ", path.Select(b => $"{{{b.Item1.FullName}}}.{b.Item2.Name}"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -336,9 +336,16 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
list.Add(f.CType.Apply(this, f.Remapper, new ExcelStream(stream.ReadCell(), sep, false), ass));
|
||||
}
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(bean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new InvalidExcelDataException($"读取结构:{bean.FullName} 字段:{f.Name} 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, stream.CurrentExcelPosition);
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
return list;
|
||||
|
|
|
|||
|
|
@ -128,9 +128,16 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
list.Add(f.CType.Apply(this, row.GetSubTitleNamedRow(fname), f.IsMultiRow /* 肯定是 false */, f.IsNullable));
|
||||
}
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(bean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"读取结构:{bean.FullName} 字段:{fname} 读取 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, $"列:{fname}");
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
|
@ -154,9 +161,16 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
list.Add(f.CType.Apply(ExcelDataCreator.Ins, null, row.GetMultiRowStream(f.Name, sep), (DefAssembly)bean.AssemblyBase));
|
||||
}
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(bean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"读取结构:{bean.FullName} 多行字段:{f.Name} 读取 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, "");
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
|
@ -166,9 +180,16 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
{
|
||||
list.Add(f.CType.Apply(ExcelDataCreator.Ins, f.Remapper, stream, (DefAssembly)bean.AssemblyBase));
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(bean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"读取结构:{bean.FullName} 字段:{f.Name} 位置:{stream.CurrentExcelPosition} 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, stream.CurrentExcelPosition);
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -130,40 +130,47 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
}
|
||||
|
||||
var fields = new List<DType>();
|
||||
foreach (var field in implBean.HierarchyFields)
|
||||
foreach (DefField f in implBean.HierarchyFields)
|
||||
{
|
||||
if (x.TryGetProperty(field.Name, out var ele))
|
||||
if (x.TryGetProperty(f.Name, out var ele))
|
||||
{
|
||||
if (ele.ValueKind == JsonValueKind.Null || ele.ValueKind == JsonValueKind.Undefined)
|
||||
{
|
||||
if (field.CType.IsNullable)
|
||||
if (f.CType.IsNullable)
|
||||
{
|
||||
fields.Add(null);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 不能 null or undefined ");
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{f.Name} 不能 null or undefined ");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
try
|
||||
{
|
||||
fields.Add(field.CType.Apply(this, ele, ass));
|
||||
fields.Add(f.CType.Apply(this, ele, ass));
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(bean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 读取失败 => {e.Message}", e);
|
||||
var dce = new DataCreateException(e, "");
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (field.CType.IsNullable)
|
||||
else if (f.CType.IsNullable)
|
||||
{
|
||||
fields.Add(null);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 缺失");
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{f.Name} 缺失");
|
||||
}
|
||||
}
|
||||
return new DBean(bean, implBean, fields);
|
||||
|
|
|
|||
|
|
@ -172,29 +172,36 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
}
|
||||
|
||||
var fields = new List<DType>();
|
||||
foreach (var field in implBean.HierarchyFields)
|
||||
foreach (DefField f in implBean.HierarchyFields)
|
||||
{
|
||||
var ele = table[field.Name];
|
||||
var ele = table[f.Name];
|
||||
|
||||
if (ele != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
// Console.WriteLine("field:{0} type:{1} value:{2}", field.Name, ele.GetType(), ele);
|
||||
fields.Add(field.CType.Apply(this, ele, ass));
|
||||
fields.Add(f.CType.Apply(this, ele, ass));
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(implBean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 读取失败 => {e.Message}", e);
|
||||
var dce = new DataCreateException(e, "");
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
else if (field.CType.IsNullable)
|
||||
else if (f.CType.IsNullable)
|
||||
{
|
||||
fields.Add(null);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 缺失");
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{f.Name} 缺失");
|
||||
}
|
||||
}
|
||||
return new DBean(bean, implBean, fields);
|
||||
|
|
|
|||
|
|
@ -98,7 +98,8 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"位置:{stream.CurrentExcelPosition} 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, stream.CurrentExcelPosition);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
return list;
|
||||
|
|
@ -132,7 +133,8 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"位置:{stream.CurrentExcelPosition} 出错 ==> {e.Message}", e);
|
||||
var dce = new DataCreateException(e, stream.CurrentExcelPosition);
|
||||
throw dce;
|
||||
}
|
||||
}
|
||||
return new DMap(type, map);
|
||||
|
|
|
|||
|
|
@ -114,26 +114,33 @@ namespace Luban.Job.Cfg.DataCreators
|
|||
}
|
||||
|
||||
var fields = new List<DType>();
|
||||
foreach (var field in implBean.HierarchyFields)
|
||||
foreach (DefField f in implBean.HierarchyFields)
|
||||
{
|
||||
var feles = x.Elements(field.Name);
|
||||
var feles = x.Elements(f.Name);
|
||||
XElement fele = feles.FirstOrDefault();
|
||||
if (fele == null)
|
||||
{
|
||||
if (field.CType.IsNullable)
|
||||
if (f.CType.IsNullable)
|
||||
{
|
||||
fields.Add(null);
|
||||
continue;
|
||||
}
|
||||
throw new Exception($"字段:{field.Name} 缺失");
|
||||
throw new Exception($"字段:{f.Name} 缺失");
|
||||
}
|
||||
try
|
||||
{
|
||||
fields.Add(field.CType.Apply(this, fele, ass));
|
||||
fields.Add(f.CType.Apply(this, fele, ass));
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.Push(implBean, f);
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"结构:{implBean.FullName} 字段:{field.Name} 读取失败 => {e.Message}", e);
|
||||
var dce = new DataCreateException(e, "");
|
||||
dce.Push(bean, f);
|
||||
throw dce;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
using Luban.Job.Cfg.DataCreators;
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
|
|
@ -25,6 +26,10 @@ namespace Luban.Job.Cfg.DataSources
|
|||
source.Load(url, sheetName, stream, exportTestData);
|
||||
return source;
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"文件{url} 加载失败 ==> {e.Message}", e);
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
using ExcelDataReader;
|
||||
using Luban.Job.Cfg.DataCreators;
|
||||
using Luban.Job.Cfg.Datas;
|
||||
using Luban.Job.Cfg.Defs;
|
||||
using Luban.Job.Common.Types;
|
||||
|
|
@ -66,6 +67,11 @@ namespace Luban.Job.Cfg.DataSources.Excel
|
|||
{
|
||||
datas.AddRange(sheet.ReadMulti(type, ((DefBean)type.Bean).IsMultiRow));
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
dce.OriginDataLocation = sheet.RawUrl;
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"sheet:{sheet.Name} ==> {e.Message} {e.StackTrace}", e);
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ using Bright.Time;
|
|||
using CommandLine;
|
||||
using Luban.Common.Protos;
|
||||
using Luban.Common.Utils;
|
||||
using Luban.Job.Cfg.DataCreators;
|
||||
using Luban.Job.Cfg.Defs;
|
||||
using Luban.Job.Cfg.Generate;
|
||||
using Luban.Job.Cfg.RawDefs;
|
||||
|
|
@ -424,6 +425,17 @@ namespace Luban.Job.Cfg
|
|||
res.ScatteredFiles.AddRange(genScatteredFiles);
|
||||
}
|
||||
}
|
||||
catch (DataCreateException e)
|
||||
{
|
||||
res.ErrCode = Luban.Common.EErrorCode.DATA_PARSE_ERROR;
|
||||
res.ErrMsg = $@"加载数据失败.
|
||||
文件: {e.OriginDataLocation}
|
||||
错误位置: {e.DataLocationInFile}
|
||||
Err: {e.OriginErrorMsg}
|
||||
变量: {e.VariableFullPathStr}
|
||||
";
|
||||
res.StackTrace = e.OriginStackTrace;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
res.ErrCode = Luban.Common.EErrorCode.JOB_EXCEPTION;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
using Bright.Time;
|
||||
using Luban.Common.Utils;
|
||||
using Luban.Job.Cfg.Cache;
|
||||
using Luban.Job.Cfg.DataCreators;
|
||||
using Luban.Job.Cfg.Datas;
|
||||
using Luban.Job.Cfg.DataSources;
|
||||
using Luban.Job.Cfg.Defs;
|
||||
|
|
@ -186,6 +187,14 @@ namespace Luban.Job.Cfg.Utils
|
|||
return record != null ? new List<Record> { record } : new List<Record>();
|
||||
}
|
||||
}
|
||||
catch (DataCreateException dce)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(dce.OriginDataLocation))
|
||||
{
|
||||
dce.OriginDataLocation = originFile;
|
||||
}
|
||||
throw;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception($"配置文件:{originFile} 生成失败. ==> {e.Message}", e);
|
||||
|
|
|
|||
Loading…
Reference in New Issue