可以在运行时更新具有 XML 源的 DisplayNameAttribute 扩展吗?
Can DisplayNameAttribute extension with XML source update in runtime?
这可能更多的是与 .NET Framework 的工作原理相关的问题,而不是寻找实际的解决方案。原因是我想知道这是我应该在修复时追求的东西,还是完全尝试其他东西。我做了一些搜索,但找不到我认为正确的答案。
我正在开发一个 ASP.NET MVC5 应用程序,该应用程序使用翻译提供程序并以 XML 文件作为源。在某些情况下,我使用 DisplayNameAttribute 扩展来装饰模型属性以提供翻译。它是通过参考这里的解决方案制作的:
这是我的实现:
[AttributeUsage(AttributeTargets.Property)]
public sealed class LocalizedDisplayNameAttribute : DisplayNameAttribute
{
public LocalizedDisplayNameAttribute(string key, string page = null) : base(FormatMessage(key, page))
{
}
private static string FormatMessage(string key, string page = null)
{
if (!string.IsNullOrWhiteSpace(key) && string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key);
}
else if (!string.IsNullOrWhiteSpace(key) && !string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key, page);
}
else
{
return string.Empty;
}
}
}
“TextGetter”是一个单独的库,用于处理从 XML 数据源中获取字符串。
属性扩展的用法如下:
[LocalizedDisplayName("Timestamp", "/report")]
public DateTimeOffset Timestamp { get; set; }
该网站还有一个功能,超级用户可以编辑翻译 XML 文件,以防某些翻译错误或丢失。通常 XML 文件中的编辑会立即可见,但具有此特定属性的属性除外。我知道通常当使用具有硬编码值的 DisplayName 属性时不能更改,因为它是编译的,尽管我假设因为这使用 XML 文件作为参考,我相信如果 XML 已更改,在这种情况下也会立即反映出来。但这似乎不会发生。
能够即时更改翻译是一项重要功能;我应该寻求其他解决方案吗?我可以在视图中设置带有翻译的 属性 名称,这是可行的,但这将需要大量重构,并将其保留为注释更加简洁。
我真的不知道从哪里拿它。
在此期间找到了一个解决方案,如果有人偶然发现它,就把它放在那里。所以这就是你应该做的,如果你想制作一个派生自 DisplayName 的属性用于本地化,并且最重要的是有一个可以在运行时更改和更新的本地化源:
[AttributeUsage(AttributeTargets.Property)]
public sealed class LocalizedDisplayNameAttribute : DisplayNameAttribute
{
private readonly string _key;
private readonly string _page;
public LocalizedDisplayNameAttribute(string key, string page = null) : base(key)
{
this._key = key;
this._page = page;
}
public override string DisplayName => this.FormatMessage(this._key, this._page);
private string FormatMessage(string key, string page = null)
{
if (!string.IsNullOrWhiteSpace(key) && string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key);
}
else if (!string.IsNullOrWhiteSpace(key) && !string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key, page);
}
else
{
return string.Empty;
}
}
}
“FormatMessage”的内容可以是您真正想要的任何内容,只需在其中插入您需要的任何代码以获取翻译后的字符串。
这可能更多的是与 .NET Framework 的工作原理相关的问题,而不是寻找实际的解决方案。原因是我想知道这是我应该在修复时追求的东西,还是完全尝试其他东西。我做了一些搜索,但找不到我认为正确的答案。
我正在开发一个 ASP.NET MVC5 应用程序,该应用程序使用翻译提供程序并以 XML 文件作为源。在某些情况下,我使用 DisplayNameAttribute 扩展来装饰模型属性以提供翻译。它是通过参考这里的解决方案制作的:
这是我的实现:
[AttributeUsage(AttributeTargets.Property)]
public sealed class LocalizedDisplayNameAttribute : DisplayNameAttribute
{
public LocalizedDisplayNameAttribute(string key, string page = null) : base(FormatMessage(key, page))
{
}
private static string FormatMessage(string key, string page = null)
{
if (!string.IsNullOrWhiteSpace(key) && string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key);
}
else if (!string.IsNullOrWhiteSpace(key) && !string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key, page);
}
else
{
return string.Empty;
}
}
}
“TextGetter”是一个单独的库,用于处理从 XML 数据源中获取字符串。
属性扩展的用法如下:
[LocalizedDisplayName("Timestamp", "/report")]
public DateTimeOffset Timestamp { get; set; }
该网站还有一个功能,超级用户可以编辑翻译 XML 文件,以防某些翻译错误或丢失。通常 XML 文件中的编辑会立即可见,但具有此特定属性的属性除外。我知道通常当使用具有硬编码值的 DisplayName 属性时不能更改,因为它是编译的,尽管我假设因为这使用 XML 文件作为参考,我相信如果 XML 已更改,在这种情况下也会立即反映出来。但这似乎不会发生。
能够即时更改翻译是一项重要功能;我应该寻求其他解决方案吗?我可以在视图中设置带有翻译的 属性 名称,这是可行的,但这将需要大量重构,并将其保留为注释更加简洁。 我真的不知道从哪里拿它。
在此期间找到了一个解决方案,如果有人偶然发现它,就把它放在那里。所以这就是你应该做的,如果你想制作一个派生自 DisplayName 的属性用于本地化,并且最重要的是有一个可以在运行时更改和更新的本地化源:
[AttributeUsage(AttributeTargets.Property)]
public sealed class LocalizedDisplayNameAttribute : DisplayNameAttribute
{
private readonly string _key;
private readonly string _page;
public LocalizedDisplayNameAttribute(string key, string page = null) : base(key)
{
this._key = key;
this._page = page;
}
public override string DisplayName => this.FormatMessage(this._key, this._page);
private string FormatMessage(string key, string page = null)
{
if (!string.IsNullOrWhiteSpace(key) && string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key);
}
else if (!string.IsNullOrWhiteSpace(key) && !string.IsNullOrWhiteSpace(page))
{
return TextGetter.GetText(key, page);
}
else
{
return string.Empty;
}
}
}
“FormatMessage”的内容可以是您真正想要的任何内容,只需在其中插入您需要的任何代码以获取翻译后的字符串。