DaedTech

Stories about Software

By

Intro to T4 Templates: Generating Text in a Hurry

Editorial Note: I originally wrote this post for the SubMain blog.  You can check out the original here, at their site.  While you’re there, take a look at GhostDoc.  In addition to comment generation capabilities, you can also effortlessly produce help documentation.

Today, I’d like to tackle a subject that inspires ambivalence in me.  Specifically, I mean the subject of automated text generation (including a common, specific flavor: code generation).

If you haven’t encountered this before, consider a common example.  When you file->new->(console) project, Visual Studio generates a Program.cs file.  This file contains standard includes, a program class, and a public static void method called “Main.”  Conceptually, you just triggered text (and code) generation.

Many schemes exist for doing this.  Really, you just need a templating scheme and some kind of processing engine to make it happen.  Think of ASP MVC, for instance.  You write markup sprinkled with interpreted variables (i.e. Razor), and your controller object processes that and spits out pure HTML to return as the response.  PHP and other server side scripting constructs operate this way and so do code/text generators.

However, I’d like to narrow the focus to a specific case: T4 templates.  You can use this powerful construct to generate all manner of text.  But use discretion, because you can also use this powerful construct to make a huge mess.  I wrote a post about the potential perils some years back, but suffice it to say that you should take care not to automate and speed up copy and paste programming.  Make sure your case for use makes sense.

The Very Basics

With the obligatory disclaimer out of the way, let’s get down to brass tacks.  I’ll offer a lightning fast getting started primer.

Open some kind of playpen project in Visual Studio, and add a new item.  You can find the item in question under the “General” heading as “Text Template.”

newtexttemplate

Give it a name.  For instance, I called mine “sample” while writing this post.  Once you do that, you will see it show up in the root directory of your project as Sample.tt.  Here is the text that it contains.

<#@ template debug="false" hostspecific="false" language="C#" #>
<#@ assembly name="System.Core" #>
<#@ import namespace="System.Linq" #>
<#@ import namespace="System.Text" #>
<#@ import namespace="System.Collections.Generic" #>
<#@ output extension=".txt" #>

Save this file.  When you do so, Visual Studio will prompt you with a message about potentially harming your computer, so something must be happening behind the scenes, right?  Indeed, something has happened.  You have generated the output of the T4 generation process.  And you can see it by expanding the caret next to your Sample.tt file as shown here.

samplett

If you open the Sample.txt file, however, you will find it empty.  That’s because we haven’t done anything interesting yet.  Add a new line with the text “hello world” to the bottom of the Sample.tt file and then save.  (And feel free to get rid of that message about harming your computer by opting out, if you want).  You will now see a new Sample.txt file containing the words “hello world.”

Read More

By

Have You Seen the NDepend API?

Editorial Note: I originally wrote this post for the NDepend blog.  You can check out the original here, at their site.  While you’re there, download NDepend and give it a try.

If you’re familiar with NDepend, you’re probably familiar with the Visual Studio plugin, the out of the box metrics, the excellent visualization tools, and the iconic Zone of Uselessness/Zone of Pain chart.  These feel familiar to NDepend users and have likely found their way into the normal application development process.

NDepend has other features as well, however, some of which I do not necessarily hear discussed as frequently.  The NDepend API has membership in that “lesser known NDepend features club.”  Yes, that’s right — if you didn’t know this, NDepend has an API that you can use.

You may be familiar, as a user, with the NDepend power tools.  These include some pretty powerful capabilities, such as duplicate code detection, so it stands to reason that you may have played with them or even that you might routinely use them.  But what you may not realize is the power tools’ source code accompanies the installation of NDepend, and it furnishes a great series of examples on how to use the NDepend API.

NDepend’s API is contained in the DLLs that support the executable and plugin, so you needn’t do anything special to obtain it.  The NDepend website also treats the API as a first class citizen, providing detailed, excellent documentation.   With your NDepend installation, you can get up and running quickly with the API.

Probably the easiest way to introduce yourself is to open the source code for the power tools project and to add a power tool, or generally to modify that assembly.  If you want to create your own assembly to use the power tools, you can do that as well, though it is a bit more involved.  The purpose of this post is not to do a walk-through of setting up with the power tools, however, since that can be found here.  I will mention two things, however, that are worth bearing in mind as you get started.

  1. If you want to use the API outside of the installed project directory, there is additional setup overhead.  Because it leverages proprietary parts of NDepend under the covers, setup is more involved than just adding a DLL by reference.
  2. Because of point (1), if you want to create your own assembly outside of the NDepend project structure, be sure to follow the setup instructions exactly.

Read More

By

Generate Documentation from Your Build

Editorial Note: I originally wrote this post for the SubMain blog.  You can check out the original here, at their site.  While you’re there, have a look at GhostDoc.

Before I get down to the brass tacks of how to do some interesting stuff, I’m going to spin a tale of woe.  Well, I might have phrased that a little strongly.  Call it a tale of corporate drudgery.

In any case, many years ago I worked briefly in a little department, at a little company that seemed to be a corporate drudgery factory.  Oh, the place and people weren’t terrible.  But the work consisted of, well, drudgery.  We ‘consulted’ in the sense that we cranked out software for other companies, for pay.  Our software plumbed the lines of business between client CRMs and ERPs or whatever.  We would write the software, then finish the software, then hand the software over, source code and all.

Naturally, commenting our code and compliance with the coding standard attained crucial importance.  Why?  Well, no practical reason.  It was just that clients would see this code.  So it needed to look professional.  Or something.  Didn’t matter what the comments said.  Didn’t matter if the standard made sense.  Compliance earned you a gold star and a move onto the next project.

As I surveyed the scene surrounding me, I observed a mountain of vacuous comments and dirty, but uniform code.

My Complex Relationship with Code Comments

My brief stay with (and departure from) this organization coincided with my growing awareness of the Software Craftsmanship movement.  Even as they copy and pasted their way toward deadlines and wrote comments announcing that while(x < 6) would proceed while x was less than 6, I became interested in the idea of self-documenting code.

Up to that point, I had diligently commented each method, file, and type I encountered.  In this regard, I looked out for fellow and future programmers.  But after one too many occasions of watching my own comments turn into lies when someone changed the code without changing the comments, I gave up.  I stopped commenting my code, focusing entirely on extractions, refactoring, and making my code as legible as possible.

I achieved an equilibrium of sorts.  In this fashion, I did less work and stopped seeing my comments become nasty little fibs.  But a single, non-subtle flaw remained in this absolutist approach.  What about documentation of a public (or internal) API?

Naturally, I tried to apply the craftsmanship-oriented reasoning unilaterally.  Just make the public API so discoverable as to render the issue moot.  But that never totally satisfied me because I still liked my handy help screens and Intellisense info when consuming others’ code.

And so I came to view XML doc comments on public methods as an exception.  These, after all, did not represent “comments.”  They came packaged with your deliverables as your product.  And I remain comfortable with that take today.

Read More

By

How to Perform Effective Team Code Reviews

Editorial Note: I originally wrote this post for the NDepend blog.  You can check out the original here, at their site.  While you’re there, check out all of the new tech debt-related features in the newest version of NDepend.

I’ve heard people say (paraphrased) that teams succeed uniformly, but fail each in its own unique way.  While I might argue the veracity of this statement, it evokes an interesting image.  Many roads, lined with many decisions, lead to many different sorts of failures.

Code review presents no exception.  Teams can fail at code review in myriad, unique ways.  And, on top of that, many paths to broader failure can involve poor code reviews (doubtless among other things).

How can I assign such importance to the code review?  After all, many would consider this an ancillary team activity and one with only upside.  Done poorly, code review catches no defects.  Done well, it catches some defects.  Right?

How Code Review Can Go Wrong

Simply put, code review can have worse than zero effect.  Ineffectual code review suffers mainly the opportunity cost of the participants’ time.  But toxic code review creates morale problems, counterproductive team dynamics, and damaging distractions.

So the first order of business is to avoid a net negative effect.  To do this, one simply has to remove the potential of toxic culture from the process of code review.  Of course, that’s a bit easier said than done, but a lot of it just means following basic rules of human decency.  Start by treating one another with respect.  Then ensure that all participants feel comfortable getting and receiving feedback.  Enlist the help of even-tempered, charismatic folks to lead by example.

Once you’ve insulated yourself against the most damaging effects, it’s time to guard against ineffectual code reviews.  It is toward that end that I’ll be focusing for the remainder of this post.  Ineffectual code reviews can ways time, as I mentioned earlier.  But they can also create a false sense of security and lead to poor choices.

So what makes code review effective?  How can your team get the most out of this activity?  I’ll offer some thoughts based on firsthand experience across a wide number of organizations.

Read More

By

Considering a Port to .NET Core? Use NDepend

Editorial Note: I originally wrote this post for the NDepend blog.  You can check out the original here, at their site.  While you’re there, take a look at the latest version of NDepend, with extensive features around technical debt measurement.

An American colloquialism holds, “only two things are certain: death and taxes.”  If I had to appropriate that for the software industry, I might say that the two certainties are death and legacy code.  Inevitably, you have code that you have had for a while, and you want to do things with it.

Software architects typically find themselves tasked with such considerations.  Oh, sure, sometimes they get to pick techs and frameworks for greenfield development.  Sometimes they get to draw fancy diagrams and lay out plans.  But frequently, life charges them with the more mundane task of “figuring out how to make that creaky old application run on an iPhone.”  Okay, maybe it’s not quite that silly, but you get the idea.

If you earn a living as an architect in the .NET world, you have, no doubt, contemplated the impact of .NET Core on your application portfolio.  Even if you have no active plans to migrate, this evolution of .NET should inform your strategic decisions going forward.  But if you have use for deploying the framework along with your application or if you want to run on different operating systems, you’re going to need to port that legacy code.

I am, by no means, an expert in .NET Core.  Instead, my areas of specialty lie in code analysis, developer training, and IT management and strategy consulting.  I help dev teams create solutions economically.  And because of this, I can recognize the value of NDepend to a port from what I do know about .NET core.

Read More