+ All Categories
Home > Documents > How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build...

How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build...

Date post: 29-Dec-2015
Category:
Upload: blaise-hawkins
View: 217 times
Download: 0 times
Share this document with a friend
32
How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013
Transcript
Page 1: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

How to make the most of Code Analysis

Patrick Smacchia

NDepend Creator and Lead Developer

Build Stuff Lithuania - 11th Dec 2013

Page 2: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Introduction to NDependContract, Unit Test and Code CoverageDesigning to make the UI testableDetect regressions early with Code RuleOn Clean Code Structure

Page 3: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Introduction to NDepend

Page 4: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Tool for .NET Developers I’ve created in April 2004Became commercial in February 2007Tool specialized in static analysis of .NET code

Integrate in Visual Studio (2013, 2012, 2010, 2008) Integrate in Build Process to produce reports

Soon 4.000 companies client worldwide JArchitect (for Java) CppDepend (for C++)

NDepend Facts

Page 5: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Code Rules written with C# LINQ syntaxDependency Graph and MatrixCode DiffCode Metrics, Treemap Trending Code Coverage…

NDepend Features

Page 6: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

How do we use NDepend to build NDepend?

Page 7: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Contract, Unit Test, Code Coverage

Page 8: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Microsoft Code Contract librarySuitable for the public surface of your product APIStandardized (documentation, compiler check…)Not adapted for an intensive usage (slow compilation)

System.Diagnostics.Debug.Assert()Adapted for an intensive usage, everywhere in your codeOnly work in DEBUG modeAt least it doesn’t slow down production execution

Code Contracts in .NET

Page 9: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Pretty much the same thing. Really!!

In both cases we want to check for assertions. In both cases we want a failure if a condition is not

fulfilled, because it means correctness violationCode Contracts MUST fail if not fulfilled at unit test

running timeAdvantage: You can run an automatic test with few

assertions, but still get the contracts assertions verified.

Code Contracts vs. Unit Tests

Page 10: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

100% ! … less is not enough!Often we hear: the last 10% are too costly to be coveredWhy is it too costly?

Because this last 10% code is not well testableHence it is not well designedHence it is error-prone

Nobody wants to let the most error-prone code uncovered by test, do you?

How much Code Coverage is needed?

Page 11: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

100% … at least needed for core business logic classes that contain the application complex logic

NDepend entire code base: 79% covered100% coverage also means all contracts get checked Isolate in some special classes uncoverable code

Blocking methods: MessageBox.Show() OpenFileDialog()

Hard to repro error cases: IO.UnauthorizedException catch

How much Code Coverage is needed?

Page 12: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

3 major .NET tools to obtain Code Coverage from automatic tests run: VS Code CoverageJetBrains dotCoverNCover

Ndepend can import Code Coverage from any of these tools

Code Coverage

Page 13: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend rules and Code Coverage

// <Name>Types tagged with FullCoveredAttribute should be 100% covered</Name>warnif count > 0 from t in Application.Types where t.HasAttribute ("NDepend.Attributes.FullCoveredAttribute".AllowNoMatch()) && t.PercentageCoverage < 100 let notFullCoveredMethods = t.Methods.Where( m => m.NbLinesOfCode> 0 && m.PercentageCoverage < 100 && !m.HasAttribute("NDepend.Attributes.UncoverableByTestAttribute".AllowNoMatch())) select new { t, t.PercentageCoverage, t.NbLinesOfCodeNotCovered, notFullCoveredMethods, t.NbLinesOfCode, t.NbLinesOfCodeCovered }

 

Page 14: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend rules and Code Coverage

// <Name>Types 100% covered should be tagged with FullCoveredAttribute</Name>warnif count > 0 from t in JustMyCode.Types where !t.HasAttribute ("NDepend.Attributes.FullCoveredAttribute".AllowNoMatch()) && t.PercentageCoverage == 100 && !t.IsGeneratedByCompilerselect new { t, t.NbLinesOfCode }

Page 15: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend rules and Code Coverage

// <Name>From now, all types added or refactored should be 100% covered by tests</Name>warnif count > 0 from t in JustMyCode.Types where  // Match methods new or modified since Baseline for Comparison... (t.WasAdded() || t.CodeWasChanged()) &&  // ...that are not 100% covered by tests t.PercentageCoverage < 100  let methodsCulprit = t.Methods.Where(m => m.PercentageCoverage < 100) select new { t, t.PercentageCoverage, methodsCulprit }

Page 16: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend rules and Code Coverage

// <Name>Types that used to be 100% covered but not anymore</Name>warnif count > 0from t in JustMyCode.Types where t.IsPresentInBothBuilds() && t.OlderVersion().PercentageCoverage == 100 && t.PercentageCoverage < 100let culpritMethods = t.Methods.Where(m => m.PercentageCoverage < 100)select new {t, t.PercentageCoverage, culpritMethods }

Page 17: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Designing to make the UI testable

Page 18: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

A kernel object, referencing a grape of objects, that is shared amongst all UI panels

The kernel hold access toApplication states (currently running an analysis?, session opened? …)

Application context (user preferences, licensing options, theme…)

Application actions (open/close session, show/hide panel…)

Session states (analysis result loaded, diffed?…)

Session actions (build a graph, edit a code query…)

NDepend UI Design

Page 19: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend UI Design

Page 20: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Suitable to write UI integration tests, that pilot the UI.Not much assertions are done in unit-tests bodies ……but thousands of code contracts nested in UI code are

covered by test run. Hence they are checked!

NDepend UI Design and Tests

foreach (var panelKind in new[] { PanelKind.StartPage, PanelKind.ProjectProperties, PanelKind.Matrix, PanelKind.Graph…}) { InvokeOnUIThread( () => m_Kernel.App.Actions.SetActivePanel(EventSender.Main, panelKind)); InvokeOnUIThread( () => m_Kernel.App.Actions.ShowPanel(EventSender.Main, panelKind));}

Page 21: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

NDepend UI Design RuledGeneric rules can be written to enforce design decisions

like: Panels shouldn’t use each other

Demo

//<Name>Panels shouldn't use each others</Name>warnif count > 0let panelsNamespaces = Application.Namespaces .WithNameWildcardMatch("NDepend.UI.Panels.*") from nUser in panelsNamespaces.UsingAny(panelsNamespaces)from nUsed in panelsNamespaces.UsedByAny(panelsNamespaces)where nUser.IsUsing(nUsed) select new { nUser, nUsed }

Page 22: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Detect Regressions early with Code Rules

Page 23: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Code Rules like Types that used to be 100% covered but not anymore

Methods that could have a lower visibility

Avoid transforming an immutable type into a mutable one

Potentially dead Types

Class with no descendant should be sealed if possible

Constructor should not call a virtual methods

Not so much about keeping the code clean for the sake of it.

Code Rules

Page 24: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

More often than not, a green rule that suddenly gets violated, sheds light on a non-trivial bug.

It is all about regression. It is not intrinsically about the rule violated……but about what happened recently, that provoked a

green code rule to be now violated.Demo!

The importance of Green Zone

Page 25: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

On Clean Code Structure

Page 26: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

What’s common about most of projects packaged into one large assembly?Nancy.dllNHibernate.dllMscorlib.dllSystem.dll

The code is completely entangled into namespaces dependencies cycle!

Common structure problem

Page 27: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

The problem comes from the lack of definition of the notion of components in .NET.A component is a group of cohesive classes (cohesive in the

sense, one get used => all get used).There is no clear definitions about how to package these

classes other than the notion of .NET assembly (or VS project).

Consequences: Real-world applications are made of hundreds of .NET assemblies

Only one structure rule: Avoid cycles

Page 28: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

But .NET assembly is a physical artefact:One assembly one physical fileNot fun to deploy hundreds of assembliesNot fun to reference dozens of assemblies of a library (and

maintain these referenced)

A component is a logical artefactFiner-grained than assembly => an assembly should

contain many componentsThis is why I advocate namespace to be the right

granularity to define component

Only one structure rule: Avoid cycles

Page 29: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

250 namespaces spawned over 10 assemblies

Design of NDepend

Page 30: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

For a public API, its practicaly impossible!For an application the code rule Avoid namespace

mutually dependent usually gives good hints about what to do, How?

Because developers usually know about high level and low level code.

For example, the rule say that mscorlib System namespace shouldn’t use any other namespace

Typically, resolving all namespaces mutually dependent will result into a well layered code structure.

How to get rid of cycles?

Page 31: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Two ways to get rid of an unwanted namespace dependency:Move type(s) from one namespace to anotherCreate an Inversion of Control by defining abstractions

(interfaces), in a new lower namespaceTry it! This is much cheaper to achieve than expected, and

getting rid of spaghettis is priceless! Because only code structure is touched (class def,

interfaces def, namespace def)Code flow (method bodies) is left untouched.

How to get rid of cycles?

Page 32: How to make the most of Code Analysis Patrick Smacchia NDepend Creator and Lead Developer Build Stuff Lithuania - 11th Dec 2013.

Introduction to NDependContract, Unit Test and Code CoverageDesigning to make the UI testableDetect regressions early with Code RuleOn Code Structure

Questions?


Recommended