XP Days at Spotify

2 Comments

Screen Shot 2015-10-30 at 1.08.46 PMToday I had the pleasure of hosting the second day of a two day XP style workshop with some incredible developers at Spotify. Here’s what we did.

Build something fast!

We kick things off by asking the class to build a Reverse Polish Notation (RPN) style calculator. In 10 minutes.

We do this partially by design – to create a little stress. But it’s also an ice breaker. Just to verify everyone’s machine is up and running. As well as gauge the experience level of the class.

We then have a discussion about what some of the challenges are when building software. As well as what quality means, and how we can shoot for that in our software.

The birth of XP

This then segues into the birth of XP. Here I share Kent and Ward’s original vision of what XP was. Talk a little about the C3 project. And basically explain the XP attitudes behind if certain things are hard, we are going to continuously do them, all the time. Testing, integration, pairing, design, etc.

I also draw the cost of change curve and share how Kent wanted a way to develop software, such that the cost didn’t increase exponentially over time.

Screen Shot 2015-10-30 at 1.08.55 PM

Elephant Carpaccio

Partly because smaller stories are a good idea, and partly because it helps them with the project they do on day two, we then do an Elephant Carpaccio story slicing exercise.

https://docs.google.com/document/u/1/d/1TCuuu-8Mm14oxsOnlk8DqfZAA1cvtYu9WGv67Yj_sSk/pub

This is great because it reminds people about what makes stories valuable in the first place, while also giving advice on how to slice. Basics, but really good stuff for people who may not have read or had any story training.

TDD together

This is where we formally introduce TDD, and revisit the RPN calculator we built at the beginning of the course.

As a class, I start with one other person, showing them the mechanics behind writing the test first, making it pass, and then … sometimes refactoring. Sometimes I don’t refactor, just to let the duplication build up and save for conversation later.

But we do this as a group, and it gives students a nice intro on a codebase and a problem they already know.

Refactoring

Something that’s surprised me as a middle aged programmer (cough) is how many people still haven’t read Martin Fowlers seminal book on refactoring. I have a lot of fun with this.

Refactoring, even in really tight circles of programming, is still a very misunderstood term. Usually it just means rewriting code. But people don’t appreciate always that when you are refactoring you aren’t adding any new value. You are only improving the existing design.

So I really hit home that the reason why that word appears in a menu at the top of your favorite ID is because of this book. And then I ask how people refactor without unit tests.

It’s a trap of course. Because you can’t. But a lot of people still do. So we talk about that.

So that’s day one. And during the day we also sprinkle in discussions about YAGNI, production readiness, and other XPisms and attitudes.

Code me a game

Day two is all about putting TDD, unit testing, refactoring, continuous integration, collective code ownership, and pairing all into practice. In teams of four, the class then goes about building a text based adventure game.

Screen Shot 2015-10-30 at 1.12.24 PM

Text based games are great for learning TDD. They are fun, most people understand how they work, and they don’t contain a lot of hairiness. But they contain enough hairiness to give a taste of what applying TDD in the real world is like (like how do you handle all those input output streams?).

We have a few rules for the text based game we are going to build.

  1. No production code without a failing unit test.
  2. No code not written in pairs.
  3. Refactoring happens continuously while the code is being developed.
  4. Check in early and often.

Screen Shot 2015-10-30 at 1.14.34 PM

It’s really fun seeing how teams of x4 tackle handling a new code base. We also have the challenge that many people come from different parts of the world. So everyone has their own keyboard which can make pairing tricky.

But people overcome. We have lots of discussion about how to test, how to design, and how to tackle all the hairiness that seems to come with coding, even on a simple text based game.

We usually do x3 one hour iterations. With a demo, code review, and discussion at the end of each.

We also track number of commit, number of stories, and code coverage.

After three to four hours people are pretty pumped and exhausted. We then sit back and reflect on what we’ve learned.

It’s really interesting watching people try TDD for the first time. On the surface, when you see other people do it, it looks really easy. But it’s not. At least at first. It’s hard. It goes against everything not only everything you’ve been taught in school. It also not the natural state for people who are just used to hacking.

But once people get it, you can see a light go one. They design their code differently. They find they need less code. And it takes a lot of the guesswork away. They only end up creating what they need. And for many that’s a revelation.

Of course TDD is only one leg of the XP stool. And all the other practices also come into play – particularly pairing. People often ask how do you keep the discipline up. You play a big part of that I say. But your pair can help you too.

Insights, Actions, and Histories

We wrap up the day with Insights, Actions, and Mysteries. Here we ask people what they learned, things they want to do, and things we still wonder about.

Screen Shot 2015-10-30 at 5.09.06 PM

Screen Shot 2015-10-30 at 5.09.15 PM

Screen Shot 2015-10-30 at 5.09.22 PM
Big insights today were the awesomeness of pairing (you can learn a lot working with someone else). Actions were YAGNI – try hard not to over engineer. And mysteries were things like how fast to move when doing TDD vs going really slow and gearing down to really really small tests.

Overall it was a great day. I always learn as much if not more than the attendees. And this was a great group to work with. See you out there!

Screen Shot 2015-10-30 at 1.13.53 PM

Advertisements

Refactoring css

1 Comment

css is one of those things I am desperately trying to get good at, and a big part of that is knowing how to structure and refactor your css files.

Here’s a good example of some ugly css from Christian Heilman’s design chapter in Smashing Book#2.

#pagetitle {
  color: black;
  text-align: left;
  border-top-width: 2px;
  border-top-color: black;
  border-top-style: solid;
  border-width-bottom: 2px;
  ...
}

The first thing you can do to clean this up is logically order elements and use the shortcut notation.

#pagetitle {
  color: black;
  text-align: left;
  line-height: 1.3em;
  border: 2px solid white;
  border-color: black white white black;
  padding: 1em 2em;
  ...
}

The next thing you can do is move common denominators out of their specific selectors and collate them. For example you could refactor this:

h1  {
  font-family: helvetica, arial, sans-serif;
  color: #000;
  margin: 0.5em;
  padding: 1em;
  font-size: 150%;
  background: #ccc;
}

h1  {
  font-family: helvetica, arial, sans-serif;
  color: #000;
  margin: 0.5em 0;
  padding: 1em;
  font-size: 120%;
  background: #999;
}

Into this:

h1, h2, h3, h4 {
  font-family: helvetica, arial, sans-serif;
  color: #000;
  margin: 0.5em 0;
  padding: 1em;
}

h1 {
  font-size: 150%;
  background: #ccc;
}

h2 {
  font-size: 120%;
  background: #999;
}

See the difference? All the common stuff is up top, and only the difference are showing below. Way better.

Refactoring try catch statements in C#

3 Comments

Sometimeswhen you are writing C# you get a lot of code that looks like this:

        public int SaveDraft(DocumentDraftDto dto)
        {
            try
            {
                int id = task.SaveDraft(dto);
                context.StatusCode = HttpStatusCode.Created;
                return id;
            }
            catch (Exception e)
            {
                log.Error(string.Format("An error occurred when saving the draft for Username={0}.", dto.UpdateUser), e);
                context.StatusCode = HttpStatusCode.InternalServerError;
                return 0;
            }
        }

        public List<DocumentDraftDto> GetDrafts(string userId)
        {
            try
            {
                List<DocumentDraftDto> documentDraftDtos = task.GetDrafts(userId);
                context.StatusCode = HttpStatusCode.OK;
                return documentDraftDtos;
            }
            catch (Exception e)
            {
                log.Error(string.Format("An error occurred when retrieving drafts for UserId={0}.", userId), e);
                context.StatusCode = HttpStatusCode.InternalServerError;
                return null;
            }
        }

The same try/catch with the same code repeated again and again.

One way to clean this up is create on generic try catch statement, and pass a function of the method you want invoked to it:

        public int SaveDraft(DocumentDraftDto dto)
        {
            return CallDocumentDraftTask(x => x.SaveDraft(dto));
        }

        public List<DocumentDraftDto> GetDrafts(string userId)
        {
            return CallDocumentDraftTask(x => x.GetDrafts(userId));
        }

        private T CallDocumentDraftTask<T>(Func<IDocumentDraftTask, T> func)
        {
            try
            {
                T resurlt = func(task);
                context.StatusCode = func.Method.Name.Contains("SaveDraft") ? HttpStatusCode.Created : HttpStatusCode.OK;
                return resurlt;
            }
            catch (Exception e)
            {
                log.Error(string.Format("An error occurred when " + func.Method.Name), e);
                context.StatusCode = HttpStatusCode.InternalServerError;
                return default(T);
            }
        }

There. Much cleaner. And less noise. And less code to maintain.

Thanks to Allan Wu for showing me this.

Working effectively with legacy code

5 Comments

Every once in a while you encounter some crusty, old, calcified edifice of code that seems to defy all your attempts at change and proves equally hard to test.

Having recently crossed paths with some code of this nature, I pulled Michael Feathers Working Effectively with Legacy Code from my book shelf and re-introduced myself to three indispensable refactorings.

Not only did these techniques and strategies help me with my legacy code, they served as as good reminders for design maxims for new stuff.

1. Extract Interface and parameterize constructor.

This technique has become so widely used it’s one we almost take for granted today.

Say you have a class and you just want to assert that something happens in side on a particular method (or conversely you want it to do something like return a specific value).

    public class InvoiceService
    {
        InvoiceDto GetInvoice(int id)
        {
            // arg! how can I test that this happened?
            WebOperationContext.Current.OutgoingResponse.StatusCode = HttpStatusCode.OK;

            return new InvoiceTask().GetInvoice(id);
        }

    }

One way to get your hands on that pesky object is to create it externally and then pass it in through the constructor.

    public interface IWebOperationContext
    {
        HttpStatusCode StatusCode { get; set; }
    }

    public class InvoiceService
    {
        private IWebOperationContext ctx;

        // inject via constructor
        public InvoiceService(IWebOperationContext ctx)
        {
            this.ctx = ctx;
        }

        public InvoiceDto GetInvoice(int id)
        {
            // ahhh - this I can make assertions on
            ctx.StatusCode = HttpStatusCode.OK;

            return new InvoiceTask().GetInvoice(id);
        }

    }

Now when you create your test class, you can inject your own version of that class or use a mocking framework (like Moq for C#) to track that certain methods on your object get called.

    public class InvoiceServiceTest
    {
        [TestFixture]
        public class When_calling_the_invoice_service
        {
            private InvoiceService service;
            private Mock<IWebOperationContext> mockContext;

            [SetUp]
            public void SetUp()
            {
                mockContext = new Mock<IWebOperationContext>();
                service = new InvoiceService(mockContext.Object);
            }

            [Test]
            public void Should_be_able_to_get_N_invoice()
            {
                service.GetInvoice(1);
                
                // verify this happened
                mockContext.VerifySet(x => x.StatusCode = HttpStatusCode.OK);
            }

        }
    }

This is one of the easiest refactorings you can do to get your hands into legacy code and is used extensively in all sorts of Java, C#, and Ruby frameworks.

2. Extract and override Factory Method.

While extract interface should often be your first line of defense, sometimes you can’t create a new interface (or the constructor may be off limits).

In cases like these try extracting and overriding a factory method.

Say you have a class where the object initialization takes place in the constructor.


    public class UserService
    {
        private TransactionManager tm;

        public UserService()
        {
            // this is hard to test
            tm = new TransactionManager();
        }
    }

This can be a real pain because if you want to change the behavior of something inside, you have no obvious way to get your hands on it.

By creating a factory method for the object of desire however, you can create a subclass for the class under test, and then override the desired functionality there.


    public class UserService
    {
        private TransactionManager tm;

        public UserService()
        {
            // create a factory method
            tm = CreateTransactionManager();
        }

        protected virtual TransactionManager CreateTransactionManager()
        {
            return new TransactionManager();
        }
    }

    public class TestUserService : UserService
    {
        // and override here in the subclass
        protected override TransactionManager CreateTransactionManager()
        {
            return new FakeTransactionManager();
        }
    }

Now when we go to test our class, we can use our TestUserService, which will behave just like our real one, only we can control what we want to happen with any internal objects (like Transaction Manager).

3. Adapt Parameter.

When you can’t extract the interface, and the parameter you want to test is difficult to fake, try using adapt parameter.

The idea here is to take a method parameter that is hard to test, and wrap it in another where you can basically have it do whatever you want.

For example say have have a notoriously hard object with work with like Java’s HttpServletRequest. And you want a way of controlling what goes on with that object.


public class RequestDispatcher
{
    // hard to test method parameter
    public void populate(HttpServletRequest request)
    {
        String [] values = request.getParameterValues(pageStageName);

        if (values != null && values.length > 0)
        {
            marketBindings.put(values[0]);
        }
    }
}

Create a new interface (called ParameterSource) and use it as a wrapper for the method under test.


public class RequestDispatcher
{
    // hard to test method parameter
    public void populate(ParameterSource source)
    {
        String [] values = source.getParameterForName(pageStageName);

        if (values != null)
        {
            marketBindings.put(values[0]);
        }
    }
}

The concrete production version of your new class would look something like this:


public class ServletParameterSource implements ParameterSource
{
    private HttpServletRequest request;

    public ServletRequestSource(HttpServletRequest request) {
        this.request = request;
    }

    String getParameterValue(string name) {
        String[] values = request.getParameterValues(name);
        if (values == null || values.length <1)
            return null;
        return values[0];
    }
}

And you are free to create a fake one for testing purposes too.

Note: This technique is slightly more risky in that you are changing a methods external API. It may be worth it however if you need to make changes and want some tests backing you up.

So there you have it. Three simple techniques for making your code more testable.

These and many more great refactorings can be found in Michael Feathers excellent book Working Effectively with Legacy Code (highly recommended reading for any aspiring programmer).

Refactoring legacy code: Sprout Method

Leave a comment

In Refactoring Legacy Code Michael Feathers describes the Sprout Method as a way for adding new functionality to a system in a way that is easy to test.

For example say we want to get the host name and port number of the machine from which our Silverlight application was served so we can connect back to it using our Restful API (something I needed to do yesterday).

We could just drop that logic do do that into the method where it’s needed:

        private void PostComplexClick(object sender, RoutedEventArgs e)
        {
            ClearTextBoxes();

            string url = Application.Current.Host.Source.AbsoluteUri + "/InvoiceService.svc" + "/" + "invoices";

            HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
            request.Method = "POST";
            request.ContentType = "application/xml;charset=UTF-8"
            request.BeginGetRequestStream(PostComplexRequestReady, request);

        }

But that would be de-testable (pun intended). We can’t get our hands on the new code we want to test.

Instead, we can add what Michael calls a Sprout method and using the powers of OO put it into an abstraction we can test.

        [TestMethod]
        public void Should_be_able_to_get_machine_name_port_number_locally()
        {
            Assert.AreEqual(@"http://localhost:49657", Url.ServerRootParser());
        }

With implementation like this:

    public class Url
    {
        public static string ServerRoot()
        {
            return ServerRootParser(Application.Current.Host.Source.AbsoluteUri);
        }
     }

Now this is fine. Until we realize that our unit tests could be serviced from a different project than our application. In other words that hard coding of the port numbers would be very fragile.

Instead we can modify our tests so that they use some dummy data, and have the actual implementation do the work deeper in the object where it will work for all cases.

So tests and implementation then look something like this:

        [TestMethod]
        public void Should_be_able_to_get_machine_name_port_number_locally()
        {
            string documentUrl = @"http://localhost:49657/ClientBin/SilverlightRestExample.xap";
            Assert.AreEqual(@"http://localhost:49657", Url.ServerRootParser(documentUrl));
        }
    public class Url
    {
    
        public static string ServerRoot()
        {
            return ServerRootParser(Application.Current.Host.Source.AbsoluteUri);
        }

        public static class InvoiceService
        {
            public static readonly string Base = ServerRoot() + "/InvoiceService.svc";
            public const string Qualifier = "invoices";

            public static readonly string Get = Base + "/" + Qualifier + "/";
            public static readonly string Post = Base + "/" + Qualifier;
        }

        public static string ServerRootParser(string documentUrl)
        {
            int ptr = documentUrl.IndexOf("ClientBin");
            return documentUrl.Substring(0, ptr -1); // http://<machine>:<port>
        }
    }

Now we can test our ServerRootParser with whatever data we want, and no have to worry about the actual runtime result of

Application.Current.Host.Source.AbsoluteUri

I feel clumsy describing this (Michael does a much better job and I highly recommend his book). But just understanding that if you have some code that is hard test, that you can always create a new method (Sprout Method) or a new class (Sprout Class) is the point of this post.

%d bloggers like this: