32

I am using code contracts and trying to understand which of the build options shall I use and when. The contract assembly build options are defined in project properties

Code Contracts -> Contract Reference Assembly:

  • None
  • Build
  • DoNotBuild

Any thoughts or recommendations?

oleksii
  • 35,458
  • 16
  • 93
  • 163

2 Answers2

35

The Contract Reference Assembly is a special kind of assembly which preserves any code contracts you defined in your source code files. This is necessary because at compile-time, the code contracts' "rewriter" (ccrewriter) removes or replaces each contract with equivalent verification code (Contract.Requires(someBool) might be rewritten as if (!someBool) throw).

Without the code contracts, if you later reference the compiled assembly (not the project and all it's source code files) in a different solution, it may not be aware of any of the code contracts. Had a Contract Reference Assembly been created, the IDE could take into account any contracts in that assembly during static analysis.

As for the settings, here's what they mean:

  • (none) means you have not made a selection, and so no reference assembly will be created. If another assembly depends on this one and you have selected Build for it, you may receive an error/warning that "no contract reference assembly was found."

  • If you change the setting to Build, a reference assembly will be created that contains all of your contracts. You will be able to use all of the code contracts defined in that assembly as if you had the source code. Choose this if you are creating a library that will be used by a 3rd party (a NuGet package, for example) or anyone after the assembly is compiled so they will have the benefit of your code contracts in static analysis.

  • If you change the setting to DoNotBuild, no reference assembly will be built preserving your code contracts. Choose this if you don't intend for this assembly to be used anywhere else, or if all other users of the assembly will have access to the source code and not need the reference assembly. It may speed up the build a little.

David Schwartz
  • 1,956
  • 19
  • 28
  • Does it make sense to set **Contract Reference Assembly** for all projects in a Solution to `DoNotBuild` when none of those assemblies are going to be used out of that solution? Looks like code contracts are visible within the solution anyways. No? – orad Aug 05 '14 at 01:20
  • 2
    @orad Missed your comment. Yes, you can set all of them to `DoNotBuild`. This feature should only be on if, for example, you were writing a NuGet library and wanted people who installed it to see the Code Contracts therein. – David Schwartz Sep 08 '14 at 23:37
  • How would you add a reference to a project built with a CC reference assembly? Should you add both assembly to your reference list? – Etienne Maheu Nov 18 '14 at 23:35
  • @EtienneMaheu If I remember correctly, CC reference assemblies work just like _.pdb files_ and _XML documentation files_. You just make sure the assembly and its CC reference assembly are in the same folder and it should work automatically. So, say you have _Assembly.dll_ and its CC reference assembly _Assembly.Contracts.dll_. You just add a reference to _Assembly.dll_ like usual and as long as the _Assembly.Contracts.dll_ file is in the same directory as _Assembly.dll_, the Code Contracts utility will pick it up automatically. Let me know if that doesn't work. – David Schwartz Nov 19 '14 at 01:18
7

Yes, the None and DoNotBuild options seem a bit strange.

If you select None and reference the library in a Project with contracts, you will get a Warning.
If you select DoNotBuild you won't get a warning.

And of course only Build produces a reference assy, and for a .EXE it all doesn't matter.

H H
  • 263,252
  • 30
  • 330
  • 514
  • 3
    But what's the point of this setting (and this "reference assembly")? – Monsignor Jun 30 '11 at 03:05
  • It's so that you can ship the contracts separately from your release code. Some people don't want the contracts in the release code because the size of generated code to implement the contracts can be quite large. So, the thought is, during development, you want to make sure you adhere to the contracts. During release, it _may_ not be necessary to keep that contract code around. So as a consumer of a library, you just need to distribute the library code itself with your program--sans contracts, thereby decreasing your overall program distribution size. – fourpastmidnight Feb 13 '16 at 00:42