通用接口上的代码契约问题
我遇到了涉及通用接口合同的问题。我有两个通用接口,每个接口都有一个方法,该方法有一个前提条件(Requires
契约)。第一个接口的契约按预期工作:前提条件被传播到实现类,并且接口方法被适当地修饰(通过代码契约编辑器扩展)。未检测到第二个接口的合约,但两个接口/合约对之间的代码几乎相同。
//
// Example working as expected
//
[ContractClass(typeof(IExporterContract<>))]
public interface IExporter<in TInput>
where TInput : class
{
// Shows adornment "requires obj != null"; contracts propogate
void Export(TInput obj);
}
[ContractClassFor(typeof(IExporter<>))]
abstract class IExporterContract<TInput> : IExporter<TInput>
where TInput : class
{
public void Export(TInput obj)
{
Contract.Requires(obj != null);
}
}
//
// Example with unexpected behavior
//
[ContractClass(typeof(IParserContract<>))]
public interface IParser<out TOutput>
where TOutput : class
{
// Workbook is Microsoft.Office.Interop.Excel.Workbook
// Does not show adornment "requires workbook != null"; contracts do not propogate
TOutput Parse(Workbook workbook);
}
[ContractClassFor(typeof(IParser<>))]
abstract class IParserContract<TOutput> : IParser<TOutput>
where TOutput : class
{
public TOutput Parse(Workbook workbook)
{
Contract.Requires(workbook != null);
return default(TOutput);
}
}
值得注意的是,Microsoft.Office.Interop.*
中的任何接口都会导致此行为。使用任何其他类型,一切都会按预期进行。然而,我不知道这是为什么。
编辑:正如Porges指出的,合同正在编写(通过IL确认),所以这似乎特定于代码合同编辑器扩展。
I am experiencing an issue involving contracts for a generic interface. I have two generic interfaces, each with a single method which has a single precondition (Requires
contract). The contract for the first interface works as expected: the precondition is propagated to implemenation classes, and the interface method is adorned appropriately (via the Code Contracts Editor Extension). The contract for the second interface is not detected, but the code is nearly identical between the two interface/contract pairs.
//
// Example working as expected
//
[ContractClass(typeof(IExporterContract<>))]
public interface IExporter<in TInput>
where TInput : class
{
// Shows adornment "requires obj != null"; contracts propogate
void Export(TInput obj);
}
[ContractClassFor(typeof(IExporter<>))]
abstract class IExporterContract<TInput> : IExporter<TInput>
where TInput : class
{
public void Export(TInput obj)
{
Contract.Requires(obj != null);
}
}
//
// Example with unexpected behavior
//
[ContractClass(typeof(IParserContract<>))]
public interface IParser<out TOutput>
where TOutput : class
{
// Workbook is Microsoft.Office.Interop.Excel.Workbook
// Does not show adornment "requires workbook != null"; contracts do not propogate
TOutput Parse(Workbook workbook);
}
[ContractClassFor(typeof(IParser<>))]
abstract class IParserContract<TOutput> : IParser<TOutput>
where TOutput : class
{
public TOutput Parse(Workbook workbook)
{
Contract.Requires(workbook != null);
return default(TOutput);
}
}
Of note, any interface in Microsoft.Office.Interop.*
causes this behavior. Using any other type, everything works as expected. I'm unaware of why this is, however.
EDIT: as Porges pointed out, the contracts are being written (confirmed via IL), so this seems to be specific to the Code Contracts Editor extension.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
我无法复制这个。给定此代码(以及您的示例):
合约按预期传播(通过 Reflector 反编译):
I can't replicate this. Given this code (along with your example):
The contract is propagated as expected (decompiled via Reflector):