如何标记生成的方法已过时?

4
我正在使用强类型DataSet,手动添加行会容易出错。我提供工厂方法来正确创建行。我希望引导我的类的消费者远离生成的*Table类上的Add*Row方法。
在生成的方法中添加过时的属性即可。不幸的是,它们会在下一次代码生成时被删除。
我无法在非生成代码中使用部分类方法,因为VS2008 DataSet设计器不使用它们。 MyType.Dataset.Designer.cs看起来有点像这样:
public partial class ThingyDataTable : global::System.Data.DataTable, global::System.Collections.IEnumerable {
    // I'd love an [Obsolete("Please use the factory method.")] here.
    // I can't use a partial method, as this method isn't partial. 
    [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
    public ShelfRow NewShelfRow()  
        return ((ShelfRow)(this.NewRow()));
    }
 }

我能否从MyType.cs中添加一个Obsolete属性?尝试使用C风格的原型不起作用,因为成员已经被定义。插入partial无效,因为生成的成员不是partial

// BROKEN EXAMPLE:
public partial class ThingyDataTable {
    // I'd love an [Obsolete("Please use the factory method.")] here.
    // I can't use a partial method, as this method isn't partial. 
    [Obsolete("Please use the factory method.")]
    public ShelfRow NewShelfRow(); // ERROR: member already defined.
}

有没有其他方法可以标记生成的方法为Obsolete

我还能以什么其他方式警告使用者不要使用生成的方法?


我会尝试使用以下查找和替换:"[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]" 替换为 "[global::System.Diagnostics.DebuggerNonUserCodeAttribute()][Obsolete("Please use the factory method.")]". 我找不到 DataSets 的模板。 - jrcs3
编辑模板是一个很有趣的想法。我该如何确保任何使用存储库源代码的人都能在检出后使用该模板? - Garth Kidd
如果你能找到模板的话。我认为Visual Studio使用xsd.exe为DataSets生成类,而模板数据在.exe或一些支持的.dll中。 - jrcs3
如果代码稳定,您可以删除*.xsd文件以防止重新生成。 - jrcs3
4个回答

1

在非生成的部分类中使用new关键字:

public partial interface ICaseRepository
    : IRepository<Case>
{
    void Delete(int id);

    [Obsolete("Use Delete(int id) instead.")]
    new void Delete(Case entity);
}

这将允许所有当前使用生成的方法来生成编译时警告。

1

用于从XSD文件生成设计器文件的自定义工具在开箱即用时并不是那么可配置。

但你可以选择:

  • 从类型化数据集的xsd文件的“属性”对话框中将其删除,即将“Custom Tool”字段从“MSDataSetGenerator”设置为空。这样,你就可以控制代码生成的时间。但这种方法容易出错,因为你可能会忘记在未来这样做...
  • 你可以创建自己的自定义工具,调用xsd.exe工具,并在适当的位置放置你想要的属性,但这意味着你需要在所有开发站点和构建服务器上安装自定义工具。(有关指针,请参见this post
  • 或者,最后,你可以强制代码生成器创建你的DataSet的内部实现,并使类实现一组公共接口,你可以允许客户端使用这些接口。你的DataSet类将无法直接在外部程序集中使用,但你的接口可以。

后者稍微不那么“自动化”,因为你需要在接口中反映DataSet模式的更改,但你可以控制一切,而且更加“工厂友好”。


谢谢你的建议!听起来比好好培训用户更痛苦,所以我会实施培训而不是采纳你的好建议。 :) - Garth Kidd

1

另一个选择是使用PostSharp 1.5和新的CustomAttributeInjector aspect(请参见在线文档)。

基本上,创建一个CompoundAspect,并将CustomAttributeInjectorAspect添加到任何您想要的地方。这应该可以工作。


谢谢,Gael!一些示例代码会使我的答案更好。可惜的是,在PostSharp文档中没有,而在PostSharp博客上的代码也不是很清晰。或许很快就会有了。 - Garth Kidd

-1

这是生成的代码,对吧。没有什么阻止你使用生成器的输出作为进一步生成器的输入,让它为你添加 [Obsolete] 属性。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接