Filtering type’s by name using CQLinq (in NDepend)

I’m running NDepend against a project which also contains code from a shared application’s codebase. This “shared” code is really messing up my NDepend numbers. For example it contains some very complex methods and methods breaking a few rules my new project adhere’s to. This has the undesirable affect of meaning that the shared code can hide issues in the new code.

I cannot change this shared code without the introducing compatibility issues with the shared applications, so I simply want NDepend to ignore the types etc. from this shared code so I can see what’s happening in any new code more clearly.

As NDepend not only comes with a Linq like language (CQLinq) but also supplies us with the code for each rule and allows us to edit on a per project basis. This means we can simply alter the rule to ignore types and/or methods etc. that we’re aware of and are happy with or not wanting to change.

So let’s look at a snippet of CQLinq code which is used for the rule Do not hide base class methods.

// Define a lookup table indexing methods by their name including parameters signature.
let lookup = Methods.Where(m => !m.IsConstructor && !m.IsStatic && !m.IsGeneratedByCompiler)
      .ToLookup(m1 => m1.Name)
from t in Application.Types
where !t.IsStatic && t.IsClass &&
   // Discard classes deriving directly from System.Object
   t.DepthOfInheritance > 1 
where t.BaseClasses.Any()

As you can see, this query creates a lookup of types, using the Application.Types call. Basically this returns all types within the application being analysed (from my understanding). So if we could filter these types and exclude those which we’re unable/unwilling to change then we could still use this rule going forward but not have it failing on code we cannot do anything about.

So all we need to do is use some standard Linq code to filter the Application.Types, something maybe like this

// ignore types from external code
let filteredTypes = from filter
   in Application.Types where
   filter.Name != "MyObject"
   select filter

and replace Application.Types in the previous query so it becomes

// Define a lookup table indexing methods by their name including parameters signature.
let lookup = Methods.Where(m => !m.IsConstructor && !m.IsStatic && !m.IsGeneratedByCompiler)
      .ToLookup(m1 => m1.Name)
from t in filteredTypes
where !t.IsStatic && t.IsClass &&
   // Discard classes deriving directly from System.Object
   t.DepthOfInheritance > 1 
where t.BaseClasses.Any()

Ofcourse we might prefer to filter at a namespace or assembly level. In my case filtering out the external assemblies is a better solution in which case I simply remove the assemblies from the list of assemblies analysed by NDepend, but this technique for filtering is still useful.

It would be cool if we could use a UI such as VisualNDepend to create a “filtered” list for us, i.e. clicking on a type or method and “ignoring” it and have NDepend create a filter for us, but doing this this way ensure we’re very explicit about what to ignore.