I have created another (hopefully useful) checkin policy for Team Foundation Server 2008 - one that checks C# and VB.NET project files for COM references. The idea came from a customer, where they require the developers to use "authorized" interop assemblies instead of developers recreating those by simply adding a COM reference to each and every project. And how do you prevent this? By having a TFS checkin policy in place.
A COM reference looks like this in an MSBuild project file:
<ItemGroup>
<COMReference Include="XcpControlLib">
<Guid>{283C8576-0726-4DBC-9609-3F855162009A}</Guid>
<VersionMajor>1</VersionMajor>
<VersionMinor>0</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>tlbimp</WrapperTool>
<Isolated>False</Isolated>
</COMReference>
</ItemGroup>
Instead of searching for the string "<COMReference" I decided to use the MSBuild Engine API in my implementation:
public override PolicyFailure[] Evaluate()
{
PendingChange[] checkedFiles = PendingCheckin.PendingChanges.CheckedPendingChanges;
ArrayList failures = new ArrayList();
foreach (PendingChange change in checkedFiles)
{
string extension = Path.GetExtension(change.LocalItem);
if ((0 == String.Compare(extension, ".csproj", false)) ||
(0 == String.Compare(extension, ".vbproj", false)))
{
if (change.ChangeType == ChangeType.Edit || change.ChangeType == ChangeType.Add)
{
// this is a workaround because project.Load(fileName doesn't work in the same process as VS
FileStream fs = File.OpenRead(change.LocalItem);
Project project = new Project();
project.Load(new StreamReader(fs), ProjectLoadSettings.IgnoreMissingImports);
foreach (BuildItemGroup big in project.ItemGroups)
{
foreach (BuildItem bi in big)
{
if (0 == String.Compare(bi.Name, "COMReference", true))
{
PolicyFailure failure = new PolicyFailure(String.Format(ComReferencePolicyStrings.activateMessage, change.LocalItem), this);
failures.Add(failure);
}
}
}
}
}
}
return (PolicyFailure[])failures.ToArray(typeof(PolicyFailure));
}
At first, I tried to load directly from the .??proj files, but Visual Studio (after thinking a bit about it it is pretty obvious...) doesn't like someone inside its process play around with the MSBuild engine. That's why I resorted to loading it indirectly.
For installation I have provided checkinpolicy.reg, however, you must adapt the path to the .dll before importing it into the registry.
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\9.0\TeamFoundation\SourceControl\Checkin Policies]
"ChrisOnNet.CheckinPolicies.ComReferencePolicy"="C:\\Work\\ChrisOnNet.CheckinPolicies.ComReferencePolicy.dll"
Once registered, you can add it to your team projects:

As usual I have included the source code (BSD licensed) in the download:
ChrisOnNet.CheckinPolicies.ComReferencePolicy.zip (35.35 KB)