Catel:我怎么知道 SavableModelBase.Load 何时失败?



使用 Catel 4.4.0.

我让用户浏览并加载他的数据文件,该文件是使用Load(stream,XML模式)方法从SavableModelBase子类实例(模型ABC)中的数据。 该用户犯了一个错误并加载了错误的文件,该文件也是一个 SavableModelBase 子类,但是一个完全不同的模型(模型 XYZ)。 代码经历了反序列化数据的动作,但当然,没有找到模型 ABC 的任何属性,因此返回的实例(模型 ABC)仅包含属性的默认值。

我希望 Load 方法要么返回空值,要么引发异常。 如何确定加载模型 ABC 的实例(该实例是全新的,因此确实具有默认属性值)与意外尝试将模型 XYZ 加载为模型 ABC 之间的区别? 我没有看到SavableModelBase的任何属性,这些属性会提醒我可能的混淆。

SaveableModelBase 是否有内置的东西可以帮助我确定加载错误,或者我需要提出某种解决方法?

如果您需要更多信息,请告诉我。 谢谢!

兰迪

由于该类可以(反)序列化多种格式(即使更改了 xml 结构),因此没有真正的方法来查看这是否失败。在这种情况下,我将检查所需的属性和/或为要以不同方式加载的每种类型使用不同的文件类型扩展名。

我决定使用自己的Load 方法创建一个 SavableModelBase 的子类。 此 Load 方法将首先读取文件的根节点,该根节点与保存文件的类的名称同名。 如果它们比较"正常",则使用父 SavableModelBase 类 Load 方法恢复加载。 否则,将引发异常。 (而且我目前忽略了二进制模式的加载。

public class LexSavableModelBase<T> : SavableModelBase<T> where T : class
{
// SNIP!
public static new T Load(Stream stream, SerializationMode mode)
{
Argument.IsNotNull(() => stream);
if (mode == SerializationMode.Xml)
{
using (XmlReader xr = XmlReader.Create(stream))
{
xr.MoveToContent();
string rootName = xr.LocalName;
if (string.Compare(rootName, typeof(T).Name, StringComparison.OrdinalIgnoreCase) != 0)
{
throw new InvalidDataException(string.Format(CultureInfo.CurrentCulture, "Expecting data from Model [{0}], but found Model [{1}] instead.", typeof(T).Name, rootName));
}
// Reset to read from the top.
stream.Seek(0, SeekOrigin.Begin);
}
}
return SavableModelBase<T>.Load<T>(stream, mode);
}
}

我敢肯定,必须两次读取文件的一部分会降低性能,而且我只做了足够的工作来满足我的一小部分场景,但它似乎做了我需要它做的事情——检测何时呈现错误的数据进行加载。 我只在我的应用程序中拥有的 4+ 个模型中的大约 150 个型号上使用它。 这些是由客户保存到磁盘上的文件并从中加载的。

如果您可以进行任何改进,请这样做。 如果您有任何问题,请告诉我。

最新更新