Like other professional community groups, a software craftsmanship group is supposed to offer benefits that would make a working professional take time from their schedule to attend. These benefits come in many forms: networking, support, feedback, education, self-improvement, and the list goes on. Not all of these benefits will resonate with everyone, and there are plenty that I did not name applying to many individuals and situations. A software craftsmanship group can supplement or replace an existing group that you’re attending.
A common complaint that I hear from attendees of other groups is about how the discussions at dinner after the meeting is the most worthwhile part of the meeting. When I hear this, my first instinct is that these people need to start going to software craftsmanship meetings in addition to or instead of their current groups.
What is Software Craftsmanship?
Software craftsmanship is often described as a movement in the software industry of like-minded people who believe in a set of values which can improve the software we write. The Software Craftsmanship Manifesto describes in what these like-minded individuals believe.
I’ve often found it interesting how the Software Craftsmanship movement seems to be an extension of the agile software development movement. I and most of the members of the Hudson Software Craftsmanship group are all developers who either work at companies follow some form of agile development or are trying to move towards it. In fact the 4 main values described in the Software Craftsmanship Manifesto specifically describe how in the attempt to achieve the values described by the Agile Software Manifesto these ones were found to be indispensible. It is the idea that pursuing one set of values that have proven to be very useful, another set has been found to be extremely valuable.
Dispelling Misinformation
There are some people who have bad opinions of software craftsmanship, and I’d like to take some time to address some of those concerns incase any readers have heard of them or share them.
It’s not elitist.
I’ve heard software craftsmanship referred to as being elitist. In my experience, this is entirely not the case. I would believe that there are people among the community that fit this description, but those people would be outliers. We are welcoming of people of all skill levels who are looking to write cleaner, better software. I for one don’t even think that everyone will or even should be software craftsmen. If you enjoy the way you’re doing this, by all means continue. I don’t believe that my methods, practices, values, and beliefs are any better than anyone else’s. We are a group that shares our beliefs and want to work together to improve ourselves.
It’s not ALT.NET.
I’ve heard Software Craftsmanship compared to ALT.NET by some people, and I can see why the comparison would be made. Both are movements in the software industry to try to do things better than we have been doing them in the past. The ALT.NET community is like-minded individuals in the .NET community who are against the direction, guidance, and tooling that has/had been coming from Microsoft. While I do not follow that guidance either, I am not openly against it. In fact, I realize that the methods that I believe in and use in my own development will not work for everyone.
Software Craftsmen will help each other move away from that tooling and guidance, because the people we are helping want to move away from it. For many developers the control-based, do everything for me approach that often comes with that tooling is perfectly acceptable. There are many developers who are not going to follow the SOLID principles, and they’re not going to be inverting dependencies and writing unit tests either. That’s OK! Other people are not wrong just because I think I can write better code by doing things differently.
It’s not just about code.
Many developers are afraid that software craftsmanship places too much of a focus on writing code. From looking at software craftsmanship from the outside, this is a very valid argument to make. It is, however, mostly based on what is made visible from outside.
The aspects of a software craftsmanship group meeting which people go home and blog about tend to be the katas, exercises, and techniques. Why? Because it is not as easy to bottle up a great blog post on an open discussion among a large group as it is to post about some cool programming exercise. Our community as a whole also tends to really like posts showing source code, so people return from the meeting and post their exercise results. We’re more about thinking and improving our entire development process than just code.
We focus on the micro through programming as well as the macro through community involvement. We focus on how to improve as a business, how to work better with our clients, customers, and peers, and how to do all of this slowly with manageable, incremental change.
What Happens at a Craftsmanship Group?
Our main focus at a software craftsmanship group is to reinforce the skills, beliefs, values, and principles of our members. We have discussions, which are based on topics in the industry. We want everyone thinking, questioning, and improving. We don’t want you to even accept things that other craftsmen tell you. Go to the meeting ready to question others. We need to back up our thoughts and ideas, and most of all we need to be willing to try new things.
Why lightning talks?
Most user groups feature a single person transferring knowledge to the masses who attend the group. In these situations the knowledge flow is unidirectional, and we don’t find that to be as effective as having people of all skill levels discussing the topic. A lightning talk is a great way to introduce a topic by spending 5 to 10 minutes discussing introducing the topic briefly. These talks then open the floor for immediate continued discussion or become ideas for later open discussions at the group.
Why open discussions?
Discussions allow us to share our ideas and get feedback on them. We will often discuss values and principles of craftsmanship. We also use this as a chance to discuss how we’re each solving some similar challenge we’re all facing. Some topics we’ve done in the past revolve around automated unit testing. These often are focused on some type and how to do them better. I recently was involved in a craftsmanship discussion revolving around the concept of BDD and went from low to high level. Some topics deal less with coding than the infrastructure we as developers depend on like our continuous build implementations and our database change management systems. Other common topics deal with how to get buy-in from a business to follow the practices that we believe to be beneficial.
Why code katas?
A kata is designed to give you a consistent experience doing the right things. Like the martial arts equivalent it is not something you would use in a real-world situation, but it is designed to emulate one. It goes through a set of steps where a master of the art has imparted wisdom by showing the steps to be taken when presented with certain challenges. These katas will let you know how and why the master takes certain steps at certain points and are designed to be repeated so that we immediately respond with the correct solution when presented with a certain challenge.
Why programming exercises?
We have all learned to program, and we need to keep ourselves in practice. No, our day jobs are not practice. Exercises are designed to give us practice so that we have recent experience solving challenging problems to assist in our everyday programming tasks. Many people believe that comparing software developers to musicians or athletes is a stretch, and I will agree with them that there are great differences between these groups. We are, however, all skilled individuals and if we’re even remotely similar to the musician or the athlete, then we need to also be practicing.
I’ve been presented with many real-world challenges where I say, “I can use the same technique here that I use when solving the Greed kata.” That being one example of a programming exercise where I have tried solutions and found some that work very well with the practices and techniques that help me write cleaner code.
What should I do next?
Find a local group of software craftsmen. If there is not one in your area or the one in your area is more than an hour drive to get to, then start one. Gauge the interest, and start making noise about it. Other people interested will join the group, share their ideas, experiences, and trials, and keep the group interesting.
Good luck!
The Software Craftsmanship group that I run is located in Hudson, OH. We are between Cleveland and Akron, and we have members from both of those locations. If you're in the area, we look forward to seeing you at one of our events.
NuGet is best described as the tool from Microsoft that lets you add references to your project directly from the NuGet feed while storing and managing them locally. It lets you keep your references local to your source code, which will help you keep your software project encapsulated. When a package you use gets an update, you can ask NuGet to update your local version of the package.
When telling people about NuGet it is important to explain how powerful it really is. NuGet is not just a collection of libraries to include in your bin folder. It will actually install the package into your project. I will show you what I mean.
Installing NuGet
NuGet can be installed through the Visual Studio Extension Manager. From within Visual Studio, open the Tools menu and select Extension Manager. Once in that window, select the Online Gallery and search for “nuget”. Then you just have to tell it to Download nuget. This will require a restart of Visual Studio.
Using NuGet to Install a Package
Now that NuGet is installed we can start using it. There are two ways to do this, and I will start with the one that is the easiest. All we need to do is right click on out project’s references folder and select “Add Library Package Reference…”
From the window that opens, we want to make sure that we select the Online section on the left and select All. Now we use the search box to search for the package that we’re trying to install. And we click the Install button. NuGet will get the package you requested as well as any Dependencies listed. Notice in the following image that WebActivator is listed as a dependency of this package. NuGet packages will often add files other than just dlls to your solution. Isis, which is the package shown here will also include its own bootstrapper, which will allow Isis to have routes mapped for itself, so you can begin using the application immediately.
Viewing the Results of Installing a Package From NuGet
Thanks to packages being able to includes these files allowing themselves to be automatically configured, I already have the Isis ASP.NET Control Panel installed. It’s not just a reference in my bin folder, it also gave me this bootstrapper file. I don’t have to do any extra work installing Isis.
Thanks to NuGet getting me all the files I can navigate to the Isis ASP.NET Control and begin using it immediately.
There is also a command line interface for NuGet. If that is your cup of tea, then I recommend checking it out instead.
The Isis ASP.NET Control Panel
In case you are wondering about the Isis package that I installed, it is a relatively new Open Source project based on a few projects that Steve Smith and I have worked on in the past. We are creating an ASP.NET control panel which can be easily installed (as you’ve seen already) into any ASP.NET application and provide tools to help manage, develop, and diagnose the application.
I learned this potentially very useful bit of information from Scott Forsyth recently. As you may know, IIS 7 is modular, which allows for a great deal of control and customization of an IIS installation. There are a lot of other great benefits also. Web servers are great tools that allow us to put our content on the web. One of the most powerful things is their support for creating dynamic sites through different programming frameworks and languages. We sometimes take for granted our having static content in our web server. The static content is all of the common content on a site, which is not dynamic. In general this means our htm, html, and image files.
If you’re ever not serving that content then you should make sure that your IIS installation is set up to serve that content using these steps.
Open up the control panel and click on the Programs category.
<p><strong>Click on “Turn Windows features on or off” in the Programs and features section.</strong></p> <p><a href="/images/files/Programs.png"><img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="Programs" border="0" alt="Programs" src="/images/files/Programs_thumb.png" width="480" height="340"></a></p> <p><strong>Expand in the tree view in this order:</strong> <em>Internet Information Services</em><strong>,</strong> <em>World Wide Web Services</em><strong>, </strong><em>Common HTTP Features</em><strong>. Then make sure that</strong> <em>Static Content</em> <strong>is checked.</strong></p> <p><a href="/images/files/WindowsFeatures.png"><img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="WindowsFeatures" border="0" alt="WindowsFeatures" src="/images/files/WindowsFeatures_thumb.png" width="360" height="412"></a></p> <p>If that was unchecked and you checked it and clicked OK, then you should be all set and serving static files like images and html pages in your web site.</p> <p>Not really sure why someone would want to turn that off, but at least it is easy to turn that setting back on.</p>
I've been reading plenty of blog posts about Software Craftsmanship including a nice response by Uncle Bob. I ran a Software Craftsmanship precompiler workshop at CodeMash again this year, and I've even seen some good feedback and follow up from attendees. If you're in the area, I really recommend coming out to CodeMash next year. I am hoping to be there again next year doing the Software Craftsmanship precompiler.
Back in 2009, Steve Smith, Rich Henning, and I got together and discussed how we were going to create the Hudson Software Craftsmanship group. We figured out some times to meet and what types of exercises we would do. The group has had a steady group of attendees over this time period. We use a room that if we're prepared can fit about 30 people. Our usual group is between 15 and 25 people who show up ready to discuss software craftsmanship, values, principles, practices, unit testing, quality, and just about anything else. We get just enough people to have some really great discussions. Our next meeting is actually tonight and right now we have 28 people signed up for the event. We found some things to focus on and we did. We're all about lightning talks, discussions, and improving our coding abilities.
In short, I've got Software Craftsmanship on the mind right now. I might as well spend some time discussing it.
I think Software Craftsmanship started as a good banner to rally behind in the fight to end crappy code. There are plenty of reasons why code might have been crappy, and I am all for rallying behind the banner of good, clean code. We're not talking about agile or lean when we talk about Software Craftsmanship, however, most craftsman are also supporting lean practices. In software craftsmanship we focus on the people, their relationships, and the code they write. I think in this sense, Software Craftsmanship can apply for any agile methods you use or even on a waterfall project. We're talking about writing code that fits the situation, which means in a lot of cases we need to cut down on the crap. We're more than that though. We're about making customers happy (sometimes the customers are just our bosses.) We are also trying to become better developers as a community. We need to help each other. The best developers in the world are the ones who have learned from other developers. You can never be great if you don't learn from others.
One of people's favorite terms to use is quality. It really has a meaning that is easy to define in generic terms, but is very difficult to nail down in terms if a quantity. I think we could all define quality in some way, but I think that we cannot determine the quality of code very well. It is very subjective, since people's definitions of quality and how they apply it are different. I think, however, that it is a central point in Software Craftsmanship. For that reason it is something that we should strive to understand and evaluate. If I were to give an important trait for a Software Craftsman to have it is the ability to determine and evaluate quality. Use whatever measure you like, but be able to understand quality and how to evaluate it depending on the circumstances of the code you're writing. Your definition of quality need not even match everyone else's.
A topic that I've heard Steve Smith argue with people over plenty of times is whether or not a software craftsman should knowingly write low quality code. This usually comes up when the customer specifically wants you to write crap. The customer might even say that they'd rather have the product done sooner with bugs rather than have the code take any longer. I've heard some good arguments on both sides. To throw my two cents in, I'll just say that it really depends on the situation that you're evaluating.
I didn't have as good of a perspective on this topic until a great discussion on this very topic broke our during a HudsonSC meeting in which Joe Brinkman gave some very good arguments for why a software developer might not want to put extra time into code. His point was that for a startup, there is a better than average chance that you will be throwing the code away soon. You do not know if this code will ever be used again. It might be gone in a few months.
I admit in most situations I would argue for having higher quality code, but in the case of a startup I think there is good reason to write code fast and get something working. I think it is assumed for some startups that their code might have bugs or other issues. My interpretation of what Joe was saying is that the business might not even be a good one, so in those instances the software need only provide the basic functionality of the idea. If it is missing features or has some bugs you can still tell if the idea is something that the market is interested in. Startups have a completely different mindset. You need to quickly and cheaply find out if the business idea is going to work before your run out of funding. If I am interpreting him correctly he is basically talking about throw-away businesses not just throw-away apps. You keep starting and tossing businesses until one of them succeeds. I think in this situation, the code can reflect the business. Once the longevitiy of the business is determined, quality can be brought back into the mix.
To look at things from a different perspective, we can take the groups of people we have that attend HudsonSC who work at banks, insurance companies, and healthcare companies. All of these are long-standing businesses that need to maintain quality code at all times. It is these who have the traditional opinions on SoftwareCraftsmanship. These groups have no reason to lower quality. In fact if they don't maintain quality, they could have serious issues. I think most of us are in the boat where we expect the business we're working for to still exist in 6 months. This means that our code needs to survive and maintain for years after we first write it.
A software craftsman should know what customers want and be able to provide code which offers the value the customer is looking for. It is up to a craftsman to determine what solution is the best one for the job and be prepared to provide the highest quality code possible. In this instance I will say that the level of quality in the code is one that should be determined by the developer and the customer.
No MVVM solution is complete without having the DataContext bound to a ViewModel, but this wouldn’t be a fun development community if there were not some disagreement on the specifics of how to achieve certain goals. I will be recommending how I like to wire up ViewModels. There are other ways of doing this, but I will explain some of the reasons I use this method.
You can start by building a View that needs to have certain traits in its ViewModel and then create a well-tested ViewModel separately. This ViewModel should have all of the properties and data required by the View. Make sure you also have any commands or other functionality the View will require. It is then your job to make the connection between these two objects. The way I like doing this is by using a Service Locator to give my View the ViewModel it needs. This also gives me a good centralized location where I can make sure that my ViewModels are wired up the way I need them to be.
To create our service model we are going to need to create a class which has methods returning the ViewModels we are using in our Views. We should have one getter per ViewModel to be requested. I tend to use names matching the name of the ViewModel for the getters. The service locator will look a bit like this when you’re done. (You can also use an IoC container in the service locator, which is what I do in all of my production code. In that case you would just use the IoC container rather than instantiating the object as is done in this example.)
Code Listing 1 – The Service Locator:
public class ServiceLocator
{
public AwesomeViewModel AwesomeViewModel
{
get { return new AwesomeViewModel(); }
}
}
Notice that I can pass in any parameters needed for the ViewModel constructor so my ViewModel can depend on abstractions. The service locator can be more complicated than this if other work needs to be done to create these ViewModels. An example of such a situation is if I have shared dependencies or I am using an IoC container to create my objects.
Now that we have our code written to get us our ViewModel object we need to make this class available to all of our Views. This can be achieved by creating an instance of one of these as a static resource in our App.xaml file. Static resources defined here are easily accessible.
Code Listing 2 – Declaring the Service Locator as a Resource in App.xaml:
<Application x:Class="Awesome.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:Awesome="clr-namespace:Awesome"
StartupUri="MainWindow.xaml">
<Application.Resources>
<Awesome:ServiceLocator x:Key="SvcLoc" />
</Application.Resources>
</Application>
The key that we have assigned to this resource is how we will reference it when we access it later. In other parts of our code we will just specify in our bindings that we are accessing this static resource and calling its properties to get the data that we need. In fact this is exactly how we can get our ViewModel into our View. When we bind our DataContext we will tell it that our source is going to be this ServiceLocator instance and that we are binding our DataContext to a specified path, which is a property of the ServiceLocator.
The binding can be done either of these two ways. I don’t really prefer one or the other. These are effectively the same things, so it really comes down to preference.
Code Listing 3 – Binding the DataContext to the ServiceLocator:
<Window.DataContext>
<Binding Path="AwesomeViewModel"
Source="{StaticResource SvcLoc}"/>
</Window.DataContext>
Code Listing 4 – Binding the DataContext to the ServiceLocator Inline:
DataContext="{Binding AwesomeViewModel, Source={StaticResource SvcLoc}}"
Now we can access this DataContext throughout our View by just binding to different paths on it.
I like this approach because it keeps the binding in the XAML and not in the code. It is also nice because we are able to bind easily to properties and have these properties do dependency injection for our ViewModels. The centralization of all of this ViewModel creation is also very convenient. We are able to visit this one class to make adjustments for how the entire application handles its ViewModel initialization.